harrison@utfyzx.uucp (David Harrison) (10/31/88)
Recently Geoff Collyer (utstat!geoff) has pointed out that under System V the command: ln old new will destroy "new" if it already exists. Historically and under other UNIX versions the same command will complain and refuse to make the link. Geoff calls the System V behaviour "an unintuitive shock". It certainly breaks any program that relies on `ln' refusing to link to "new" as a way of doing locks (including parts of Cnews). There certainly are lock problems under SV: the print spooler will croak if it is fed a large number of jobs nearly simultaneously; a number of users changing their passwords nearly simultaneously can leave you without an /etc/passwd file; etc. Both of these have happened to me and the fix I use is to write a SV IPC onionskin around these commands with semaphores to implement real kernel-level locks. I have some questions and one comment on this situation. First the questions: if one re-writes ln (as Geoff has done) to reproduce the old behaviour and replaces the SV `ln' in /bin with this version what will break? People have been using the old `ln' behaviour for some years, but are people now relying on the new behaviour too? If so, how? Will implementing such a change make passwd and lp more reliable with lots of users? What does POSIX say? Finally the comment: if one adheres to traditional UNIX philosophy the System V `ln' is correct. It now behaves just like its cousins `cp' and `mv': tell it to do something and it will. If one wishes to test for the existence of file "new" this philosophy says that one should use a tool for that, not some behaviour of a program that is supposed to make links. I know one problem with the above statement; code like: if [ !exists new ] # new command `exists' then ln old new fi leaves a terrible window of vulnerability between the test and the link. What is needed is a proper lock mechanism, and System V provides it with its IPC facilities in the kernel where they belong. -- David Harrison, Dept. of Physics, Univ. of Toronto | "Why do 3 notes make a UUCP: {utgpu,sq,oscvax}!utfyzx!harrison | triad and not a triangle?" BITNET: HARRISON@UTORPHYS | - Ernst Mach
les@chinet.chi.il.us (Leslie Mikesell) (11/02/88)
In article <1988Oct31.141701.11055@utfyzx.uucp> harrison@utfyzx.UUCP (David Harrison) writes: >Recently Geoff Collyer (utstat!geoff) has pointed out that under System >V the command: > ln old new >will destroy "new" if it already exists. Historically and under other Many sysV's have /etc/link which just passes its arguments to the system call. In some versions it is executable only by root, but that is easy to fix. Personally, I think that ln should have had a -f flag to delete an existing file with the same names as the destination (but I also think that sysV is severely crippled by not having an atomic rename). >There certainly are lock problems under SV: the print spooler will >croak if it is fed a large number of jobs nearly simultaneously; a Can someone explain this one? Does it involve the FIFO or creating the spooled work file? Does uucp have the same problem? Les Mikesell
geoff@desint.UUCP (Geoff Kuenning) (11/02/88)
In article <1988Oct31.141701.11055@utfyzx.uucp> harrison@utfyzx.UUCP (David Harrison) writes: > Recently Geoff Collyer (utstat!geoff) has pointed out that under System > V the command: > ln old new > will destroy "new" if it already exists. Historically and under other > UNIX versions the same command will complain and refuse to make the link. > Geoff calls the System V behaviour "an unintuitive shock". It certainly > breaks any program that relies on `ln' refusing to link to "new" as a way > of doing locks (including parts of Cnews). ... > code like: > if [ !exists new ] # new command `exists' > then > ln old new > fi > leaves a terrible window of vulnerability between the test and the > link. After seeing this, I checked on my system, since several of my important scripts use 'ln' to implement locks. However, I found that all of these scripts use the following sequence to make the lock: trap "" 1 2 15 touch lock ln lock lock1 || exit 1 trap "rm -f lock lock1; exit 1" 1 2 15 This *will* work, because ln will fail complaining the "lock" and "lock1" are identical. On the other hand, if your scripts use the following sequence, they will fail to lock on System V: touch lock.$$ ln lock.$$ lock || exit 1 -- Geoff Kuenning geoff@ITcorp.com uunet!desint!geoff
rta@pixar.UUCP (Rick Ace) (11/02/88)
In article <1988Oct31.141701.11055@utfyzx.uucp>, harrison@utfyzx.uucp (David Harrison) writes: > Recently Geoff Collyer (utstat!geoff) has pointed out that under System > V the command: > ln old new > will destroy "new" if it already exists. Historically and under other > UNIX versions the same command will complain and refuse to make the link. > Geoff calls the System V behaviour "an unintuitive shock". It certainly > breaks any program that relies on `ln' refusing to link to "new" as a way > of doing locks (including parts of Cnews). > ... > I have some questions and one comment on this situation. > > First the questions: if one re-writes ln (as Geoff has done) to > reproduce the old behaviour and replaces the SV `ln' in /bin > with this version what will break? Don't do this. Other pieces of the vendor's software likely depend (or will come to depend in future releases) upon the new behavior of ln. If you install your own ln, you waive the right to go back to the vendor and complain when you have problems; if they ask you if you're running the software the way it came "out of the box," you cannot all honesty answer "yes." As an anecdote, consider this: at NYIT, we were running 4.1bsd on our Vax systems. Along came 4.2bsd with its new signal(3) semantics. The change in semantics broke several of our programs, so I charged ahead and "fixed" signal in the C library to work the way it did under 4.1bsd. That cured one problem, but others surfaced when I recompiled some Berkeley programs that had expected to get the new signal. After a bit of head-scratching, the solution I chose was to restore the 4.2bsd semantics to signal, implement a new library routine called v7signal(), and change our software to use v7signal(). If you want something that works like Seventh Edition ln, code it up and install it under another name, like v7ln. Rick Ace Pixar 3240 Kerner Blvd, San Rafael CA 94901 ...!{sun,ucbvax}!pixar!rta
jfh@rpp386.Dallas.TX.US (John F. Haugh II) (11/04/88)
In article <2630@pixar.UUCP> rta@pixar.UUCP (Rick Ace) writes: >If you want something that works like Seventh Edition ln, code it up >and install it under another name, like v7ln. Or, create a directory /v7bin and put all of the working v7 binaries you write in there. And put that directory before /bin in your PATH -- John F. Haugh II +----Make believe quote of the week---- VoiceNet: (214) 250-3311 Data: -6272 | Nancy Reagan on Richard Stallman: InterNet: jfh@rpp386.Dallas.TX.US | "Just say `Gno'" UucpNet : <backbone>!killer!rpp386!jfh +--------------------------------------
geoff@utstat.uucp (Geoff Collyer) (11/06/88)
I see a race in Geoff Kuenning's inventive solution to locking with ln(1) on System V: > trap "" 1 2 15 > touch lock > ln lock lock1 || exit 1 > trap "rm -f lock lock1; exit 1" 1 2 15 If the "rm -f lock lock1" runs in one copy of this script just after the "touch lock" runs in another, then the ln will fail unnecessarily. The race can be fixed by simply not removing "lock", since "lock1" is the real lock. -- Geoff Collyer utzoo!utstat!geoff, geoff@utstat.toronto.edu