racy updates of /etc/mtab

Rob Landley rob at landley.net
Fri Sep 15 15:40:02 UTC 2006


On Friday 15 September 2006 2:24 am, Denis Vlasenko wrote:
> On Thursday 14 September 2006 20:24, Rob Landley wrote:
> > On Thursday 14 September 2006 12:32 pm, Denis Vlasenko wrote:
> > > I think we should not modify /etc/mtab in place, as we do today,
> > > but create /etc/mtab.new, write new contents into it and
> > > then rename it. With exception: if /etc/mtab is a symlink,
> > > we probably shouldn't touch it (it is most likely link to /proc).
> > > 
> > > This approach will be race-free. Do you agree with such a plan?
> > 
> > Why will it be race-free?  If two updates happen at the same time, both 
read 
> > the old file to create their new files, both rename their new files back 
to 
> > the old name.  The second rename deletes the first, so an update gets 
> > dropped.
> 
> We will create /etc/mtab.new with O_CREAT | O_EXCL:
> 
> O_EXCL When  used  with  O_CREAT,  if  the file already exists it is an
>        error and the open() will fail. In this context, a symbolic link
>        exists,  regardless  of where it points to.
> 
> If it fails, then we maybe have concurrent (u)mount. Loop a few times
> trying to create it, then complain and overwrite it (stale file).
> 
> IOW: /etc/mtab.new will serve as a lock file too.

I don't think the extra size and complexity is worth it.

> > I'm trusting addmntent() and such to handle these details for us.  If the 
> > library isn't doing the appropriate locking for legacy mtab support, fix 
the 
> > library.
> 
> I'm afraid libc people will pass it back to us on the grounds that
> setmntent() has a filename parameter for a reason.

Perhaps so.

Isn't there a file locking ioctl we could use here?

Rummages...  From login.c:
    if (fcntl(fileno(fp), F_SETLK, &lock) < 0) {

> This is the second pass, writing back all entries except unmounted one.

So it's a bit like del_line_matching() in loginutils/deluser.c?

That's at least a single atomic transaction (operating on the theory that the 
whole passwd file fits easily in memory), although mmap isn't that bad of an 
alternative either.

I think the lock fcntl is probably the easy way to deal with it.  (I'm not 
remotely concerned about /etc/mtab getting out of sync with reality, I 
actually expect it.  I just don't want it to get corrupted, and don't want to 
make the code bigger.)

Rob
-- 
Never bet against the cheap plastic solution.



More information about the busybox mailing list