# man > time_namespaces(7)

[_time_namespaces_(7)](https://www.chedong.com/phpMan.php/man/timenamespaces/7/markdown)                Miscellaneous Information Manual                [_time_namespaces_(7)](https://www.chedong.com/phpMan.php/man/timenamespaces/7/markdown)

## NAME
       time_namespaces - overview of Linux time namespaces

## DESCRIPTION
       Time namespaces virtualize the values of two system clocks:

       •  **CLOCK_MONOTONIC  **(and  likewise **CLOCK_MONOTONIC_COARSE **and **CLOCK_MONOTONIC_RAW**), a nonset‐
          table clock that represents monotonic time  since—as described  by  POSIX—"some   unspeci‐
          fied  point in the past".

       •  **CLOCK_BOOTTIME  **(and likewise **CLOCK_BOOTTIME_ALARM**), a nonsettable clock that is identical
          to **CLOCK_MONOTONIC**, except that it also includes any time that the system is suspended.

       Thus, the processes in a time namespace share per-namespace values for  these  clocks.   This
       affects  various  APIs  that  measure  against  these  clocks,  including:  [**clock_gettime**(2)](https://www.chedong.com/phpMan.php/man/clockgettime/2/markdown),
       [**clock_nanosleep**(2)](https://www.chedong.com/phpMan.php/man/clocknanosleep/2/markdown), [**nanosleep**(2)](https://www.chedong.com/phpMan.php/man/nanosleep/2/markdown), [**timer_settime**(2)](https://www.chedong.com/phpMan.php/man/timersettime/2/markdown), [**timerfd_settime**(2)](https://www.chedong.com/phpMan.php/man/timerfdsettime/2/markdown), and _/proc/uptime_.

       Currently, the only way to create  a  time  namespace  is  by  calling  [**unshare**(2)](https://www.chedong.com/phpMan.php/man/unshare/2/markdown)  with  the
       **CLONE_NEWTIME  **flag.   This  call creates a new time namespace but does _not_ place the calling
       process in the new namespace.  Instead, the calling process's subsequently  created  children
       are placed in the new namespace.  This allows clock offsets (see below) for the new namespace
       to    be    set   before   the   first   process   is   placed   in   the   namespace.    The
       _/proc/_pid_/ns/time_for_children_ symbolic link shows the time namespace in which  the  children
       of  a  process will be created.  (A process can use a file descriptor opened on this symbolic
       link in a call to [**setns**(2)](https://www.chedong.com/phpMan.php/man/setns/2/markdown) in order to move into the namespace.)

   _**/proc/_pid[4m/timens_offsets**
       Associated with each time namespace are offsets, expressed with respect to the  initial  time
       namespace,  that  define  the values of the monotonic and boot-time clocks in that namespace.
       These offsets are exposed via the file _/proc/_pid_/timens_offsets_.  Within this file, the  off‐
       sets are expressed as lines consisting of three space-delimited fields:

           <clock-id> <offset-secs> <offset-nanosecs>

       The _clock-id_ is a string that identifies the clock whose offsets are being shown.  This field
       is  either  _monotonic_,  for  **CLOCK_MONOTONIC**, or _boottime_, for **CLOCK_BOOTTIME**.  The remaining
       fields express the offset (seconds plus nanoseconds) for the clock in  this  time  namespace.
       These  offsets are expressed relative to the clock values in the initial time namespace.  The
       _offset-secs_ value can be negative, subject to restrictions noted below; _offset-nanosecs_ is an
       unsigned value.

       In the initial time namespace, the contents of the _timens_offsets_ file are as follows:

           $ **cat /proc/self/timens_offsets**
           monotonic           0         0
           boottime            0         0

       In a new time namespace that has had no member processes, the clock offsets can  be  modified
       by  writing newline-terminated records of the same form to the _timens_offsets_ file.  The file
       can be written to multiple times, but after the first process has been created in or has  en‐
       tered the namespace, [**write**(2)](https://www.chedong.com/phpMan.php/man/write/2/markdown)s on this file fail with the error **EACCES**.  In order to write to
       the  _timens_offsets_  file,  a process must have the **CAP_SYS_TIME **capability in the user name‐
       space that owns the time namespace.

       Writes to the _timens_offsets_ file can fail with the following errors:

       **EINVAL **An _offset-nanosecs_ value is greater than 999,999,999.

       **EINVAL **A _clock-id_ value is not valid.

       **EPERM  **The caller does not have the **CAP_SYS_TIME **capability.

       **ERANGE **An _offset-secs_ value is out of range.  In particular;

              •  _offset-secs_ can't be set to a value which would make the current time on the corre‐
                 sponding clock inside the namespace a negative value; and

              •  _offset-secs_ can't be set to a value such that the time on the  corresponding  clock
                 inside  the  namespace  would  exceed  half  of  the  value  of the kernel constant
                 **KTIME_SEC_MAX **(this limits the clock  value  to  a  maximum  of  approximately  146
                 years).

       In  a  new  time namespace created by [**unshare**(2)](https://www.chedong.com/phpMan.php/man/unshare/2/markdown), the contents of the _timens_offsets_ file are
       inherited from the time namespace of the creating process.

## NOTES
       Use of time namespaces requires a kernel that is configured with the **CONFIG_TIME_NS **option.

       Note that time namespaces do not virtualize the **CLOCK_REALTIME **clock.  Virtualization of this
       clock was avoided for reasons of complexity and overhead within the kernel.

       For  compatibility  with  the  initial  implementation,  when  writing  a  _clock-id_  to   the
       _/proc/_pid_/timens_offsets_  file, the numerical values of the IDs can be written instead of the
       symbolic names show above; i.e., 1 instead of _monotonic_, and  7  instead  of  _boottime_.   For
       readability, the use of the symbolic names over the numbers is preferred.

       The  motivation for adding time namespaces was to allow the monotonic and boot-time clocks to
       maintain consistent values during container migration and checkpoint/restore.

## EXAMPLES
       The following shell session demonstrates the operation of time namespaces.  We begin by  dis‐
       playing the inode number of the time namespace of a shell in the initial time namespace:

           $ **readlink /proc/$$/ns/time**
           time:[4026531834]

       Continuing  in  the  initial time namespace, we display the system uptime using [**uptime**(1)](https://www.chedong.com/phpMan.php/man/uptime/1/markdown) and
       use the _clock_times_ example program shown in [**clock_getres**(2)](https://www.chedong.com/phpMan.php/man/clockgetres/2/markdown) to display the values of various
       clocks:

           $ **uptime --pretty**
           up 21 hours, 17 minutes
           $ **./clock_times**
           CLOCK_REALTIME : 1585989401.971 (18356 days +  8h 36m 41s)
           CLOCK_TAI      : 1585989438.972 (18356 days +  8h 37m 18s)
           CLOCK_MONOTONIC:      56338.247 (15h 38m 58s)
           CLOCK_BOOTTIME :      76633.544 (21h 17m 13s)

       We then use [**unshare**(1)](https://www.chedong.com/phpMan.php/man/unshare/1/markdown) to create a time namespace and execute a [**bash**(1)](https://www.chedong.com/phpMan.php/man/bash/1/markdown) shell.  From the  new
       shell, we use the built-in **echo **command to write records to the _timens_offsets_ file adjusting
       the offset for the **CLOCK_MONOTONIC **clock forward 2 days and the offset for the **CLOCK_BOOTTIME**
       clock forward 7 days:

           $ **PS1="ns2# " sudo unshare -T -- bash --norc**
           ns2# **echo "monotonic $((2*24*60*60)) 0" > /proc/$$/timens_offsets**
           ns2# **echo "boottime  $((7*24*60*60)) 0" > /proc/$$/timens_offsets**

       Above,  we  started the [**bash**(1)](https://www.chedong.com/phpMan.php/man/bash/1/markdown) shell with the **--norc **option so that no start-up scripts were
       executed.  This ensures that no child processes are created from the shell before we  have  a
       chance to update the _timens_offsets_ file.

       We  then  use  [**cat**(1)](https://www.chedong.com/phpMan.php/man/cat/1/markdown)  to  display the contents of the _timens_offsets_ file.  The execution of
       [**cat**(1)](https://www.chedong.com/phpMan.php/man/cat/1/markdown) creates the first process in the new time namespace, after which further  attempts  to
       update the _timens_offsets_ file produce an error.

           ns2# **cat /proc/$$/timens_offsets**
           monotonic      172800         0
           boottime       604800         0
           ns2# **echo "boottime $((9*24*60*60)) 0" > /proc/$$/timens_offsets**
           bash: echo: write error: Permission denied

       Continuing in the new namespace, we execute [**uptime**(1)](https://www.chedong.com/phpMan.php/man/uptime/1/markdown) and the _clock_times_ example program:

           ns2# **uptime --pretty**
           up 1 week, 21 hours, 18 minutes
           ns2# **./clock_times**
           CLOCK_REALTIME : 1585989457.056 (18356 days +  8h 37m 37s)
           CLOCK_TAI      : 1585989494.057 (18356 days +  8h 38m 14s)
           CLOCK_MONOTONIC:     229193.332 (2 days + 15h 39m 53s)
           CLOCK_BOOTTIME :     681488.629 (7 days + 21h 18m  8s)

       From the above output, we can see that the monotonic and boot-time clocks have different val‐
       ues in the new time namespace.

       Examining  the  _/proc/_pid_/ns/time_  and  _/proc/_pid_/ns/time_for_children_ symbolic links, we see
       that the shell is a member of the initial time namespace, but its children are created in the
       new namespace.

           ns2# **readlink /proc/$$/ns/time**
           time:[4026531834]
           ns2# **readlink /proc/$$/ns/time_for_children**
           time:[4026532900]
           ns2# **readlink /proc/self/ns/time   **# Creates a child process
           time:[4026532900]

       Returning to the shell in the initial time namespace, we see that the monotonic and boot-time
       clocks are unaffected by the _timens_offsets_ changes that were made in the  other  time  name‐
       space:

           $ **uptime --pretty**
           up 21 hours, 19 minutes
           $ **./clock_times**
           CLOCK_REALTIME : 1585989401.971 (18356 days +  8h 38m 51s)
           CLOCK_TAI      : 1585989438.972 (18356 days +  8h 39m 28s)
           CLOCK_MONOTONIC:      56338.247 (15h 41m  8s)
           CLOCK_BOOTTIME :      76633.544 (21h 19m 23s)

## SEE ALSO
       [**nsenter**(1)](https://www.chedong.com/phpMan.php/man/nsenter/1/markdown), [**unshare**(1)](https://www.chedong.com/phpMan.php/man/unshare/1/markdown), [**clock_settime**(2)](https://www.chedong.com/phpMan.php/man/clocksettime/2/markdown), [**setns**(2)](https://www.chedong.com/phpMan.php/man/setns/2/markdown), [**unshare**(2)](https://www.chedong.com/phpMan.php/man/unshare/2/markdown), [**namespaces**(7)](https://www.chedong.com/phpMan.php/man/namespaces/7/markdown), [**time**(7)](https://www.chedong.com/phpMan.php/man/time/7/markdown)

Linux man-pages 6.7                          2023-10-31                           [_time_namespaces_(7)](https://www.chedong.com/phpMan.php/man/timenamespaces/7/markdown)
