]> arthur.barton.de Git - netdata.git/blobdiff - src/common.c
handle usleep() on systems that do not accept more than 999999 usec; implement altern...
[netdata.git] / src / common.c
index 699f58c64d025938456eb35553795dcb6711db32..02d37ab675ccd8a8c7dba1a12e8f0bcfb9efeed2 100644 (file)
@@ -10,7 +10,7 @@
 #include <sys/stat.h>
 #include <fcntl.h>
 #include <sys/mman.h>
-
+#include <time.h>
 
 #include "log.h"
 #include "common.h"
@@ -27,6 +27,51 @@ unsigned long long timems(void) {
        return now.tv_sec * 1000000ULL + now.tv_usec;
 }
 
+int usecsleep(unsigned long long usec) {
+
+#ifdef NETDATA_WITH_NANOSLEEP
+       // we expect microseconds (1.000.000 per second)
+       // but timespec is nanoseconds (1.000.000.000 per second)
+       struct timespec req = { .tv_sec = usec / 1000000, .tv_nsec = (usec % 1000000) * 1000 }, rem;
+
+       while(nanosleep(&req, &rem) == -1) {
+               error("nanosleep() failed for %llu microseconds.", usec);
+
+               if(likely(errno == EINTR)) {
+                       req.tv_sec = rem.tv_sec;
+                       req.tv_nsec = rem.tv_nsec;
+               }
+               else {
+                       error("Cannot nanosleep() for %llu microseconds.", usec);
+                       break;
+               }
+       }
+
+       return 0;
+#else
+       int ret = usleep(usec);
+       if(unlikely(ret == -1 && errno == EINVAL)) {
+               // on certain systems, usec has to be up to 999999
+               if(usec > 999999) {
+                       int counter = usec / 999999;
+                       while(counter--)
+                               usleep(999999);
+
+                       usleep(usec % 999999);
+               }
+               else {
+                       error("Cannot usleep() for %llu microseconds.", usec);
+                       return ret;
+               }
+       }
+
+       if(ret != 0)
+               error("usleep() failed for %llu microseconds.", usec);
+
+       return ret;
+#endif
+}
+
 unsigned char netdata_map_chart_names[256] = {
                [0] = '\0', //
                [1] = '_', //