krew: Cross-device 'single file' copying on windows fails

PS W:\> .\krew.exe install --manifest=krew.yaml
Installing plugin: krew
W1029 12:35:34.778118   28440 install.go:127] failed to install plugin "krew": install failed: failed while moving files to the installation directory: could not rename file from "C:\\Users\\h\\AppData\\Local\\Temp\\krew-temp-move316849743" to "W:\\.krew\\store\\krew\\v0.3.1": rename C:\Users\h\AppData\Local\Temp\krew-temp-move316849743 W:\.krew\store\krew\v0.3.1: The system cannot move the file to a different disk drive.
F1029 12:35:34.781121   28440 root.go:58] failed to install some plugins: [krew]
  • Windows
  • Following installation instructions
  • Running the install command both from C: and W: fails

About this issue

  • Original URL
  • State: closed
  • Created 5 years ago
  • Reactions: 1
  • Comments: 23 (14 by maintainers)

Commits related to this issue

Most upvoted comments

This issue also affects me. I had to change the TMP env var to the C: disk and it worked.

So this is really odd… golang produces a *LinkError on all platforms, which contains the errno from the rename syscall. The error for moving files on Linux/Windows is a

type Errno uintptr

and on both platforms, the errno for moving across devices is EXDEV = 0x12 (see zerrors_linux_amd64.go and https://docs.microsoft.com/en-us/cpp/c-runtime-library/errno-doserrno-sys-errlist-and-sys-nerr?view=vs-2019).

So why does it not correctly determine that this is a failed move operation here?

if le, ok := err.(*os.LinkError); err != nil && ok {
	if errno, ok := le.Err.(syscall.Errno); ok && errno == 18 {
		glog.V(4).Infof("Cross-device link error (ERRNO=18), fallback to manual copy")
		return copyDir(from, to)
	}
}