Closed ncw closed 8 months ago
I have gone through some very not fun times dealing with when this should have the dir, etc. mode bits set and when not.
Yes I've been there too :-)
Are you sure that this is consistently handled this way in go? i.e. when I use the usual built-in
os
commands to getFileInfo
, does it always return with these bits set? If so, I am fine with it, but I want to be sure.
The os.FileMode
has had a chequered history in Go. At first it was just whatever was read from the OS but then Go got Windows support which is like putting a round peg in a square hole so it had to be changed. It is still rather unix centric, but it is platform independent now.
If you look at the help for fs.FileMode
(os.FileMode
is just an alias now-a-days) you'll see
type FileMode uint32
A FileMode represents a file's mode and permission bits. The bits have the
same definition on all systems, so that information about files can be moved
from one system to another portably. Not all bits apply to all systems.
The only required bit is ModeDir for directories.
And if you look at the actual definition of the bits you'll see that they are defined like this for all OSes.
// The defined file mode bits are the most significant bits of the FileMode.
// The nine least-significant bits are the standard Unix rwxrwxrwx permissions.
// The values of these bits should be considered part of the public API and
// may be used in wire protocols or disk representations: they must not be
// changed, although new bits might be added.
const (
// The single letters are the abbreviations
// used by the String method's formatting.
ModeDir FileMode = 1 << (32 - 1 - iota) // d: is a directory
ModeAppend // a: append-only
ModeExclusive // l: exclusive use
ModeTemporary // T: temporary file; Plan 9 only
ModeSymlink // L: symbolic link
ModeDevice // D: device file
ModeNamedPipe // p: named pipe (FIFO)
ModeSocket // S: Unix domain socket
ModeSetuid // u: setuid
ModeSetgid // g: setgid
ModeCharDevice // c: Unix character device, when ModeDevice is set
ModeSticky // t: sticky
ModeIrregular // ?: non-regular file; nothing else is known about this file
// Mask for the type bits. For regular files, none will be set.
ModeType = ModeDir | ModeSymlink | ModeNamedPipe | ModeSocket | ModeDevice | ModeCharDevice | ModeIrregular
ModePerm FileMode = 0777 // Unix permission bits
)
So I feel confident in saying that yes, it will always use exactly these bits whatever OS you are running on.
Perhaps the code I wrote to implement this should zero out everything except the 9 unix permissions bits so there aren't any Linux bits left in the mode so we've entirely Go-ified the mode. Currently it only zeroes out the fs.ModeType
which means it should work for all Go programs but there is a possibility of reading any other bits from the mode.
Perhaps the code I wrote to implement this should zero out everything except the 9 unix permissions bits so there aren't any Linux bits left in the mode so we've entirely Go-ified the mode.
Any downside to doing this? It sounds right to me, but 🤷♂️
If you look at the help for fs.FileMode (os.FileMode is just an alias now-a-days) you'll see
Yeah, I implemented a read-write fs.FS
interface and implementation for another project. Hard but good.
Perhaps the code I wrote to implement this should zero out everything except the 9 unix permissions bits so there aren't any Linux bits left in the mode so we've entirely Go-ified the mode.
Any downside to doing this? It sounds right to me, but 🤷♂️
I think making the FileMode 100% Go friendly is the right thing to do. If there are other bits in there we can extract to Go standard bits then that can be future work.
I've updated the PR
Yeah, I implemented a read-write
fs.FS
interface and implementation for another project. Hard but good.
:-)
I have gone through some very not fun times dealing with when this should have the dir, etc. mode bits set and when not. Are you sure that this is consistently handled this way in go? i.e. when I use the usual built-in
os
commands to getFileInfo
, does it always return with these bits set? If so, I am fine with it, but I want to be sure.