A bit of Unix history on 'su -'

July 17, 2023

These days, modern versions of su interpret 'su -' as 'su -l' (via). Although they have different implementations of su, this is true on Linux, FreeBSD, and OpenBSD. However, it turns out that this feature wasn't always in Unix's su.

The V7 su(1) is quite minimal, and has no equivalent of '-' or '-l'. In fact, V7 su takes no options at all; it treats its first argument as the username to su to and ignores all other arguments to just run the shell (passing it the nominal program name of 'su', cf). Su became rather more complex in System III, where it gained both 'su -' and the ability to use additional arguments, which were passed to /bin/sh as command line arguments (su also got other changes, such as logging). Based on reading the System III code for su.c, I believe that you could use both 'su -' and 'su login args' together, with the meaning that 'su - login args' would reset $HOME, chdir to the target login's home directory, setuid to them, and then run '/bin/sh args'. Unfortunately I can't find System III manual pages, so I can't see what it documented for su usage.

Su in 4.2 BSD has a more complicated story. The 4.2 BSD su(1) manual page claims the same minimal usage as V7 su. However, the 4.2 BSD su.c code shows that it actually had a much more elaborate usage; su supported both '-' and '-f', as well as command line arguments for the invoked shell. The '-f' option passed '-f' as the first argument to the shell; according to the 4.2 BSD csh(1) manual page, this caused it to skip reading .cshrc. Unlike the System III su, the 4.2 BSD su always used the target login's shell, even when passing arguments to it (this matters when the target has a restricted shell). As with System III, you could combine '-' and additional arguments, 'su - login arg ...'. In 4.3 BSD, the su(1) manual page actually documents all of this. The BSD su didn't change again until 1990's 4.3 BSD Reno where it added a Kerberos focus and '-l' and '-m' options, based on the su(1) manual page we have.

Based on the NetBSD su(1) manual page, the NetBSD su may be the closest to this ancestral *BSD version of su, since NetBSD has retained the -K argument related to Kerberos.

I suspect that the various Linux implementations of su (which have come from at least the shadow package and util-linux) have had a '-l' option for a long time, but I lack the energy to trace the various packages back through history. The Linux su(s) have had additional options for a long time, although in some sense 2006 is probably 'recent' as far as Linux su features are concerned.

Written on 17 July 2023.
« Social media posts aren't as small and simple as you might think
Non-uniform CPU hyperthreading is here and can cause fun issues »

Page tools: View Source, Add Comment.
Login: Password:
Atom Syndication: Recent Comments.

Last modified: Mon Jul 17 22:44:30 2023
This dinky wiki is brought to you by the Insane Hackers Guild, Python sub-branch.