Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

os: IsNotExist returns true for invalid file names #23105

Closed
perillo opened this issue Dec 12, 2017 · 10 comments
Closed

os: IsNotExist returns true for invalid file names #23105

perillo opened this issue Dec 12, 2017 · 10 comments
Labels
FrozenDueToAge NeedsFix The path to resolution is known, but the work has not been done.
Milestone

Comments

@perillo
Copy link
Contributor

perillo commented Dec 12, 2017

What version of Go are you using (go version)?

go1.9.2 linux/amd64

Does this issue reproduce with the latest release?

Yes

What operating system and processor architecture are you using (go env)?

GOARCH="amd64"
GOBIN="/home/manlio/.local/bin"
GOEXE=""
GOHOSTARCH="amd64"
GOHOSTOS="linux"
GOOS="linux"
GOPATH="/home/manlio/.local/lib/go:/home/manlio/code/src/go"
GORACE=""
GOROOT="/usr/lib/go"
GOTOOLDIR="/usr/lib/go/pkg/tool/linux_amd64"
GCCGO="gccgo"
CC="gcc"
GOGCCFLAGS="-fPIC -m64 -pthread -fmessage-length=0 -fdebug-prefix-map=/tmp/go-build134836490=/tmp/go-build -gno-record-gcc-switches"
CXX="g++"
CGO_ENABLED="1"
CGO_CFLAGS="-g -O2"
CGO_CPPFLAGS=""
CGO_CXXFLAGS="-g -O2"
CGO_FFLAGS="-g -O2"
CGO_LDFLAGS="-g -O2"
PKG_CONFIG="pkg-config"

What did you do?

https://play.golang.org/p/7xo02WfeHR

Also, see https://groups.google.com/forum/#!topic/golang-nuts/MZ_u50ZIB_I

What did you expect to see?

file does not exist

What did you see instead?

file exist
stat xxx...xxx: File name too long

@perillo
Copy link
Contributor Author

perillo commented Dec 12, 2017

This is probably a duplicate of #18974

@ianlancetaylor
Copy link
Contributor

@perillo I don't think it's a dup. #18974 was about ENOTDIR. This is about ENAMETOOLONG. I think it would be reasonable for IsNotExist to return true for ENAMETOOLONG; if we see that error, we know for sure that the file does not exist.

@ianlancetaylor ianlancetaylor added the NeedsFix The path to resolution is known, but the work has not been done. label Dec 12, 2017
@ianlancetaylor ianlancetaylor added this to the Go1.11 milestone Dec 12, 2017
@slrz
Copy link

slrz commented Dec 12, 2017

Responding to ENAMETOOLONG probably warrants a different approach than with ENOENT/ErrNotExist. I don't think it should be covered by IsNotExist. I always thought of the latter as "a syscall returned ENOENT(or a Go function returned an error with similar semantics)". ENAMETOOLONG doesn't match that pattern.

The code looks very misleading to me: just because IsNotExist returns false on an error returned from stat, you can't conclude that the file exists. The call might've also hit some wildly different error.

@mvdan
Copy link
Member

mvdan commented Dec 12, 2017

Shouldn't the issue title read false instead of true?

@ianlancetaylor
Copy link
Contributor

@slrz Upon reflection, I think you're right. One could imagine a deep set of directories, a/b/c/d where let's assume that each letter is actually 255 characters long. Then opening a/b/c/d/e might fail with ENAMETOOLONG, whereas os.Chdir("a/b/c") followed by opening d/e might succeed. At least, that is my current understanding. If that is indeed possible, then I agree that ENAMETOOLONG does not necessarily mean that the file does not exist.

@mattn
Copy link
Member

mattn commented Dec 13, 2017

I don't think this should be fixed. non-nil err does not mean file not exists.

https://play.golang.org/p/BnbP5Lik-l

@perillo
Copy link
Contributor Author

perillo commented Dec 13, 2017

@mattn https://play.golang.org/p/MPqPCmPcjE

The linux man(3) page about errno defines ENAMETOOLONG as "Filename too long"
but the man(2) page about stat defines it as "pathname is too long"

From https://en.wikipedia.org/wiki/Filename and https://en.wikipedia.org/wiki/Path_(computing) it seems that pathname and filename are equivalent, so I don't understand why in my code os.Stat returns ENOENT instead of ENAMETOOLONG.

@tv42
Copy link

tv42 commented Dec 13, 2017

ENAMETOOLONG means the kernel refuses to deal with your input, and thus provides no information on whether a file exists or not.

@perillo, you need to handle your errors, of which IsNotExist is just one scenario. @mattn's example https://play.golang.org/p/BnbP5Lik-l is the right way to do it (apart from unnecessary nesting).

As far as I can tell, there is no bug here.

@taruti
Copy link
Contributor

taruti commented Dec 13, 2017

Please don't change the functionality of os.IsNotExist for ENAMETOOLONG or the various Windows cases.

@bradfitz
Copy link
Contributor

Sounds like we don't want to change anything here and there's no bug.

@golang golang locked and limited conversation to collaborators May 29, 2019
Sign up for free to subscribe to this conversation on GitHub. Already have an account? Sign in.
Labels
FrozenDueToAge NeedsFix The path to resolution is known, but the work has not been done.
Projects
None yet
Development

No branches or pull requests

9 participants