{"action":"created","issue":{"url":"https://api.github.com/repos/golang/go/issues/3358","repository_url":"https://api.github.com/repos/golang/go","labels_url":"https://api.github.com/repos/golang/go/issues/3358/labels{/name}","comments_url":"https://api.github.com/repos/golang/go/issues/3358/comments","events_url":"https://api.github.com/repos/golang/go/issues/3358/events","html_url":"https://github.com/golang/go/issues/3358","id":51280467,"number":3358,"title":"os: some functions fail if full paths are long (more than about 250 chars) on windows","user":{"login":"alexbrainman","id":9796621,"avatar_url":"https://avatars.githubusercontent.com/u/9796621?v=3","gravatar_id":"","url":"https://api.github.com/users/alexbrainman","html_url":"https://github.com/alexbrainman","followers_url":"https://api.github.com/users/alexbrainman/followers","following_url":"https://api.github.com/users/alexbrainman/following{/other_user}","gists_url":"https://api.github.com/users/alexbrainman/gists{/gist_id}","starred_url":"https://api.github.com/users/alexbrainman/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/alexbrainman/subscriptions","organizations_url":"https://api.github.com/users/alexbrainman/orgs","repos_url":"https://api.github.com/users/alexbrainman/repos","events_url":"https://api.github.com/users/alexbrainman/events{/privacy}","received_events_url":"https://api.github.com/users/alexbrainman/received_events","type":"User","site_admin":false},"labels":[{"url":"https://api.github.com/repos/golang/go/labels/OS-Windows","name":"OS-Windows","color":"ededed"}],"state":"open","locked":false,"assignee":null,"milestone":{"url":"https://api.github.com/repos/golang/go/milestones/6","html_url":"https://github.com/golang/go/milestones/Unplanned","labels_url":"https://api.github.com/repos/golang/go/milestones/6/labels","id":1055141,"number":6,"title":"Unplanned","description":"No plan to fix in any specific release.\r\n","creator":{"login":"rsc","id":104030,"avatar_url":"https://avatars.githubusercontent.com/u/104030?v=3","gravatar_id":"","url":"https://api.github.com/users/rsc","html_url":"https://github.com/rsc","followers_url":"https://api.github.com/users/rsc/followers","following_url":"https://api.github.com/users/rsc/following{/other_user}","gists_url":"https://api.github.com/users/rsc/gists{/gist_id}","starred_url":"https://api.github.com/users/rsc/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/rsc/subscriptions","organizations_url":"https://api.github.com/users/rsc/orgs","repos_url":"https://api.github.com/users/rsc/repos","events_url":"https://api.github.com/users/rsc/events{/privacy}","received_events_url":"https://api.github.com/users/rsc/received_events","type":"User","site_admin":false},"open_issues":1333,"closed_issues":395,"state":"open","created_at":"2015-04-06T20:47:19Z","updated_at":"2016-05-09T21:32:28Z","due_on":"2099-12-31T05:00:00Z","closed_at":null},"comments":31,"created_at":"2012-03-20T05:47:54Z","updated_at":"2016-05-09T21:50:14Z","closed_at":null,"body":"<pre>This program creates directory, but fails to create file inside (CAREFUL IF CHANGING\nTHIS PROGRAM - YOU MIGHT END UP WITH FILES/DIRECTORIES YOU WILL NOT BE ABLE TO DELETE\nWITH STANDARD SHELL TOOLS):\n\npackage main\n\nimport (\n\t&quot;fmt&quot;\n\t&quot;log&quot;\n\t&quot;os&quot;\n\t&quot;strings&quot;\n)\n\nfunc main() {\n//\troot := `\\\\?\\c:\\`\n\troot := `c:\\`\n\tdir := root + strings.Repeat(&quot;d&quot;, 200)\n\tfile := dir + `\\` + strings.Repeat(&quot;f&quot;, 200)\n\terr := os.Mkdir(dir, 0777)\n\tif err != nil {\n\t\tlog.Fatalf(&quot;Mkdir(%s): %v&quot;, dir, err)\n\t}\n\tf, err := os.Create(file)\n\tif err != nil {\n\t\tlog.Fatalf(&quot;Create(%s): %v&quot;, file, err)\n\t}\n\t_, err = fmt.Fprintf(f, &quot;Hello world&quot;)\n\tif err != nil {\n\t\tlog.Fatalf(&quot;Fprintf(%s): %v&quot;, file, err)\n\t}\n\terr = f.Close()\n\tif err != nil {\n\t\tlog.Fatalf(&quot;Close(%s): %v&quot;, file, err)\n\t}\n\terr = os.Remove(file)\n\tif err != nil {\n\t\tlog.Fatalf(&quot;Remove(%s): %v&quot;, file, err)\n\t}\n\terr = os.Remove(dir)\n\tif err != nil {\n\t\tlog.Fatalf(&quot;Remove(%s): %v&quot;, dir, err)\n\t}\n}\n\nThis can be handled properly if we use \\\\?\\ path prefix (uncomment line in the code).\nBut \\\\?\\ prefixed paths needs to be &quot;normalized&quot;: they have to be absolute, no\n. or .. allowed, / is not allowed, UNC paths needs to be handled properly. See\n<a href=\"http://goo.gl/th2fJ\">http://goo.gl/th2fJ</a> for details, especially &quot;Maximum Path Length Limitation&quot;\nsection.\n\nThis issue has come up on our own builder: <a href=\"http://goo.gl/FbblU\">http://goo.gl/FbblU</a>. Perhaps our own paths do\nnot need to be that long. I did not look into that yet.\n\nAlex</pre>"},"comment":{"url":"https://api.github.com/repos/golang/go/issues/comments/218000832","html_url":"https://github.com/golang/go/issues/3358#issuecomment-218000832","issue_url":"https://api.github.com/repos/golang/go/issues/3358","id":218000832,"user":{"login":"iafan","id":1728158,"avatar_url":"https://avatars.githubusercontent.com/u/1728158?v=3","gravatar_id":"","url":"https://api.github.com/users/iafan","html_url":"https://github.com/iafan","followers_url":"https://api.github.com/users/iafan/followers","following_url":"https://api.github.com/users/iafan/following{/other_user}","gists_url":"https://api.github.com/users/iafan/gists{/gist_id}","starred_url":"https://api.github.com/users/iafan/starred{/owner}{/repo}","subscriptions_url":"https://api.github.com/users/iafan/subscriptions","organizations_url":"https://api.github.com/users/iafan/orgs","repos_url":"https://api.github.com/users/iafan/repos","events_url":"https://api.github.com/users/iafan/events{/privacy}","received_events_url":"https://api.github.com/users/iafan/received_events","type":"User","site_admin":false},"created_at":"2016-05-09T21:50:14Z","updated_at":"2016-05-09T21:50:14Z","body":"Hi there. Just ran across the same issue in #15615 (thanks to @bradfitz for pointing me to this thread). \r\n\r\nI don't think it makes sense to \"magically\" fix the file paths on every syscall, tbh. My concern is, obviously, the speed. I traverse a huge directory tree, and I don't want Go internals to be analyzing and fixing the path deep in the loop, when the proper solution in my case would be to provide a `\\\\?\\`-prefixed canonical path just once in the call to `filepath.Walk()`.\r\n\r\nWhat makes sense to me is to have some helper function, e.g. `filepath.Canonicalize()` that, under Windows, would replace all `/` with `\\` and prepend `\\\\?\\` (or return an error if the provided path is not absolute). This way everyone can use such a function as early as possible (when processing user input or external data), and forget about _\"if windows then ... else ...\"_ kind of code. The very existence of such a function, along with its documentation, will make other developers aware of OS-specific caveats. Other corresponding FS-related functions might then link to that function.\r\n\r\nInternal functions that return the file path, like `os.Getwd()`, `os.TempDir()` or `filepath.Abs()` could also benefit from returning a canonicalized path that other functions can safely consume."}}