Whamcloud - gitweb
LU-5443 libcfs: replace direct HZ access with kernel APIs 93/11993/11
authorJian Yu <jian.yu@intel.com>
Tue, 18 Nov 2014 02:32:20 +0000 (18:32 -0800)
committerOleg Drokin <oleg.drokin@intel.com>
Tue, 9 Dec 2014 08:10:31 +0000 (08:10 +0000)
On some customer's systems, kernel was compiled with HZ defined to
100, instead of 1000. This improves performance for HPC applications.
However, to use these systems with Lustre, customers have to re-build
Lustre for the kernel because Lustre directly uses the defined
constant HZ.

Since kernel 2.6.21, some non-HZ dependent timing APIs become non-
inline functions, which can be used in Lustre codes to replace the
direct HZ access.

These kernel APIs include:
 jiffies_to_msecs()
 jiffies_to_usecs()
 jiffies_to_timespec()
 msecs_to_jiffies()
 usecs_to_jiffies()
 timespec_to_jiffies()

And here are some samples of the replacement:
 HZ            -> msecs_to_jiffies(MSEC_PER_SEC)
 n * HZ        -> msecs_to_jiffies(n * MSEC_PER_SEC)
 HZ / n        -> msecs_to_jiffies(MSEC_PER_SEC / n)
 n / HZ        -> jiffies_to_msecs(n) / MSEC_PER_SEC
 n / HZ * 1000 -> jiffies_to_msecs(n)

This patch replaces the direct HZ access in libcfs module.

The patch also replaces ONE_BILLION with NSEC_PER_SEC,
and ONE_MILLION with USEC_PER_SEC in linux-time.h.

Signed-off-by: Jian Yu <jian.yu@intel.com>
Change-Id: I33846f378eb876cd8958ff0c397ffb56a552f256
Reviewed-on: http://review.whamcloud.com/11993
Tested-by: Jenkins
Reviewed-by: James Simmons <uja.ornl@gmail.com>
Tested-by: Maloo <hpdd-maloo@intel.com>
Reviewed-by: Nathaniel Clark <nathaniel.l.clark@intel.com>
Reviewed-by: Oleg Drokin <oleg.drokin@intel.com>
libcfs/include/libcfs/linux/linux-time.h
libcfs/libcfs/linux/linux-crypto.c
libcfs/libcfs/linux/linux-tcpip.c

index 987dfc1..af0c6c9 100644 (file)
@@ -125,7 +125,7 @@ static inline void cfs_fs_time_nsec(cfs_fs_time_t *t, struct timespec *s)
  */
 static inline unsigned long long __cfs_fs_time_flat(cfs_fs_time_t *t)
 {
-        return (unsigned long long)t->tv_sec * ONE_BILLION + t->tv_nsec;
+       return (unsigned long long)t->tv_sec * NSEC_PER_SEC + t->tv_nsec;
 }
 
 
@@ -177,60 +177,56 @@ static inline int cfs_fs_time_beforeq(cfs_fs_time_t *t1, cfs_fs_time_t *t2)
         return __cfs_fs_time_flat(t1) <= __cfs_fs_time_flat(t2);
 }
 
-#if 0
-static inline cfs_duration_t cfs_duration_build(int64_t nano)
-{
-#if (BITS_PER_LONG == 32)
-        /* We cannot use do_div(t, ONE_BILLION), do_div can only process
-         * 64 bits n and 32 bits base */
-        int64_t  t = nano * HZ;
-        do_div(t, 1000);
-        do_div(t, 1000000);
-        return (cfs_duration_t)t;
-#else
-        return (nano * HZ / ONE_BILLION);
-#endif
-}
-#endif
-
 static inline cfs_duration_t cfs_time_seconds(int seconds)
 {
-        return ((cfs_duration_t)seconds) * HZ;
+
+       return ((cfs_duration_t)seconds) * msecs_to_jiffies(MSEC_PER_SEC);
 }
 
 static inline time_t cfs_duration_sec(cfs_duration_t d)
 {
-        return d / HZ;
+
+       return d / msecs_to_jiffies(MSEC_PER_SEC);
 }
 
 static inline void cfs_duration_usec(cfs_duration_t d, struct timeval *s)
 {
-#if (BITS_PER_LONG == 32) && (HZ > 4096)
-        __u64 t;
-
-        s->tv_sec = d / HZ;
-        t = (d - (cfs_duration_t)s->tv_sec * HZ) * ONE_MILLION;
-        do_div(t, HZ);
-        s->tv_usec = t;
+#if (BITS_PER_LONG == 32)
+       if (msecs_to_jiffies(MSEC_PER_SEC) > 4096) {
+               __u64 t;
+
+               s->tv_sec = d / msecs_to_jiffies(MSEC_PER_SEC);
+               t = (d - (cfs_duration_t)s->tv_sec *
+                    msecs_to_jiffies(MSEC_PER_SEC)) * USEC_PER_SEC;
+               do_div(t, msecs_to_jiffies(MSEC_PER_SEC));
+               s->tv_usec = t;
+       } else {
+               s->tv_sec = d / msecs_to_jiffies(MSEC_PER_SEC);
+               s->tv_usec = ((d - (cfs_duration_t)s->tv_sec *
+                              msecs_to_jiffies(MSEC_PER_SEC)) *
+                              USEC_PER_SEC) / msecs_to_jiffies(MSEC_PER_SEC);
+       }
 #else
-        s->tv_sec = d / HZ;
-        s->tv_usec = ((d - (cfs_duration_t)s->tv_sec * HZ) * \
-                ONE_MILLION) / HZ;
+       s->tv_sec = d / msecs_to_jiffies(MSEC_PER_SEC);
+       s->tv_usec = ((d - (cfs_duration_t)s->tv_sec *
+                      msecs_to_jiffies(MSEC_PER_SEC)) *
+                      USEC_PER_SEC) / msecs_to_jiffies(MSEC_PER_SEC);
 #endif
 }
 
 static inline void cfs_duration_nsec(cfs_duration_t d, struct timespec *s)
 {
 #if (BITS_PER_LONG == 32)
-        __u64 t;
+       __u64 t;
 
-        s->tv_sec = d / HZ;
-        t = (d - s->tv_sec * HZ) * ONE_BILLION;
-        do_div(t, HZ);
-        s->tv_nsec = t;
+       s->tv_sec = d / msecs_to_jiffies(MSEC_PER_SEC);
+       t = (d - s->tv_sec * msecs_to_jiffies(MSEC_PER_SEC)) * NSEC_PER_SEC;
+       do_div(t, msecs_to_jiffies(MSEC_PER_SEC));
+       s->tv_nsec = t;
 #else
-        s->tv_sec = d / HZ;
-        s->tv_nsec = ((d - s->tv_sec * HZ) * ONE_BILLION) / HZ;
+       s->tv_sec = d / msecs_to_jiffies(MSEC_PER_SEC);
+       s->tv_nsec = ((d - s->tv_sec * msecs_to_jiffies(MSEC_PER_SEC)) *
+                     NSEC_PER_SEC) / msecs_to_jiffies(MSEC_PER_SEC);
 #endif
 }
 
index c694aab..84727aa 100644 (file)
@@ -310,7 +310,8 @@ static void cfs_crypto_performance_test(enum cfs_crypto_hash_alg hash_alg)
        memset(buf, 0xAD, PAGE_SIZE);
        kunmap(page);
 
-       for (start = jiffies, end = start + HZ, bcount = 0;
+       for (start = jiffies, end = start + msecs_to_jiffies(MSEC_PER_SEC),
+            bcount = 0;
             time_before(jiffies, end) && err == 0; bcount++) {
                struct cfs_crypto_hash_desc *hdesc;
                int i;
index de1a63f..9a12e8c 100644 (file)
@@ -288,15 +288,15 @@ EXPORT_SYMBOL(libcfs_ipif_free_enumeration);
 int
 libcfs_sock_write (struct socket *sock, void *buffer, int nob, int timeout)
 {
-        int            rc;
-        mm_segment_t   oldmm = get_fs();
-        long           ticks = timeout * HZ;
-        unsigned long  then;
-        struct timeval tv;
+       int             rc;
+       mm_segment_t    oldmm = get_fs();
+       long            jiffies_left = timeout * msecs_to_jiffies(MSEC_PER_SEC);
+       unsigned long   then;
+       struct timeval  tv;
 
-        LASSERT (nob > 0);
-        /* Caller may pass a zero timeout if she thinks the socket buffer is
-         * empty enough to take the whole message immediately */
+       LASSERT(nob > 0);
+       /* Caller may pass a zero timeout if she thinks the socket buffer is
+        * empty enough to take the whole message immediately */
 
        for (;;) {
                struct kvec  iov = {
@@ -307,12 +307,16 @@ libcfs_sock_write (struct socket *sock, void *buffer, int nob, int timeout)
                        .msg_flags      = (timeout == 0) ? MSG_DONTWAIT : 0
                };
 
-                if (timeout != 0) {
-                        /* Set send timeout to remaining time */
-                        tv = (struct timeval) {
-                                .tv_sec = ticks / HZ,
-                                .tv_usec = ((ticks % HZ) * 1000000) / HZ
-                        };
+               if (timeout != 0) {
+                       /* Set send timeout to remaining time */
+                       tv = (struct timeval) {
+                               .tv_sec = jiffies_left /
+                                         msecs_to_jiffies(MSEC_PER_SEC),
+                               .tv_usec = ((jiffies_left %
+                                           msecs_to_jiffies(MSEC_PER_SEC)) *
+                                           USEC_PER_SEC) /
+                                           msecs_to_jiffies(MSEC_PER_SEC)
+                       };
                         set_fs(KERNEL_DS);
                         rc = sock_setsockopt(sock, SOL_SOCKET, SO_SNDTIMEO,
                                              (char *)&tv, sizeof(tv));
@@ -327,7 +331,7 @@ libcfs_sock_write (struct socket *sock, void *buffer, int nob, int timeout)
 
                then = jiffies;
                rc = kernel_sendmsg(sock, &msg, &iov, 1, nob);
-               ticks -= jiffies - then;
+               jiffies_left -= jiffies - then;
 
                 if (rc == nob)
                         return 0;
@@ -340,7 +344,7 @@ libcfs_sock_write (struct socket *sock, void *buffer, int nob, int timeout)
                         return (-ECONNABORTED);
                 }
 
-                if (ticks <= 0)
+               if (jiffies_left <= 0)
                         return -EAGAIN;
 
                 buffer = ((char *)buffer) + rc;
@@ -354,16 +358,16 @@ EXPORT_SYMBOL(libcfs_sock_write);
 int
 libcfs_sock_read (struct socket *sock, void *buffer, int nob, int timeout)
 {
-        int            rc;
-        mm_segment_t   oldmm = get_fs();
-        long           ticks = timeout * HZ;
-        unsigned long  then;
-        struct timeval tv;
+       int             rc;
+       mm_segment_t    oldmm = get_fs();
+       long            jiffies_left = timeout * msecs_to_jiffies(MSEC_PER_SEC);
+       unsigned long   then;
+       struct timeval  tv;
 
-        LASSERT (nob > 0);
-        LASSERT (ticks > 0);
+       LASSERT(nob > 0);
+       LASSERT(jiffies_left > 0);
 
-        for (;;) {
+       for (;;) {
                struct kvec  iov = {
                        .iov_base = buffer,
                        .iov_len  = nob
@@ -372,11 +376,14 @@ libcfs_sock_read (struct socket *sock, void *buffer, int nob, int timeout)
                        .msg_flags      = 0
                };
 
-                /* Set receive timeout to remaining time */
-                tv = (struct timeval) {
-                        .tv_sec = ticks / HZ,
-                        .tv_usec = ((ticks % HZ) * 1000000) / HZ
-                };
+               /* Set receive timeout to remaining time */
+               tv = (struct timeval) {
+                       .tv_sec = jiffies_left / msecs_to_jiffies(MSEC_PER_SEC),
+                       .tv_usec = ((jiffies_left %
+                                   msecs_to_jiffies(MSEC_PER_SEC)) *
+                                   USEC_PER_SEC) /
+                                   msecs_to_jiffies(MSEC_PER_SEC)
+               };
                 set_fs(KERNEL_DS);
                 rc = sock_setsockopt(sock, SOL_SOCKET, SO_RCVTIMEO,
                                      (char *)&tv, sizeof(tv));
@@ -389,7 +396,7 @@ libcfs_sock_read (struct socket *sock, void *buffer, int nob, int timeout)
 
                then = jiffies;
                rc = kernel_recvmsg(sock, &msg, &iov, 1, nob, 0);
-               ticks -= jiffies - then;
+               jiffies_left -= jiffies - then;
 
                 if (rc < 0)
                         return rc;
@@ -403,7 +410,7 @@ libcfs_sock_read (struct socket *sock, void *buffer, int nob, int timeout)
                 if (nob == 0)
                         return 0;
 
-                if (ticks <= 0)
+               if (jiffies_left <= 0)
                         return -ETIMEDOUT;
         }
 }