Does systemd-tmpfiles --clean remove open files?

Solution Verified - Updated -

Environment

  • Red Hat Enterprise Linux 7

Issue

  • Will systemd-tmpfiles-clean.service or manual execution of systemd-tmpfiles --clean remove open files?

  • In earlier versions of RHEL, when using tmpwatch to clean up files, the --fuser option could be used to ensure open files wouldn't be used. Does systemd-tmpfiles have something like this?

  • I'm planning to use tmpwatch's --fuser feature. Does systemd-tmpfiles support running fuser so that it won't delete any files which have an open file descriptor?

Resolution

  • When using systemd-tmpfiles to clean files based on age,1 each of the 3 traditional timestamps (atime, mtime, & ctime) are taken into account

  • systemd-tmpfiles does not provide a feature analogous to tmpwatch --fuser
    systemd-tmpfiles does not check to see if a file is opened by a process
    systemd-tmpfiles only looks at the file timestamps2

  • Simply put, if an application reads from a file3 or writes to a file more often than the tmpfiles.d(5) age parameter, the file will not be removed by systemd-tmpfiles --clean

  • Note also that the tmpwatch package (and thus tmpwatch --fuser) is still available in RHEL 7


  1. That is, with d, D, v, or x (see man tmpfiles.d

  2. See this [systemd-devel] tmpfiles versus tmpwatch mailing list thread, in particular, the following quote from Lennart Poettering: "Nope, we do not support this, and it's unlikely we ever will. fuser is relatively expensive, since it iterates manually through all subdirectories of /proc to find open files. If the kernel had a better interface for this, that makes this less expensive, we might consider supporting that, but the iterating through /proc is simply too bad." Another user response: "tmpwatch's fuser feature is IMHO just a countermeasure for filesystems mounted with noatime in combination with wrongly behaving software which has long living processes opening files in /tmp. That's wrong by design." 

  3. Assuming the relevant filesystem is mounted without the noatime option 

Diagnostic Steps

  • Example:

    [root]# cat /etc/tmpfiles.d/rsaw.conf
    #Type  Path    Mode  UID   GID   Age   Arg
    d      /rsaw   0770  rsaw  rsaw  10s
    [root]# ping localhost >/rsaw/openfile &
    [1] 4731
    [root]# sleep 10
    [root]# systemd-tmpfiles --clean
    [root]# ll /rsaw
    total 4
    -rw-r--r--. 1 root root 3610 Dec  4 12:53 openfile
    

    In the above, the /rsaw dir is meant to be cleaned when files have gone more than 10 seconds without being accessed -- /rsaw/openfile doesn't get deleted by systemd-tmpfiles --clean because the ping command is running in the background constantly writing

  • Continuing the above example:

    [root]# fg
    ping localhost > /rsaw/openfile
    ^C
    [root]# less /rsaw/openfile 
    
    [1]+  Stopped                 less /rsaw/openfile
    [root]# lsof +D /rsaw
    COMMAND  PID USER   FD   TYPE DEVICE SIZE/OFF    NODE NAME
    less    4770 root    4r   REG  253,3     7692 2033468 /rsaw/openfile
    [root]# sleep 10
    [root]# systemd-tmpfiles --clean
    [root]# ll /rsaw
    total 0
    

    So the ping command is killed and then less opens the output file -- after waiting 10 seconds, systemd-tmpfiles --clean deletes the file, despite it still being open by less

This solution is part of Red Hat’s fast-track publication program, providing a huge library of solutions that Red Hat engineers have created while supporting our customers. To give you the knowledge you need the instant it becomes available, these articles may be presented in a raw and unedited form.