Overwriting shared text. Was Re: Which commands (in /bin & ...

Robert Elz kre at munnari.OZ
Sat Oct 25 19:42:57 AEST 1986


In article <1269 at ttrdc.UUCP>, levy at ttrdc.UUCP (Daniel R. Levy) writes:
> ... at least on SysV, it is not possible to overwrite, or remove the
> last link to, any executable file which is currently being run (this doesn't
> count shell scripts).   I do not know whether BSD has the same restriction.
> Could someone suggest a reason for this (other than security)...

BSD has a similar restriction, you can't overwrite a shared text executable
(I suspect that the SysV implementation is really that too - a non-shared
executable can probably be overwritten) while its being executed, though
on BSD you are allowed to unlink it.  The unlink is just like unlinking
an open file though - while the directory entry is removed, the file
(and its inode) hang around until the last execution of the process
completes.  Since there is no longer a name for the file, new executions
other than by an existing process forking are obviously impossible.

The reason is simple, and its not related to paging out of the text
space, though its similar.

For shared text executables, unix keeps a table of texts currently
in use (the "text" table).  That is indexed by device/inode pairs.
When you exec a shared process, the kernel looks in this table to
see if the process is already being executed, and if it is, just
gives you a copy of the text that's already in code, rather than
reading a new copy from the filesystem.  That's what "shared text"
is all about.  The initial data space is still read from the file.

Now, if you were to change the file while a copy was running, when
you did the next exec, strange things would happen.  Most likely,
the new process would end up with the old text (that was being run
when the file was changed) and the new data sapce.  Unless you're
lucky, this isn't going to work well.

There are ways that this could be fixed - when the file is written,
the kernel could mark the text table so that the next exec would
read a new text from the filesystem.  However, this doesn't seem
important enough to bother with really, just prohibiting writes
seems good enough.  Probiting unlink is too extreme though I think,
allowing the unlink, but simply not releasing the inode is a
sufficient precaution.

Robert Elz		seismo!munnari!kre	kre at munnari.oz.au



More information about the Comp.unix.wizards mailing list