Re: RCS file ownership?
Hi all! Years ago, I mean 10+, I was -- strangely -- quite actively using RCS for local configuration file history management, and fell into the same pit myself. I made this [1] off the cuff diff then, and reading this thread thought that I need to see how badly it would apply for today's tree. Well, surprisingly, it succeeded without any rejections, so here it is, maybe someone will find it useful. It's automatic, so no option to enable this when invoking rcs(1). Also, all I did was just regenerating the diff, not compiled or tested now... And I'm pretty sure I have had some troubles with it back then... Anyway, enjoy :) Dani [1] https://gist.github.com/levaidaniel/dfc71d782a6e023459c04a3f30ff5a6e ‐‐‐ Original Message ‐‐‐ > Date: Thu, 30 Apr 2020 10:37:38 +0100 > From: Craig Skinner skin...@britvault.co.uk > To: misc@openbsd.org > Subject: Re: RCS file ownership? > Message-ID: 20200430103738.1f7304f6@fir.internal > > G'day Adam/all, > > On Wed, 29 Apr 2020 12:43:42 -0500 Adam Thompson wrote: > > > When I use co(1) with "-l" to check out a file (and/or "ci -l") is > > there any way to preserve file ownership and not have it reset to > > the user running co(1) or ci(1)? > > Attached is a script I've used for years to work around this issue. > > No licence, do what you want with it. > > Rather rubbish to do this in the shell > > cop = check out, permissions > cip = check in, permissions > > $ ls -ltrhF /usr/local/bin/c* | fgrep ciop > -r-xr-xr-x 1 root bin 1.8K Jun 29 2013 /usr/local/bin/ciop* > lrwxr-xr-x 1 root wheel 4B Apr 13 2015 /usr/local/bin/cop@ -> ciop > lrwxr-xr-x 1 root wheel 4B Apr 13 2015 /usr/local/bin/cip@ -> ciop > > Cheers, > > -- > > Craig Skinner | http://linkd.in/yGqkv7 > > [Attachment of type application/octet-stream removed.]
Re: RCS file ownership?
Adam Thompson wrote: > AFAICT, GNU RCS (v5.9.4, ca. 2015, examined) creates a temp file, > unlinks the target file, then renames the temp file. I beleve this > guarantees(-ish, modulo "special" filesystems including NFS and > FreeBSD's directory-SUID behaviour) that resulting file ownership = > euid. mktemp and rename sound like reasonable. > The GNU docs mention the repo owner in passing a few times but do not > have a section describing multi-user operation. The documentation is irrelevant. It should focus on what the code does, why it seems to do it, and about whether the resulting behaviour is convenient. > I'm not sure which other implementations you'd be worried about All of them. > - I thought OpenBSD's RCS was the direct descendant of NetBSD's and > shares common lineage with the other *BSDs? The top of each source file claims otherwise. It is a rewrite. > All in all, it looks like RCS and its docs were written in the era > when UNIX machines were - more or less by universally - used by > multiple people, and you just had an innate sense of how multi-user > file ownership would work. Most of my UNIX machines now resemble > appliances, and exactly zero of them are multi-user in the classical > sense. Documentation is irrelevant.
Re: RCS file ownership?
Being neither a C programmer nor a Texinfo fan, checking GNU RCS is a bit painful, and my conclusions aren't guaranteed. AFAICT, GNU RCS (v5.9.4, ca. 2015, examined) creates a temp file, unlinks the target file, then renames the temp file. I beleve this guarantees(-ish, modulo "special" filesystems including NFS and FreeBSD's directory-SUID behaviour) that resulting file ownership = euid. The GNU docs mention the repo owner in passing a few times but do not have a section describing multi-user operation. The Tichy docs also don't mention file ownership. I'm trying to review the O'Donovan book, too, but it's been a long time since I had to tool up to handle raw PS... not quite there yet. Purdue RCS appears to be the direct ancestor of GNU RCS. I'm not sure which other implementations you'd be worried about - I thought OpenBSD's RCS was the direct descendant of NetBSD's and shares common lineage with the other *BSDs? All in all, it looks like RCS and its docs were written in the era when UNIX machines were - more or less by universally - used by multiple people, and you just had an innate sense of how multi-user file ownership would work. Most of my UNIX machines now resemble appliances, and exactly zero of them are multi-user in the classical sense. -Adam On 2020-04-29 21:53, Theo de Raadt wrote: Sorry, but my mail goes further. It says it should be correct. For some definition of correct. It should either behave somehow for a logical reason, or it should behave in the historical fashion. Or once the historical behaviour is looked at, if there is an argument that is wrong, then it should be changed with logic about "this is an improvement" backing the argument. I think it is wrong to document how *this* rcs implimentation behaves, without comparing it against others. My guess is 50% that the others don't unlink, but rewrite the file. And the changes it might require to be compatible are not substantial. At most a 20 line diff, to a few programs in the family. athom...@athompso.net wrote: Thank you for that detail! Addressing this one corner case would require substantial changes, I think. Not worth it, in my opinion. I think it would be worthwhile describing the multi-user mode of operation of RCS in the manual, as it's currently completely absent/omitted. Patch coming soon, maybe tomorrow if I can make time. -Adam On Apr. 29, 2020 21:28, Theo de Raadt wrote: athom...@athompso.net wrote: > Heh, good point. Didn't even occur to me because as it happens, I am > running as root and would like to not change the ownership.-Adam > On Apr. 29, 2020 13:32, Anders Andersson wrote: > > On Wed, Apr 29, 2020 at 7:46 PM Adam Thompson > wrote: > > > > When I use co(1) with "-l" to check out a file (and/or "ci -l") is > there > > any way to preserve file ownership and *not* have it reset to the > user > > running co(1) or ci(1)? > > I don't see anything in rcs(1), co(1) or ci(1) that even mentions > the > > fact that the file will wind up owned by the user running the > command. > > Ideas? Pointers to documentation? > > How could it possibly do anything else unless you always run co as > root? Our rcs tools do: 52628 co RET kbind 0 52628 co CALL unlink(0x7f7ed1f3) 52628 co NAMI "ls.c" 52628 co RET unlink -1 errno 2 No such file or directory 52628 co CALL open (0x7f7ed1f3,0x601,0100444) 52628 co NAMI "ls.c" 52628 co RET open 4 52628 co CALL kbind(0x7f7ec908,24,0x847da2a816b5d817) Which appears to be this: else { (void)unlink(dst); if ((fd = open(dst, O_WRONLY|O_CREAT|O_TRUNC, mode)) == -1) err(1, "%s", dst); I don't know what older or gnu rcs do. I guess whichever way this is done it must balance concerns between atomicity of concurrent reads performed by earlier processes, versus replacement of a potentially active file. If the latter is chosen, it would unlink(), perform the open more carefully, check that it is in the right place with fstat, but then it needs some work for ftruncate (to get rid of extra file contents at the end). If the open() failed, it might try an unlink followed by open()? Other rcs implimentations need to be checked. It is better if they work the same.
Re: RCS file ownership?
G'day Adam/all, On Wed, 29 Apr 2020 12:43:42 -0500 Adam Thompson wrote: > When I use co(1) with "-l" to check out a file (and/or "ci -l") is > there any way to preserve file ownership and *not* have it reset to > the user running co(1) or ci(1)? Attached is a script I've used for years to work around this issue. No licence, do what you want with it. Rather rubbish to do this in the shell cop = check out, permissions cip = check in, permissions $ ls -ltrhF /usr/local/bin/c* | fgrep ciop -r-xr-xr-x 1 root bin 1.8K Jun 29 2013 /usr/local/bin/ciop* lrwxr-xr-x 1 root wheel 4B Apr 13 2015 /usr/local/bin/cop@ -> ciop lrwxr-xr-x 1 root wheel 4B Apr 13 2015 /usr/local/bin/cip@ -> ciop Cheers, -- Craig Skinner | http://linkd.in/yGqkv7 ciop Description: Binary data
Re: RCS file ownership?
Sorry, but my mail goes further. It says it should be correct. For some definition of correct. It should either behave somehow for a logical reason, or it should behave in the historical fashion. Or once the historical behaviour is looked at, if there is an argument that is wrong, then it should be changed with logic about "this is an improvement" backing the argument. I think it is wrong to document how *this* rcs implimentation behaves, without comparing it against others. My guess is 50% that the others don't unlink, but rewrite the file. And the changes it might require to be compatible are not substantial. At most a 20 line diff, to a few programs in the family. athom...@athompso.net wrote: > Thank you for that detail! > > Addressing this one corner case would require substantial changes, I think. > Not worth > it, in my opinion. > > I think it would be worthwhile describing the multi-user mode of operation of > RCS in > the manual, as it's currently completely absent/omitted. Patch coming soon, > maybe > tomorrow if I can make time. > > -Adam > > On Apr. 29, 2020 21:28, Theo de Raadt wrote: > > athom...@athompso.net wrote: > > > Heh, good point. Didn't even occur to me because as it happens, I am > > running as root and would like to not change the ownership.-Adam > > On Apr. 29, 2020 13:32, Anders Andersson wrote: > > > > On Wed, Apr 29, 2020 at 7:46 PM Adam Thompson > > wrote: > > > > > > When I use co(1) with "-l" to check out a file (and/or "ci -l") is > > there > > > any way to preserve file ownership and *not* have it reset to the > > user > > > running co(1) or ci(1)? > > > I don't see anything in rcs(1), co(1) or ci(1) that even mentions > > the > > > fact that the file will wind up owned by the user running the > > command. > > > Ideas? Pointers to documentation? > > > > How could it possibly do anything else unless you always run co as > > root? > > Our rcs tools do: > > 52628 co RET kbind 0 > 52628 co CALL unlink(0x7f7ed1f3) > 52628 co NAMI "ls.c" > 52628 co RET unlink -1 errno 2 No such file or directory > 52628 co CALL open > (0x7f7ed1f3,0x601,0100444 |S_IRGRP|S_IROTH|S_IFREG>) > 52628 co NAMI "ls.c" > 52628 co RET open 4 > 52628 co CALL kbind(0x7f7ec908,24,0x847da2a816b5d817) > > Which appears to be this: > > else { > (void)unlink(dst); > > if ((fd = open(dst, O_WRONLY|O_CREAT|O_TRUNC, mode)) == -1) > err(1, "%s", dst); > > I don't know what older or gnu rcs do. I guess whichever way this is done > it must balance concerns between atomicity of concurrent reads performed > by earlier processes, versus replacement of a potentially active file. > > If the latter is chosen, it would unlink(), perform the open more > carefully, check that it is in the right place with fstat, but then > it needs some work for ftruncate (to get rid of extra file contents > at the end). If the open() failed, it might try an unlink followed by > open()? > > Other rcs implimentations need to be checked. It is better if they work > the same. >
Re: RCS file ownership?
Thank you for that detail! Addressing this one corner case would require substantial changes, I think. Not worth it, in my opinion. I think it would be worthwhile describing the multi-user mode of operation of RCS in the manual, as it's currently completely absent/omitted. Patch coming soon, maybe tomorrow if I can make time. -Adam On Apr. 29, 2020 21:28, Theo de Raadt wrote: athom...@athompso.net wrote: > Heh, good point. Didn't even occur to me because as it happens, I am > running as root and would like to not change the ownership.-Adam > On Apr. 29, 2020 13:32, Anders Andersson wrote: > > On Wed, Apr 29, 2020 at 7:46 PM Adam Thompson > wrote: > > > > When I use co(1) with "-l" to check out a file (and/or "ci -l") is > there > > any way to preserve file ownership and *not* have it reset to the > user > > running co(1) or ci(1)? > > I don't see anything in rcs(1), co(1) or ci(1) that even mentions > the > > fact that the file will wind up owned by the user running the > command. > > Ideas? Pointers to documentation? > > How could it possibly do anything else unless you always run co as > root? Our rcs tools do: 52628 co RET kbind 0 52628 co CALL unlink(0x7f7ed1f3) 52628 co NAMI "ls.c" 52628 co RET unlink -1 errno 2 No such file or directory 52628 co CALL open(0x7f7ed1f3,0x601,0100444) 52628 co NAMI "ls.c" 52628 co RET open 4 52628 co CALL kbind(0x7f7ec908,24,0x847da2a816b5d817) Which appears to be this: else { (void)unlink(dst); if ((fd = open(dst, O_WRONLY|O_CREAT|O_TRUNC, mode)) == -1) err(1, "%s", dst); I don't know what older or gnu rcs do. I guess whichever way this is done it must balance concerns between atomicity of concurrent reads performed by earlier processes, versus replacement of a potentially active file. If the latter is chosen, it would unlink(), perform the open more carefully, check that it is in the right place with fstat, but then it needs some work for ftruncate (to get rid of extra file contents at the end). If the open() failed, it might try an unlink followed by open()? Other rcs implimentations need to be checked. It is better if they work the same.
Re: RCS file ownership?
athom...@athompso.net wrote: > Heh, good point. Didn't even occur to me because as it happens, I am > running as root and would like to not change the ownership.-Adam > On Apr. 29, 2020 13:32, Anders Andersson wrote: > > On Wed, Apr 29, 2020 at 7:46 PM Adam Thompson > wrote: > > > > When I use co(1) with "-l" to check out a file (and/or "ci -l") is > there > > any way to preserve file ownership and *not* have it reset to the > user > > running co(1) or ci(1)? > > I don't see anything in rcs(1), co(1) or ci(1) that even mentions > the > > fact that the file will wind up owned by the user running the > command. > > Ideas? Pointers to documentation? > > How could it possibly do anything else unless you always run co as > root? Our rcs tools do: 52628 co RET kbind 0 52628 co CALL unlink(0x7f7ed1f3) 52628 co NAMI "ls.c" 52628 co RET unlink -1 errno 2 No such file or directory 52628 co CALL open(0x7f7ed1f3,0x601,0100444) 52628 co NAMI "ls.c" 52628 co RET open 4 52628 co CALL kbind(0x7f7ec908,24,0x847da2a816b5d817) Which appears to be this: else { (void)unlink(dst); if ((fd = open(dst, O_WRONLY|O_CREAT|O_TRUNC, mode)) == -1) err(1, "%s", dst); I don't know what older or gnu rcs do. I guess whichever way this is done it must balance concerns between atomicity of concurrent reads performed by earlier processes, versus replacement of a potentially active file. If the latter is chosen, it would unlink(), perform the open more carefully, check that it is in the right place with fstat, but then it needs some work for ftruncate (to get rid of extra file contents at the end). If the open() failed, it might try an unlink followed by open()? Other rcs implimentations need to be checked. It is better if they work the same.
Re: RCS file ownership?
Heh, good point. Didn't even occur to me because as it happens, I am running as root and would like to not change the ownership.-Adam On Apr. 29, 2020 13:32, Anders Andersson wrote: On Wed, Apr 29, 2020 at 7:46 PM Adam Thompson wrote: > > When I use co(1) with "-l" to check out a file (and/or "ci -l") is there > any way to preserve file ownership and *not* have it reset to the user > running co(1) or ci(1)? > I don't see anything in rcs(1), co(1) or ci(1) that even mentions the > fact that the file will wind up owned by the user running the command. > Ideas? Pointers to documentation? How could it possibly do anything else unless you always run co as root?
Re: RCS file ownership?
On Wed, Apr 29, 2020 at 7:46 PM Adam Thompson wrote: > > When I use co(1) with "-l" to check out a file (and/or "ci -l") is there > any way to preserve file ownership and *not* have it reset to the user > running co(1) or ci(1)? > I don't see anything in rcs(1), co(1) or ci(1) that even mentions the > fact that the file will wind up owned by the user running the command. > Ideas? Pointers to documentation? How could it possibly do anything else unless you always run co as root?
RCS file ownership?
When I use co(1) with "-l" to check out a file (and/or "ci -l") is there any way to preserve file ownership and *not* have it reset to the user running co(1) or ci(1)? I don't see anything in rcs(1), co(1) or ci(1) that even mentions the fact that the file will wind up owned by the user running the command. Ideas? Pointers to documentation? Thanks, -Adam