diff --git a/hack/vendor.sh b/hack/vendor.sh index 5467f2e1aa..9eaee3a1e1 100755 --- a/hack/vendor.sh +++ b/hack/vendor.sh @@ -78,7 +78,7 @@ clone git github.com/philhofer/fwd 899e4efba8eaa1fea74175308f3fae18ff3319fa clone git github.com/tinylib/msgp 75ee40d2601edf122ef667e2a07d600d4c44490c # fsnotify -clone git gopkg.in/fsnotify.v1 v1.2.0 +clone git gopkg.in/fsnotify.v1 v1.2.11 # awslogs deps clone git github.com/aws/aws-sdk-go v0.9.9 diff --git a/vendor/src/gopkg.in/fsnotify.v1/.travis.yml b/vendor/src/gopkg.in/fsnotify.v1/.travis.yml index 67467e1407..00fd5dd30c 100644 --- a/vendor/src/gopkg.in/fsnotify.v1/.travis.yml +++ b/vendor/src/gopkg.in/fsnotify.v1/.travis.yml @@ -2,10 +2,24 @@ sudo: false language: go go: - - 1.4.1 + - 1.5.4 + - 1.6.1 + - tip + +matrix: + allow_failures: + - go: tip before_script: - - FIXED=$(go fmt ./... | wc -l); if [ $FIXED -gt 0 ]; then echo "gofmt - $FIXED file(s) not formatted correctly, please run gofmt to fix this." && exit 1; fi + - go get -u github.com/golang/lint/golint + +script: + - go test -v --race ./... + +after_script: + - test -z "$(gofmt -s -l -w . | tee /dev/stderr)" + - test -z "$(golint ./... | tee /dev/stderr)" + - go vet ./... os: - linux diff --git a/vendor/src/gopkg.in/fsnotify.v1/AUTHORS b/vendor/src/gopkg.in/fsnotify.v1/AUTHORS index 4e0e8284e9..6438bb31ce 100644 --- a/vendor/src/gopkg.in/fsnotify.v1/AUTHORS +++ b/vendor/src/gopkg.in/fsnotify.v1/AUTHORS @@ -9,22 +9,30 @@ # Please keep the list sorted. Adrien Bustany +Amit Krishnan +Bjørn Erik Pedersen Caleb Spare Case Nelson -Chris Howey +Chris Howey Christoffer Buchholz +Daniel Wagner-Hall Dave Cheney +Evan Phoenix Francisco Souza Hari haran John C Barstow Kelvin Fo +Ken-ichirou MATSUZAWA Matt Layher Nathan Youngman Paul Hammond +Pawel Knap Pieter Droogendijk Pursuit92 +Riku Voipio Rob Figueiredo Soge Zhang +Tiffany Jernigan Tilak Sharma Travis Cline Tudor Golubenco @@ -32,3 +40,4 @@ Yukang bronze1man debrando henrikedwards +铁哥 diff --git a/vendor/src/gopkg.in/fsnotify.v1/CHANGELOG.md b/vendor/src/gopkg.in/fsnotify.v1/CHANGELOG.md index ea9428a2a4..44ca62e537 100644 --- a/vendor/src/gopkg.in/fsnotify.v1/CHANGELOG.md +++ b/vendor/src/gopkg.in/fsnotify.v1/CHANGELOG.md @@ -1,53 +1,78 @@ # Changelog +## v1.2.10 / 2016-03-02 + +* Fix golint errors in windows.go [#121](https://github.com/fsnotify/fsnotify/pull/121) (thanks @tiffanyfj) + +## v1.2.9 / 2016-01-13 + +kqueue: Fix logic for CREATE after REMOVE [#111](https://github.com/fsnotify/fsnotify/pull/111) (thanks @bep) + +## v1.2.8 / 2015-12-17 + +* kqueue: fix race condition in Close [#105](https://github.com/fsnotify/fsnotify/pull/105) (thanks @djui for reporting the issue and @ppknap for writing a failing test) +* inotify: fix race in test +* enable race detection for continuous integration (Linux, Mac, Windows) + +## v1.2.5 / 2015-10-17 + +* inotify: use epoll_create1 for arm64 support (requires Linux 2.6.27 or later) [#100](https://github.com/fsnotify/fsnotify/pull/100) (thanks @suihkulokki) +* inotify: fix path leaks [#73](https://github.com/fsnotify/fsnotify/pull/73) (thanks @chamaken) +* kqueue: watch for rename events on subdirectories [#83](https://github.com/fsnotify/fsnotify/pull/83) (thanks @guotie) +* kqueue: avoid infinite loops from symlinks cycles [#101](https://github.com/fsnotify/fsnotify/pull/101) (thanks @illicitonion) + +## v1.2.1 / 2015-10-14 + +* kqueue: don't watch named pipes [#98](https://github.com/fsnotify/fsnotify/pull/98) (thanks @evanphx) + ## v1.2.0 / 2015-02-08 -* inotify: use epoll to wake up readEvents [#66](https://github.com/go-fsnotify/fsnotify/pull/66) (thanks @PieterD) -* inotify: closing watcher should now always shut down goroutine [#63](https://github.com/go-fsnotify/fsnotify/pull/63) (thanks @PieterD) -* kqueue: close kqueue after removing watches, fixes [#59](https://github.com/go-fsnotify/fsnotify/issues/59) +* inotify: use epoll to wake up readEvents [#66](https://github.com/fsnotify/fsnotify/pull/66) (thanks @PieterD) +* inotify: closing watcher should now always shut down goroutine [#63](https://github.com/fsnotify/fsnotify/pull/63) (thanks @PieterD) +* kqueue: close kqueue after removing watches, fixes [#59](https://github.com/fsnotify/fsnotify/issues/59) ## v1.1.1 / 2015-02-05 -* inotify: Retry read on EINTR [#61](https://github.com/go-fsnotify/fsnotify/issues/61) (thanks @PieterD) +* inotify: Retry read on EINTR [#61](https://github.com/fsnotify/fsnotify/issues/61) (thanks @PieterD) ## v1.1.0 / 2014-12-12 -* kqueue: rework internals [#43](https://github.com/go-fsnotify/fsnotify/pull/43) +* kqueue: rework internals [#43](https://github.com/fsnotify/fsnotify/pull/43) * add low-level functions * only need to store flags on directories - * less mutexes [#13](https://github.com/go-fsnotify/fsnotify/issues/13) + * less mutexes [#13](https://github.com/fsnotify/fsnotify/issues/13) * done can be an unbuffered channel * remove calls to os.NewSyscallError -* More efficient string concatenation for Event.String() [#52](https://github.com/go-fsnotify/fsnotify/pull/52) (thanks @mdlayher) -* kqueue: fix regression in rework causing subdirectories to be watched [#48](https://github.com/go-fsnotify/fsnotify/issues/48) -* kqueue: cleanup internal watch before sending remove event [#51](https://github.com/go-fsnotify/fsnotify/issues/51) +* More efficient string concatenation for Event.String() [#52](https://github.com/fsnotify/fsnotify/pull/52) (thanks @mdlayher) +* kqueue: fix regression in rework causing subdirectories to be watched [#48](https://github.com/fsnotify/fsnotify/issues/48) +* kqueue: cleanup internal watch before sending remove event [#51](https://github.com/fsnotify/fsnotify/issues/51) ## v1.0.4 / 2014-09-07 * kqueue: add dragonfly to the build tags. * Rename source code files, rearrange code so exported APIs are at the top. -* Add done channel to example code. [#37](https://github.com/go-fsnotify/fsnotify/pull/37) (thanks @chenyukang) +* Add done channel to example code. [#37](https://github.com/fsnotify/fsnotify/pull/37) (thanks @chenyukang) ## v1.0.3 / 2014-08-19 -* [Fix] Windows MOVED_TO now translates to Create like on BSD and Linux. [#36](https://github.com/go-fsnotify/fsnotify/issues/36) +* [Fix] Windows MOVED_TO now translates to Create like on BSD and Linux. [#36](https://github.com/fsnotify/fsnotify/issues/36) ## v1.0.2 / 2014-08-17 -* [Fix] Missing create events on OS X. [#14](https://github.com/go-fsnotify/fsnotify/issues/14) (thanks @zhsso) +* [Fix] Missing create events on OS X. [#14](https://github.com/fsnotify/fsnotify/issues/14) (thanks @zhsso) * [Fix] Make ./path and path equivalent. (thanks @zhsso) ## v1.0.0 / 2014-08-15 * [API] Remove AddWatch on Windows, use Add. -* Improve documentation for exported identifiers. [#30](https://github.com/go-fsnotify/fsnotify/issues/30) +* Improve documentation for exported identifiers. [#30](https://github.com/fsnotify/fsnotify/issues/30) * Minor updates based on feedback from golint. ## dev / 2014-07-09 -* Moved to [github.com/go-fsnotify/fsnotify](https://github.com/go-fsnotify/fsnotify). +* Moved to [github.com/fsnotify/fsnotify](https://github.com/fsnotify/fsnotify). * Use os.NewSyscallError instead of returning errno (thanks @hariharan-uno) - + ## dev / 2014-07-04 * kqueue: fix incorrect mutex used in Close() @@ -55,7 +80,7 @@ ## dev / 2014-06-28 -* [API] Don't set the Write Op for attribute notifications [#4](https://github.com/go-fsnotify/fsnotify/issues/4) +* [API] Don't set the Write Op for attribute notifications [#4](https://github.com/fsnotify/fsnotify/issues/4) * Fix for String() method on Event (thanks Alex Brainman) * Don't build on Plan 9 or Solaris (thanks @4ad) @@ -93,11 +118,11 @@ ## v0.9.3 / 2014-12-31 -* kqueue: cleanup internal watch before sending remove event [#51](https://github.com/go-fsnotify/fsnotify/issues/51) +* kqueue: cleanup internal watch before sending remove event [#51](https://github.com/fsnotify/fsnotify/issues/51) ## v0.9.2 / 2014-08-17 -* [Backport] Fix missing create events on OS X. [#14](https://github.com/go-fsnotify/fsnotify/issues/14) (thanks @zhsso) +* [Backport] Fix missing create events on OS X. [#14](https://github.com/fsnotify/fsnotify/issues/14) (thanks @zhsso) ## v0.9.1 / 2014-06-12 @@ -260,4 +285,3 @@ [#25]: https://github.com/howeyc/fsnotify/issues/25 [#24]: https://github.com/howeyc/fsnotify/issues/24 [#21]: https://github.com/howeyc/fsnotify/issues/21 - diff --git a/vendor/src/gopkg.in/fsnotify.v1/CONTRIBUTING.md b/vendor/src/gopkg.in/fsnotify.v1/CONTRIBUTING.md index 0f377f341b..617e45a06e 100644 --- a/vendor/src/gopkg.in/fsnotify.v1/CONTRIBUTING.md +++ b/vendor/src/gopkg.in/fsnotify.v1/CONTRIBUTING.md @@ -2,7 +2,7 @@ ## Issues -* Request features and report bugs using the [GitHub Issue Tracker](https://github.com/go-fsnotify/fsnotify/issues). +* Request features and report bugs using the [GitHub Issue Tracker](https://github.com/fsnotify/fsnotify/issues). * Please indicate the platform you are using fsnotify on. * A code example to reproduce the problem is appreciated. @@ -10,7 +10,7 @@ ### Contributor License Agreement -fsnotify is derived from code in the [golang.org/x/exp](https://godoc.org/golang.org/x/exp) package and it may be included [in the standard library](https://github.com/go-fsnotify/fsnotify/issues/1) in the future. Therefore fsnotify carries the same [LICENSE](https://github.com/go-fsnotify/fsnotify/blob/master/LICENSE) as Go. Contributors retain their copyright, so you need to fill out a short form before we can accept your contribution: [Google Individual Contributor License Agreement](https://developers.google.com/open-source/cla/individual). +fsnotify is derived from code in the [golang.org/x/exp](https://godoc.org/golang.org/x/exp) package and it may be included [in the standard library](https://github.com/fsnotify/fsnotify/issues/1) in the future. Therefore fsnotify carries the same [LICENSE](https://github.com/fsnotify/fsnotify/blob/master/LICENSE) as Go. Contributors retain their copyright, so you need to fill out a short form before we can accept your contribution: [Google Individual Contributor License Agreement](https://developers.google.com/open-source/cla/individual). Please indicate that you have signed the CLA in your pull request. @@ -28,7 +28,7 @@ Please indicate that you have signed the CLA in your pull request. For smooth sailing, always use the original import path. Installing with `go get` makes this easy. -1. Install from GitHub (`go get -u github.com/go-fsnotify/fsnotify`) +1. Install from GitHub (`go get -u github.com/fsnotify/fsnotify`) 2. Create your feature branch (`git checkout -b my-new-feature`) 3. Ensure everything works and the tests pass (see below) 4. Commit your changes (`git commit -am 'Add some feature'`) @@ -53,7 +53,7 @@ To aid in cross-platform testing there is a Vagrantfile for Linux and BSD. * Install [Vagrant](http://www.vagrantup.com/) and [VirtualBox](https://www.virtualbox.org/) * Setup [Vagrant Gopher](https://github.com/nathany/vagrant-gopher) in your `src` folder. * Run `vagrant up` from the project folder. You can also setup just one box with `vagrant up linux` or `vagrant up bsd` (note: the BSD box doesn't support Windows hosts at this time, and NFS may prompt for your host OS password) -* Once setup, you can run the test suite on a given OS with a single command `vagrant ssh linux -c 'cd go-fsnotify/fsnotify; go test'`. +* Once setup, you can run the test suite on a given OS with a single command `vagrant ssh linux -c 'cd fsnotify/fsnotify; go test'`. * When you're done, you will want to halt or destroy the Vagrant boxes. Notice: fsnotify file system events won't trigger in shared folders. The tests get around this limitation by using the /tmp directory. diff --git a/vendor/src/gopkg.in/fsnotify.v1/NotUsed.xcworkspace b/vendor/src/gopkg.in/fsnotify.v1/NotUsed.xcworkspace deleted file mode 100644 index e69de29bb2..0000000000 diff --git a/vendor/src/gopkg.in/fsnotify.v1/README.md b/vendor/src/gopkg.in/fsnotify.v1/README.md index 7a0b247364..fee2a36ba4 100644 --- a/vendor/src/gopkg.in/fsnotify.v1/README.md +++ b/vendor/src/gopkg.in/fsnotify.v1/README.md @@ -1,6 +1,6 @@ # File system notifications for Go -[![Coverage](http://gocover.io/_badge/github.com/go-fsnotify/fsnotify)](http://gocover.io/github.com/go-fsnotify/fsnotify) [![GoDoc](https://godoc.org/gopkg.in/fsnotify.v1?status.svg)](https://godoc.org/gopkg.in/fsnotify.v1) +[![GoDoc](https://godoc.org/github.com/fsnotify/fsnotify?status.svg)](https://godoc.org/github.com/fsnotify/fsnotify) [![Go Report Card](https://goreportcard.com/badge/github.com/fsnotify/fsnotify)](https://goreportcard.com/report/github.com/fsnotify/fsnotify) [![Coverage](http://gocover.io/_badge/github.com/fsnotify/fsnotify)](http://gocover.io/github.com/fsnotify/fsnotify) Go 1.3+ required. @@ -8,44 +8,26 @@ Cross platform: Windows, Linux, BSD and OS X. |Adapter |OS |Status | |----------|----------|----------| -|inotify |Linux, Android\*|Supported [![Build Status](https://travis-ci.org/go-fsnotify/fsnotify.svg?branch=master)](https://travis-ci.org/go-fsnotify/fsnotify)| -|kqueue |BSD, OS X, iOS\*|Supported [![Circle CI](https://circleci.com/gh/go-fsnotify/fsnotify.svg?style=svg)](https://circleci.com/gh/go-fsnotify/fsnotify)| +|inotify |Linux 2.6.27 or later, Android\*|Supported [![Build Status](https://travis-ci.org/fsnotify/fsnotify.svg?branch=master)](https://travis-ci.org/fsnotify/fsnotify)| +|kqueue |BSD, OS X, iOS\*|Supported [![Build Status](https://travis-ci.org/fsnotify/fsnotify.svg?branch=master)](https://travis-ci.org/fsnotify/fsnotify)| |ReadDirectoryChangesW|Windows|Supported [![Build status](https://ci.appveyor.com/api/projects/status/ivwjubaih4r0udeh/branch/master?svg=true)](https://ci.appveyor.com/project/NathanYoungman/fsnotify/branch/master)| -|FSEvents |OS X |[Planned](https://github.com/go-fsnotify/fsnotify/issues/11)| -|FEN |Solaris 11 |[Planned](https://github.com/go-fsnotify/fsnotify/issues/12)| +|FSEvents |OS X |[Planned](https://github.com/fsnotify/fsnotify/issues/11)| +|FEN |Solaris 11 |[In Progress](https://github.com/fsnotify/fsnotify/issues/12)| |fanotify |Linux 2.6.37+ | | -|USN Journals |Windows |[Maybe](https://github.com/go-fsnotify/fsnotify/issues/53)| -|Polling |*All* |[Maybe](https://github.com/go-fsnotify/fsnotify/issues/9)| +|USN Journals |Windows |[Maybe](https://github.com/fsnotify/fsnotify/issues/53)| +|Polling |*All* |[Maybe](https://github.com/fsnotify/fsnotify/issues/9)| \* Android and iOS are untested. -Please see [the documentation](https://godoc.org/gopkg.in/fsnotify.v1) for usage. Consult the [Wiki](https://github.com/go-fsnotify/fsnotify/wiki) for the FAQ and further information. +Please see [the documentation](https://godoc.org/github.com/fsnotify/fsnotify) for usage. Consult the [Wiki](https://github.com/fsnotify/fsnotify/wiki) for the FAQ and further information. ## API stability -Two major versions of fsnotify exist. +fsnotify is a fork of [howeyc/fsnotify](https://godoc.org/github.com/howeyc/fsnotify) with a new API as of v1.0. The API is based on [this design document](http://goo.gl/MrYxyA). -**[fsnotify.v0](https://gopkg.in/fsnotify.v0)** is API-compatible with [howeyc/fsnotify](https://godoc.org/github.com/howeyc/fsnotify). Bugfixes *may* be backported, but I recommend upgrading to v1. +All [releases](https://github.com/fsnotify/fsnotify/releases) are tagged based on [Semantic Versioning](http://semver.org/). Further API changes are [planned](https://github.com/fsnotify/fsnotify/milestones), and will be tagged with a new major revision number. -```go -import "gopkg.in/fsnotify.v0" -``` - -\* Refer to the package as fsnotify (without the .v0 suffix). - -**[fsnotify.v1](https://gopkg.in/fsnotify.v1)** provides [a new API](https://godoc.org/gopkg.in/fsnotify.v1) based on [this design document](http://goo.gl/MrYxyA). You can import v1 with: - -```go -import "gopkg.in/fsnotify.v1" -``` - -Further API changes are [planned](https://github.com/go-fsnotify/fsnotify/milestones), but a new major revision will be tagged, so you can depend on the v1 API. - -**Master** may have unreleased changes. Use it to test the very latest code or when [contributing][], but don't expect it to remain API-compatible: - -```go -import "github.com/go-fsnotify/fsnotify" -``` +Go 1.6 supports dependencies located in the `vendor/` folder. Unless you are creating a library, it is recommended that you copy fsnotify into `vendor/github.com/fsnotify/fsnotify` within your project. ## Contributing @@ -53,7 +35,12 @@ Please refer to [CONTRIBUTING][] before opening an issue or pull request. ## Example -See [example_test.go](https://github.com/go-fsnotify/fsnotify/blob/master/example_test.go). +See [example_test.go](https://github.com/fsnotify/fsnotify/blob/master/example_test.go). +[contributing]: https://github.com/fsnotify/fsnotify/blob/master/CONTRIBUTING.md + +## Related Projects + +* [notify](https://github.com/rjeczalik/notify) +* [fsevents](https://github.com/fsnotify/fsevents) -[contributing]: https://github.com/go-fsnotify/fsnotify/blob/master/CONTRIBUTING.md diff --git a/vendor/src/gopkg.in/fsnotify.v1/circle.yml b/vendor/src/gopkg.in/fsnotify.v1/circle.yml deleted file mode 100644 index 204217fb0b..0000000000 --- a/vendor/src/gopkg.in/fsnotify.v1/circle.yml +++ /dev/null @@ -1,26 +0,0 @@ -## OS X build (CircleCI iOS beta) - -# Pretend like it's an Xcode project, at least to get it running. -machine: - environment: - XCODE_WORKSPACE: NotUsed.xcworkspace - XCODE_SCHEME: NotUsed - # This is where the go project is actually checked out to: - CIRCLE_BUILD_DIR: $HOME/.go_project/src/github.com/go-fsnotify/fsnotify - -dependencies: - pre: - - brew upgrade go - -test: - override: - - go test ./... - -# Idealized future config, eventually with cross-platform build matrix :-) - -# machine: -# go: -# version: 1.4 -# os: -# - osx -# - linux diff --git a/vendor/src/gopkg.in/fsnotify.v1/fen.go b/vendor/src/gopkg.in/fsnotify.v1/fen.go new file mode 100644 index 0000000000..ced39cb881 --- /dev/null +++ b/vendor/src/gopkg.in/fsnotify.v1/fen.go @@ -0,0 +1,37 @@ +// Copyright 2010 The Go Authors. All rights reserved. +// Use of this source code is governed by a BSD-style +// license that can be found in the LICENSE file. + +// +build solaris + +package fsnotify + +import ( + "errors" +) + +// Watcher watches a set of files, delivering events to a channel. +type Watcher struct { + Events chan Event + Errors chan error +} + +// NewWatcher establishes a new watcher with the underlying OS and begins waiting for events. +func NewWatcher() (*Watcher, error) { + return nil, errors.New("FEN based watcher not yet supported for fsnotify\n") +} + +// Close removes all watches and closes the events channel. +func (w *Watcher) Close() error { + return nil +} + +// Add starts watching the named file or directory (non-recursively). +func (w *Watcher) Add(name string) error { + return nil +} + +// Remove stops watching the the named file or directory (non-recursively). +func (w *Watcher) Remove(name string) error { + return nil +} diff --git a/vendor/src/gopkg.in/fsnotify.v1/fsnotify.go b/vendor/src/gopkg.in/fsnotify.v1/fsnotify.go index c899ee0083..d1d39a0ebd 100644 --- a/vendor/src/gopkg.in/fsnotify.v1/fsnotify.go +++ b/vendor/src/gopkg.in/fsnotify.v1/fsnotify.go @@ -2,7 +2,7 @@ // Use of this source code is governed by a BSD-style // license that can be found in the LICENSE file. -// +build !plan9,!solaris +// +build !plan9 // Package fsnotify provides a platform-independent interface for file system notifications. package fsnotify diff --git a/vendor/src/gopkg.in/fsnotify.v1/inotify.go b/vendor/src/gopkg.in/fsnotify.v1/inotify.go index d7759ec8c8..780b2a005d 100644 --- a/vendor/src/gopkg.in/fsnotify.v1/inotify.go +++ b/vendor/src/gopkg.in/fsnotify.v1/inotify.go @@ -23,6 +23,7 @@ type Watcher struct { Events chan Event Errors chan error mu sync.Mutex // Map access + cv *sync.Cond // sync removing on rm_watch with IN_IGNORE fd int poller *fdPoller watches map[string]*watch // Map of inotify watches (key: path) @@ -54,6 +55,7 @@ func NewWatcher() (*Watcher, error) { done: make(chan struct{}), doneResp: make(chan struct{}), } + w.cv = sync.NewCond(&w.mu) go w.readEvents() return w, nil @@ -134,8 +136,10 @@ func (w *Watcher) Remove(name string) error { } // inotify_rm_watch will return EINVAL if the file has been deleted; // the inotify will already have been removed. - // That means we can safely delete it from our watches, whatever inotify_rm_watch does. - delete(w.watches, name) + // watches and pathes are deleted in ignoreLinux() implicitly and asynchronously + // by calling inotify_rm_watch() below. e.g. readEvents() goroutine receives IN_IGNORE + // so that EINVAL means that the wd is being rm_watch()ed or its file removed + // by another thread and we have not received IN_IGNORE event. success, errno := syscall.InotifyRmWatch(w.fd, watch.wd) if success == -1 { // TODO: Perhaps it's not helpful to return an error here in every case. @@ -146,6 +150,14 @@ func (w *Watcher) Remove(name string) error { // explicitly by inotify_rm_watch, implicitly when the file they are watching is deleted. return errno } + + // wait until ignoreLinux() deleting maps + exists := true + for exists { + w.cv.Wait() + _, exists = w.watches[name] + } + return nil } @@ -209,7 +221,7 @@ func (w *Watcher) readEvents() { // If EOF is received. This should really never happen. err = io.EOF } else if n < 0 { - // If an error occured while reading. + // If an error occurred while reading. err = errno } else { // Read was too short. @@ -249,7 +261,7 @@ func (w *Watcher) readEvents() { event := newEvent(name, mask) // Send the events that are not ignored on the events channel - if !event.ignoreLinux(mask) { + if !event.ignoreLinux(w, raw.Wd, mask) { select { case w.Events <- event: case <-w.done: @@ -266,9 +278,15 @@ func (w *Watcher) readEvents() { // Certain types of events can be "ignored" and not sent over the Events // channel. Such as events marked ignore by the kernel, or MODIFY events // against files that do not exist. -func (e *Event) ignoreLinux(mask uint32) bool { +func (e *Event) ignoreLinux(w *Watcher, wd int32, mask uint32) bool { // Ignore anything the inotify API says to ignore if mask&syscall.IN_IGNORED == syscall.IN_IGNORED { + w.mu.Lock() + defer w.mu.Unlock() + name := w.paths[int(wd)] + delete(w.paths, int(wd)) + delete(w.watches, name) + w.cv.Broadcast() return true } diff --git a/vendor/src/gopkg.in/fsnotify.v1/inotify_poller.go b/vendor/src/gopkg.in/fsnotify.v1/inotify_poller.go index 3b41784041..23a5ca1460 100644 --- a/vendor/src/gopkg.in/fsnotify.v1/inotify_poller.go +++ b/vendor/src/gopkg.in/fsnotify.v1/inotify_poller.go @@ -39,7 +39,7 @@ func newFdPoller(fd int) (*fdPoller, error) { poller.fd = fd // Create epoll fd - poller.epfd, errno = syscall.EpollCreate(1) + poller.epfd, errno = syscall.EpollCreate1(0) if poller.epfd == -1 { return nil, errno } diff --git a/vendor/src/gopkg.in/fsnotify.v1/kqueue.go b/vendor/src/gopkg.in/fsnotify.v1/kqueue.go index 265622d201..b8ea30846d 100644 --- a/vendor/src/gopkg.in/fsnotify.v1/kqueue.go +++ b/vendor/src/gopkg.in/fsnotify.v1/kqueue.go @@ -72,12 +72,17 @@ func (w *Watcher) Close() error { w.isClosed = true w.mu.Unlock() + // copy paths to remove while locked w.mu.Lock() - ws := w.watches + var pathsToRemove = make([]string, 0, len(w.watches)) + for name := range w.watches { + pathsToRemove = append(pathsToRemove, name) + } w.mu.Unlock() + // unlock before calling Remove, which also locks var err error - for name := range ws { + for _, name := range pathsToRemove { if e := w.Remove(name); e != nil && err == nil { err = e } @@ -94,7 +99,8 @@ func (w *Watcher) Add(name string) error { w.mu.Lock() w.externalWatches[name] = true w.mu.Unlock() - return w.addWatch(name, noteAllEvents) + _, err := w.addWatch(name, noteAllEvents) + return err } // Remove stops watching the the named file or directory (non-recursively). @@ -153,7 +159,8 @@ var keventWaitTime = durationToTimespec(100 * time.Millisecond) // addWatch adds name to the watched file set. // The flags are interpreted as described in kevent(2). -func (w *Watcher) addWatch(name string, flags uint32) error { +// Returns the real path to the file which was added, if any, which may be different from the one passed in the case of symlinks. +func (w *Watcher) addWatch(name string, flags uint32) (string, error) { var isDir bool // Make ./name and name equivalent name = filepath.Clean(name) @@ -161,7 +168,7 @@ func (w *Watcher) addWatch(name string, flags uint32) error { w.mu.Lock() if w.isClosed { w.mu.Unlock() - return errors.New("kevent instance already closed") + return "", errors.New("kevent instance already closed") } watchfd, alreadyWatching := w.watches[name] // We already have a watch, but we can still override flags. @@ -173,12 +180,17 @@ func (w *Watcher) addWatch(name string, flags uint32) error { if !alreadyWatching { fi, err := os.Lstat(name) if err != nil { - return err + return "", err } // Don't watch sockets. if fi.Mode()&os.ModeSocket == os.ModeSocket { - return nil + return "", nil + } + + // Don't watch named pipes. + if fi.Mode()&os.ModeNamedPipe == os.ModeNamedPipe { + return "", nil } // Follow Symlinks @@ -190,18 +202,26 @@ func (w *Watcher) addWatch(name string, flags uint32) error { if fi.Mode()&os.ModeSymlink == os.ModeSymlink { name, err = filepath.EvalSymlinks(name) if err != nil { - return nil + return "", nil + } + + w.mu.Lock() + _, alreadyWatching = w.watches[name] + w.mu.Unlock() + + if alreadyWatching { + return name, nil } fi, err = os.Lstat(name) if err != nil { - return nil + return "", nil } } watchfd, err = syscall.Open(name, openMode, 0700) if watchfd == -1 { - return err + return "", err } isDir = fi.IsDir() @@ -210,7 +230,7 @@ func (w *Watcher) addWatch(name string, flags uint32) error { const registerAdd = syscall.EV_ADD | syscall.EV_CLEAR | syscall.EV_ENABLE if err := register(w.kq, []int{watchfd}, registerAdd, flags); err != nil { syscall.Close(watchfd) - return err + return "", err } if !alreadyWatching { @@ -224,6 +244,7 @@ func (w *Watcher) addWatch(name string, flags uint32) error { // Watch the directory if it has not been watched before, // or if it was watched before, but perhaps only a NOTE_DELETE (watchDirectoryFiles) w.mu.Lock() + watchDir := (flags&syscall.NOTE_WRITE) == syscall.NOTE_WRITE && (!alreadyWatching || (w.dirFlags[name]&syscall.NOTE_WRITE) != syscall.NOTE_WRITE) // Store flags so this watch can be updated later @@ -232,11 +253,11 @@ func (w *Watcher) addWatch(name string, flags uint32) error { if watchDir { if err := w.watchDirectoryFiles(name); err != nil { - return err + return "", err } } } - return nil + return name, nil } // readEvents reads from kqueue and converts the received kevents into @@ -304,19 +325,24 @@ func (w *Watcher) readEvents() { if event.Op&Remove == Remove { // Look for a file that may have overwritten this. // For example, mv f1 f2 will delete f2, then create f2. - fileDir, _ := filepath.Split(event.Name) - fileDir = filepath.Clean(fileDir) - w.mu.Lock() - _, found := w.watches[fileDir] - w.mu.Unlock() - if found { - // make sure the directory exists before we watch for changes. When we - // do a recursive watch and perform rm -fr, the parent directory might - // have gone missing, ignore the missing directory and let the - // upcoming delete event remove the watch from the parent directory. - if _, err := os.Lstat(fileDir); os.IsExist(err) { - w.sendDirectoryChangeEvents(fileDir) - // FIXME: should this be for events on files or just isDir? + if path.isDir { + fileDir := filepath.Clean(event.Name) + w.mu.Lock() + _, found := w.watches[fileDir] + w.mu.Unlock() + if found { + // make sure the directory exists before we watch for changes. When we + // do a recursive watch and perform rm -fr, the parent directory might + // have gone missing, ignore the missing directory and let the + // upcoming delete event remove the watch from the parent directory. + if _, err := os.Lstat(fileDir); err == nil { + w.sendDirectoryChangeEvents(fileDir) + } + } + } else { + filePath := filepath.Clean(event.Name) + if fileInfo, err := os.Lstat(filePath); err == nil { + w.sendFileCreatedEventIfNew(filePath, fileInfo) } } } @@ -359,7 +385,8 @@ func (w *Watcher) watchDirectoryFiles(dirPath string) error { for _, fileInfo := range files { filePath := filepath.Join(dirPath, fileInfo.Name()) - if err := w.internalWatch(filePath, fileInfo); err != nil { + filePath, err = w.internalWatch(filePath, fileInfo) + if err != nil { return err } @@ -385,26 +412,38 @@ func (w *Watcher) sendDirectoryChangeEvents(dirPath string) { // Search for new files for _, fileInfo := range files { filePath := filepath.Join(dirPath, fileInfo.Name()) - w.mu.Lock() - _, doesExist := w.fileExists[filePath] - w.mu.Unlock() - if !doesExist { - // Send create event - w.Events <- newCreateEvent(filePath) - } + err := w.sendFileCreatedEventIfNew(filePath, fileInfo) - // like watchDirectoryFiles (but without doing another ReadDir) - if err := w.internalWatch(filePath, fileInfo); err != nil { + if err != nil { return } - - w.mu.Lock() - w.fileExists[filePath] = true - w.mu.Unlock() } } -func (w *Watcher) internalWatch(name string, fileInfo os.FileInfo) error { +// sendFileCreatedEvent sends a create event if the file isn't already being tracked. +func (w *Watcher) sendFileCreatedEventIfNew(filePath string, fileInfo os.FileInfo) (err error) { + w.mu.Lock() + _, doesExist := w.fileExists[filePath] + w.mu.Unlock() + if !doesExist { + // Send create event + w.Events <- newCreateEvent(filePath) + } + + // like watchDirectoryFiles (but without doing another ReadDir) + filePath, err = w.internalWatch(filePath, fileInfo) + if err != nil { + return err + } + + w.mu.Lock() + w.fileExists[filePath] = true + w.mu.Unlock() + + return nil +} + +func (w *Watcher) internalWatch(name string, fileInfo os.FileInfo) (string, error) { if fileInfo.IsDir() { // mimic Linux providing delete events for subdirectories // but preserve the flags used if currently watching subdirectory @@ -412,7 +451,7 @@ func (w *Watcher) internalWatch(name string, fileInfo os.FileInfo) error { flags := w.dirFlags[name] w.mu.Unlock() - flags |= syscall.NOTE_DELETE + flags |= syscall.NOTE_DELETE | syscall.NOTE_RENAME return w.addWatch(name, flags) } diff --git a/vendor/src/gopkg.in/fsnotify.v1/windows.go b/vendor/src/gopkg.in/fsnotify.v1/windows.go index 811585227d..c836bdb3db 100644 --- a/vendor/src/gopkg.in/fsnotify.v1/windows.go +++ b/vendor/src/gopkg.in/fsnotify.v1/windows.go @@ -71,7 +71,7 @@ func (w *Watcher) Add(name string) error { in := &input{ op: opAddWatch, path: filepath.Clean(name), - flags: sys_FS_ALL_EVENTS, + flags: sysFSALLEVENTS, reply: make(chan error), } w.input <- in @@ -97,43 +97,43 @@ func (w *Watcher) Remove(name string) error { const ( // Options for AddWatch - sys_FS_ONESHOT = 0x80000000 - sys_FS_ONLYDIR = 0x1000000 + sysFSONESHOT = 0x80000000 + sysFSONLYDIR = 0x1000000 // Events - sys_FS_ACCESS = 0x1 - sys_FS_ALL_EVENTS = 0xfff - sys_FS_ATTRIB = 0x4 - sys_FS_CLOSE = 0x18 - sys_FS_CREATE = 0x100 - sys_FS_DELETE = 0x200 - sys_FS_DELETE_SELF = 0x400 - sys_FS_MODIFY = 0x2 - sys_FS_MOVE = 0xc0 - sys_FS_MOVED_FROM = 0x40 - sys_FS_MOVED_TO = 0x80 - sys_FS_MOVE_SELF = 0x800 + sysFSACCESS = 0x1 + sysFSALLEVENTS = 0xfff + sysFSATTRIB = 0x4 + sysFSCLOSE = 0x18 + sysFSCREATE = 0x100 + sysFSDELETE = 0x200 + sysFSDELETESELF = 0x400 + sysFSMODIFY = 0x2 + sysFSMOVE = 0xc0 + sysFSMOVEDFROM = 0x40 + sysFSMOVEDTO = 0x80 + sysFSMOVESELF = 0x800 // Special events - sys_FS_IGNORED = 0x8000 - sys_FS_Q_OVERFLOW = 0x4000 + sysFSIGNORED = 0x8000 + sysFSQOVERFLOW = 0x4000 ) func newEvent(name string, mask uint32) Event { e := Event{Name: name} - if mask&sys_FS_CREATE == sys_FS_CREATE || mask&sys_FS_MOVED_TO == sys_FS_MOVED_TO { + if mask&sysFSCREATE == sysFSCREATE || mask&sysFSMOVEDTO == sysFSMOVEDTO { e.Op |= Create } - if mask&sys_FS_DELETE == sys_FS_DELETE || mask&sys_FS_DELETE_SELF == sys_FS_DELETE_SELF { + if mask&sysFSDELETE == sysFSDELETE || mask&sysFSDELETESELF == sysFSDELETESELF { e.Op |= Remove } - if mask&sys_FS_MODIFY == sys_FS_MODIFY { + if mask&sysFSMODIFY == sysFSMODIFY { e.Op |= Write } - if mask&sys_FS_MOVE == sys_FS_MOVE || mask&sys_FS_MOVE_SELF == sys_FS_MOVE_SELF || mask&sys_FS_MOVED_FROM == sys_FS_MOVED_FROM { + if mask&sysFSMOVE == sysFSMOVE || mask&sysFSMOVESELF == sysFSMOVESELF || mask&sysFSMOVEDFROM == sysFSMOVEDFROM { e.Op |= Rename } - if mask&sys_FS_ATTRIB == sys_FS_ATTRIB { + if mask&sysFSATTRIB == sysFSATTRIB { e.Op |= Chmod } return e @@ -242,7 +242,7 @@ func (w *Watcher) addWatch(pathname string, flags uint64) error { if err != nil { return err } - if flags&sys_FS_ONLYDIR != 0 && pathname != dir { + if flags&sysFSONLYDIR != 0 && pathname != dir { return nil } ino, err := getIno(dir) @@ -302,11 +302,11 @@ func (w *Watcher) remWatch(pathname string) error { return fmt.Errorf("can't remove non-existent watch for: %s", pathname) } if pathname == dir { - w.sendEvent(watch.path, watch.mask&sys_FS_IGNORED) + w.sendEvent(watch.path, watch.mask&sysFSIGNORED) watch.mask = 0 } else { name := filepath.Base(pathname) - w.sendEvent(watch.path+"\\"+name, watch.names[name]&sys_FS_IGNORED) + w.sendEvent(watch.path+"\\"+name, watch.names[name]&sysFSIGNORED) delete(watch.names, name) } return w.startRead(watch) @@ -316,13 +316,13 @@ func (w *Watcher) remWatch(pathname string) error { func (w *Watcher) deleteWatch(watch *watch) { for name, mask := range watch.names { if mask&provisional == 0 { - w.sendEvent(watch.path+"\\"+name, mask&sys_FS_IGNORED) + w.sendEvent(watch.path+"\\"+name, mask&sysFSIGNORED) } delete(watch.names, name) } if watch.mask != 0 { if watch.mask&provisional == 0 { - w.sendEvent(watch.path, watch.mask&sys_FS_IGNORED) + w.sendEvent(watch.path, watch.mask&sysFSIGNORED) } watch.mask = 0 } @@ -353,8 +353,8 @@ func (w *Watcher) startRead(watch *watch) error { err := os.NewSyscallError("ReadDirectoryChanges", e) if e == syscall.ERROR_ACCESS_DENIED && watch.mask&provisional == 0 { // Watched directory was probably removed - if w.sendEvent(watch.path, watch.mask&sys_FS_DELETE_SELF) { - if watch.mask&sys_FS_ONESHOT != 0 { + if w.sendEvent(watch.path, watch.mask&sysFSDELETESELF) { + if watch.mask&sysFSONESHOT != 0 { watch.mask = 0 } } @@ -428,7 +428,7 @@ func (w *Watcher) readEvents() { } case syscall.ERROR_ACCESS_DENIED: // Watched directory was probably removed - w.sendEvent(watch.path, watch.mask&sys_FS_DELETE_SELF) + w.sendEvent(watch.path, watch.mask&sysFSDELETESELF) w.deleteWatch(watch) w.startRead(watch) continue @@ -444,7 +444,7 @@ func (w *Watcher) readEvents() { var offset uint32 for { if n == 0 { - w.Events <- newEvent("", sys_FS_Q_OVERFLOW) + w.Events <- newEvent("", sysFSQOVERFLOW) w.Errors <- errors.New("short read in readEvents()") break } @@ -458,22 +458,22 @@ func (w *Watcher) readEvents() { var mask uint64 switch raw.Action { case syscall.FILE_ACTION_REMOVED: - mask = sys_FS_DELETE_SELF + mask = sysFSDELETESELF case syscall.FILE_ACTION_MODIFIED: - mask = sys_FS_MODIFY + mask = sysFSMODIFY case syscall.FILE_ACTION_RENAMED_OLD_NAME: watch.rename = name case syscall.FILE_ACTION_RENAMED_NEW_NAME: if watch.names[watch.rename] != 0 { watch.names[name] |= watch.names[watch.rename] delete(watch.names, watch.rename) - mask = sys_FS_MOVE_SELF + mask = sysFSMOVESELF } } sendNameEvent := func() { if w.sendEvent(fullname, watch.names[name]&mask) { - if watch.names[name]&sys_FS_ONESHOT != 0 { + if watch.names[name]&sysFSONESHOT != 0 { delete(watch.names, name) } } @@ -482,11 +482,11 @@ func (w *Watcher) readEvents() { sendNameEvent() } if raw.Action == syscall.FILE_ACTION_REMOVED { - w.sendEvent(fullname, watch.names[name]&sys_FS_IGNORED) + w.sendEvent(fullname, watch.names[name]&sysFSIGNORED) delete(watch.names, name) } if w.sendEvent(fullname, watch.mask&toFSnotifyFlags(raw.Action)) { - if watch.mask&sys_FS_ONESHOT != 0 { + if watch.mask&sysFSONESHOT != 0 { watch.mask = 0 } } @@ -529,16 +529,16 @@ func (w *Watcher) sendEvent(name string, mask uint64) bool { func toWindowsFlags(mask uint64) uint32 { var m uint32 - if mask&sys_FS_ACCESS != 0 { + if mask&sysFSACCESS != 0 { m |= syscall.FILE_NOTIFY_CHANGE_LAST_ACCESS } - if mask&sys_FS_MODIFY != 0 { + if mask&sysFSMODIFY != 0 { m |= syscall.FILE_NOTIFY_CHANGE_LAST_WRITE } - if mask&sys_FS_ATTRIB != 0 { + if mask&sysFSATTRIB != 0 { m |= syscall.FILE_NOTIFY_CHANGE_ATTRIBUTES } - if mask&(sys_FS_MOVE|sys_FS_CREATE|sys_FS_DELETE) != 0 { + if mask&(sysFSMOVE|sysFSCREATE|sysFSDELETE) != 0 { m |= syscall.FILE_NOTIFY_CHANGE_FILE_NAME | syscall.FILE_NOTIFY_CHANGE_DIR_NAME } return m @@ -547,15 +547,15 @@ func toWindowsFlags(mask uint64) uint32 { func toFSnotifyFlags(action uint32) uint64 { switch action { case syscall.FILE_ACTION_ADDED: - return sys_FS_CREATE + return sysFSCREATE case syscall.FILE_ACTION_REMOVED: - return sys_FS_DELETE + return sysFSDELETE case syscall.FILE_ACTION_MODIFIED: - return sys_FS_MODIFY + return sysFSMODIFY case syscall.FILE_ACTION_RENAMED_OLD_NAME: - return sys_FS_MOVED_FROM + return sysFSMOVEDFROM case syscall.FILE_ACTION_RENAMED_NEW_NAME: - return sys_FS_MOVED_TO + return sysFSMOVEDTO } return 0 }