Error reformatting, and use the suspend-aware monotonic clock on Linux.

This commit is contained in:
Adam Ierymenko 2021-04-13 18:57:44 -04:00
parent 37d706b635
commit ad92a46b8d
No known key found for this signature in database
GPG key ID: C8877CF2D7A5D7F3
8 changed files with 73 additions and 77 deletions

View file

@ -19,10 +19,11 @@
namespace ZeroTier { namespace ZeroTier {
/** /**
* A per-API-call equivalent to the runtime * A per-API-call equivalent to the general context.
* *
* This captures several things that are passed into API calls and follow * This is created when external C API calls are made and follows the call
* the call chain. Some such as tPtr may be supplied to callbacks. * graph around from function to function as needed. It's cleaner and probably
* faster than passing clock, ticks, and tPtr around everywhere.
*/ */
class CallContext class CallContext
{ {

View file

@ -18,8 +18,10 @@
#include <sys/stat.h> #include <sys/stat.h>
#ifndef __WINDOWS__ #ifndef __WINDOWS__
#include <dirent.h> #include <dirent.h>
#include <fcntl.h> #include <fcntl.h>
#endif #endif
#include <algorithm> #include <algorithm>
@ -32,31 +34,35 @@
namespace ZeroTier { namespace ZeroTier {
#ifdef __APPLE__ #ifdef __APPLE__
static clock_serv_t _machGetRealtimeClock() noexcept static clock_serv_t _machGetRealtimeClock() noexcept
{ {
clock_serv_t c; clock_serv_t c;
host_get_clock_service(mach_host_self(),CALENDAR_CLOCK,&c); host_get_clock_service(mach_host_self(), CALENDAR_CLOCK, &c);
return c; return c;
} }
static clock_serv_t _machGetMonotonicClock() noexcept static clock_serv_t _machGetMonotonicClock() noexcept
{ {
clock_serv_t c; clock_serv_t c;
host_get_clock_service(mach_host_self(),REALTIME_CLOCK,&c); host_get_clock_service(mach_host_self(), SYSTEM_CLOCK, &c);
return c; return c;
} }
clock_serv_t OSUtils::s_machRealtimeClock = _machGetRealtimeClock(); clock_serv_t OSUtils::s_machRealtimeClock = _machGetRealtimeClock();
clock_serv_t OSUtils::s_machMonotonicClock = _machGetMonotonicClock(); clock_serv_t OSUtils::s_machMonotonicClock = _machGetMonotonicClock();
#endif #endif
unsigned int OSUtils::ztsnprintf(char *buf,unsigned int len,const char *fmt,...) unsigned int OSUtils::ztsnprintf(char *buf, unsigned int len, const char *fmt, ...)
{ {
va_list ap; va_list ap;
va_start(ap,fmt); va_start(ap, fmt);
int n = (int)vsnprintf(buf,len,fmt,ap); int n = (int)vsnprintf(buf, len, fmt, ap);
va_end(ap); va_end(ap);
if ((n >= (int)len)||(n < 0)) { if ((n >= (int)len) || (n < 0)) {
if (len) if (len)
buf[len - 1] = (char)0; buf[len - 1] = (char)0;
throw std::length_error("buf[] overflow"); throw std::length_error("buf[] overflow");
@ -66,13 +72,14 @@ unsigned int OSUtils::ztsnprintf(char *buf,unsigned int len,const char *fmt,...)
} }
#ifdef __UNIX_LIKE__ #ifdef __UNIX_LIKE__
bool OSUtils::redirectUnixOutputs(const char *stdoutPath,const char *stderrPath)
bool OSUtils::redirectUnixOutputs(const char *stdoutPath, const char *stderrPath)
{ {
int fdout = open(stdoutPath,O_WRONLY|O_CREAT,0600); int fdout = open(stdoutPath, O_WRONLY | O_CREAT, 0600);
if (fdout > 0) { if (fdout > 0) {
int fderr; int fderr;
if (stderrPath) { if (stderrPath) {
fderr = open(stderrPath,O_WRONLY|O_CREAT,0600); fderr = open(stderrPath, O_WRONLY | O_CREAT, 0600);
if (fderr <= 0) { if (fderr <= 0) {
::close(fdout); ::close(fdout);
return false; return false;
@ -80,17 +87,18 @@ bool OSUtils::redirectUnixOutputs(const char *stdoutPath,const char *stderrPath)
} else fderr = fdout; } else fderr = fdout;
::close(STDOUT_FILENO); ::close(STDOUT_FILENO);
::close(STDERR_FILENO); ::close(STDERR_FILENO);
::dup2(fdout,STDOUT_FILENO); ::dup2(fdout, STDOUT_FILENO);
::dup2(fderr,STDERR_FILENO); ::dup2(fderr, STDERR_FILENO);
return true; return true;
} }
return false; return false;
} }
#endif // __UNIX_LIKE__ #endif // __UNIX_LIKE__
Vector<String> OSUtils::listDirectory(const char *path,bool includeDirectories) Vector< String > OSUtils::listDirectory(const char *path, bool includeDirectories)
{ {
Vector<String> r; Vector< String > r;
#ifdef __WINDOWS__ #ifdef __WINDOWS__
HANDLE hFind; HANDLE hFind;
@ -109,11 +117,11 @@ Vector<String> OSUtils::listDirectory(const char *path,bool includeDirectories)
if (!d) if (!d)
return r; return r;
dptr = (struct dirent *)0; dptr = (struct dirent *)0;
for(;;) { for (;;) {
if (readdir_r(d,&de,&dptr)) if (readdir_r(d, &de, &dptr))
break; break;
if (dptr) { if (dptr) {
if ((strcmp(dptr->d_name,".") != 0)&&(strcmp(dptr->d_name,"..") != 0)&&((dptr->d_type != DT_DIR)||(includeDirectories))) if ((strcmp(dptr->d_name, ".") != 0) && (strcmp(dptr->d_name, "..") != 0) && ((dptr->d_type != DT_DIR) || (includeDirectories)))
r.push_back(String(dptr->d_name)); r.push_back(String(dptr->d_name));
} else break; } else break;
} }
@ -150,12 +158,12 @@ bool OSUtils::rmDashRf(const char *path)
if (!d) if (!d)
return true; return true;
dptr = (struct dirent *)0; dptr = (struct dirent *)0;
for(;;) { for (;;) {
if (readdir_r(d,&de,&dptr) != 0) if (readdir_r(d, &de, &dptr) != 0)
break; break;
if (!dptr) if (!dptr)
break; break;
if ((strcmp(dptr->d_name,".") != 0)&&(strcmp(dptr->d_name,"..") != 0)&&(strlen(dptr->d_name) > 0)) { if ((strcmp(dptr->d_name, ".") != 0) && (strcmp(dptr->d_name, "..") != 0) && (strlen(dptr->d_name) > 0)) {
String p(path); String p(path);
p.push_back(ZT_PATH_SEPARATOR); p.push_back(ZT_PATH_SEPARATOR);
p.append(dptr->d_name); p.append(dptr->d_name);
@ -170,10 +178,10 @@ bool OSUtils::rmDashRf(const char *path)
#endif #endif
} }
void OSUtils::lockDownFile(const char *path,bool isDir) void OSUtils::lockDownFile(const char *path, bool isDir)
{ {
#ifdef __UNIX_LIKE__ #ifdef __UNIX_LIKE__
chmod(path,isDir ? 0700 : 0600); chmod(path, isDir ? 0700 : 0600);
#else #else
#ifdef __WINDOWS__ #ifdef __WINDOWS__
{ {
@ -202,25 +210,25 @@ void OSUtils::lockDownFile(const char *path,bool isDir)
#endif #endif
} }
bool OSUtils::fileExists(const char *path,bool followLinks) bool OSUtils::fileExists(const char *path, bool followLinks)
{ {
struct stat s; struct stat s;
#ifdef __UNIX_LIKE__ #ifdef __UNIX_LIKE__
if (!followLinks) if (!followLinks)
return (lstat(path,&s) == 0); return (lstat(path, &s) == 0);
#endif #endif
return (stat(path,&s) == 0); return (stat(path, &s) == 0);
} }
bool OSUtils::readFile(const char *path,String &buf) bool OSUtils::readFile(const char *path, String &buf)
{ {
char tmp[16384]; char tmp[16384];
FILE *f = fopen(path,"rb"); FILE *f = fopen(path, "rb");
if (f) { if (f) {
for(;;) { for (;;) {
long n = (long)fread(tmp,1,sizeof(tmp),f); long n = (long)fread(tmp, 1, sizeof(tmp), f);
if (n > 0) if (n > 0)
buf.append(tmp,n); buf.append(tmp, n);
else break; else break;
} }
fclose(f); fclose(f);
@ -229,11 +237,11 @@ bool OSUtils::readFile(const char *path,String &buf)
return false; return false;
} }
bool OSUtils::writeFile(const char *path,const void *buf,unsigned int len) bool OSUtils::writeFile(const char *path, const void *buf, unsigned int len)
{ {
FILE *f = fopen(path,"wb"); FILE *f = fopen(path, "wb");
if (f) { if (f) {
if ((long)fwrite(buf,1,len,f) != (long)len) { if ((long)fwrite(buf, 1, len, f) != (long)len) {
fclose(f); fclose(f);
return false; return false;
} else { } else {
@ -244,9 +252,9 @@ bool OSUtils::writeFile(const char *path,const void *buf,unsigned int len)
return false; return false;
} }
Vector<String> OSUtils::split(const char *s,const char *const sep,const char *esc,const char *quot) Vector< String > OSUtils::split(const char *s, const char *const sep, const char *esc, const char *quot)
{ {
Vector<String> fields; Vector< String > fields;
String buf; String buf;
if (!esc) if (!esc)
@ -268,11 +276,11 @@ Vector<String> OSUtils::split(const char *s,const char *const sep,const char *es
} else buf.push_back(*s); } else buf.push_back(*s);
} else { } else {
const char *quotTmp; const char *quotTmp;
if (strchr(esc,*s)) if (strchr(esc, *s))
escapeState = true; escapeState = true;
else if ((buf.size() <= 0)&&((quotTmp = strchr(quot,*s)))) else if ((buf.size() <= 0) && ((quotTmp = strchr(quot, *s))))
quoteState = *quotTmp; quoteState = *quotTmp;
else if (strchr(sep,*s)) { else if (strchr(sep, *s)) {
if (buf.size() > 0) { if (buf.size() > 0) {
fields.push_back(buf); fields.push_back(buf);
buf.clear(); buf.clear();
@ -316,7 +324,7 @@ ZeroTier::String OSUtils::platformDefaultHomePath()
if (bufferSize) if (bufferSize)
return userDefinedPath; return userDefinedPath;
#else #else
if(const char* userDefinedPath = getenv("ZEROTIER_HOME")) if (const char *userDefinedPath = getenv("ZEROTIER_HOME"))
return String(userDefinedPath); return String(userDefinedPath);
#endif #endif

View file

@ -196,11 +196,7 @@ public:
#else #else
#ifdef __LINUX__ #ifdef __LINUX__
timespec ts; timespec ts;
#ifdef CLOCK_MONOTONIC_COARSE clock_gettime(CLOCK_BOOTTIME,&ts);
clock_gettime(CLOCK_MONOTONIC_COARSE,&ts);
#else
clock_gettime(CLOCK_MONOTONIC,&ts);
#endif
return ( (1000LL * (int64_t)ts.tv_sec) + ((int64_t)(ts.tv_nsec / 1000000)) ); return ( (1000LL * (int64_t)ts.tv_sec) + ((int64_t)(ts.tv_nsec / 1000000)) );
#else #else
#ifdef __APPLE__ #ifdef __APPLE__

View file

@ -807,6 +807,6 @@ mod tests {
let cert_signed_decoded = cert_signed_decoded.ok().unwrap(); let cert_signed_decoded = cert_signed_decoded.ok().unwrap();
assert!(cert_signed_decoded.signature.len() > 0); assert!(cert_signed_decoded.signature.len() > 0);
assert!(cert_signed_decoded.verify() == CertificateError::None); assert!(cert_signed_decoded.verify(-1) == CertificateError::None);
} }
} }

View file

@ -274,7 +274,7 @@ fn delete<'a>(store: &Arc<Store>, cli_args: &ArgMatches<'a>) -> i32 {
0 0
} }
pub(crate) fn run<'a>(store: Arc<Store>, cli_args: &ArgMatches<'a>) -> i32 { pub(crate) fn run(store: Arc<Store>, cli_args: &ArgMatches) -> i32 {
match cli_args.subcommand() { match cli_args.subcommand() {
("list", None) => list(&store), ("list", None) => list(&store),
("show", Some(sub_cli_args)) => show(&store, sub_cli_args), ("show", Some(sub_cli_args)) => show(&store, sub_cli_args),

View file

@ -35,17 +35,9 @@ use crate::osdep as osdep;
#[cfg(unix)] #[cfg(unix)]
fn bind_udp_socket(_device_name: &str, address: &InetAddress) -> Result<FastUDPRawOsSocket, &'static str> { fn bind_udp_socket(_device_name: &str, address: &InetAddress) -> Result<FastUDPRawOsSocket, &'static str> {
unsafe { unsafe {
let af; let (af, sa_len) = match address.family() {
let sa_len; InetAddressFamily::IPv4 => (osdep::AF_INET, std::mem::size_of::<osdep::sockaddr_in>() as osdep::socklen_t),
match address.family() { InetAddressFamily::IPv6 => (osdep::AF_INET6, std::mem::size_of::<osdep::sockaddr_in6>() as osdep::socklen_t),
InetAddressFamily::IPv4 => {
af = osdep::AF_INET;
sa_len = std::mem::size_of::<osdep::sockaddr_in>() as osdep::socklen_t;
}
InetAddressFamily::IPv6 => {
af = osdep::AF_INET6;
sa_len = std::mem::size_of::<osdep::sockaddr_in6>() as osdep::socklen_t;
}
_ => { _ => {
return Err("unrecognized address family"); return Err("unrecognized address family");
} }

View file

@ -18,7 +18,6 @@ use zerotier_core::InetAddress;
use crate::osdep as osdep; use crate::osdep as osdep;
#[inline(always)]
fn s6_addr_as_ptr<A>(a: &A) -> *const A { fn s6_addr_as_ptr<A>(a: &A) -> *const A {
a as *const A a as *const A
} }

View file

@ -47,9 +47,9 @@ impl Error for UnexpectedStatusCodeError {}
impl std::fmt::Display for UnexpectedStatusCodeError { impl std::fmt::Display for UnexpectedStatusCodeError {
fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result { fn fmt(&self, f: &mut std::fmt::Formatter) -> std::fmt::Result {
if self.1.is_empty() { if self.1.is_empty() {
write!(f, "unexpected status code: {} {}", self.0.as_str(), self.0.canonical_reason().unwrap_or("???")) write!(f, "{} {} (???)", self.0.as_str(), self.0.canonical_reason().unwrap_or("???"))
} else { } else {
write!(f, "unexpected status code: {} {} ({})", self.0.as_str(), self.0.canonical_reason().unwrap_or("???"), self.1) write!(f, "{} {} ({})", self.0.as_str(), self.0.canonical_reason().unwrap_or("???"), self.1)
} }
} }
} }