OSX:以编程方式获得正常运行时间?

时间:2010-07-16 22:39:43

标签: macos uptime

类似于linux的东西

cat /proc/uptime

以秒为单位返回正常运行时间,最好不解析正常运行时间(1)。

7 个答案:

答案 0 :(得分:14)

Uptime article on Wikipedia有一个有趣的领导:

  

使用sysctl

     

还有一种使用sysctl的方法   调用系统的最后一次启动   时间:$ sysctl kern.boottime   kern.boottime:{sec = 1271934886,   usec = 667779} 4月22日星期四12:14:46   2010

哪些引用sysctl(8),引用sysctl(3)

答案 1 :(得分:14)

老问题,我知道,但我需要做同样的事情,所以我想我会发布我正在使用的代码,这是我从http://cocoadev.com/wiki/FindingUptime获得的

#include <time.h>
#include <errno.h>
#include <sys/sysctl.h>

double uptime()
{
    struct timeval boottime;
    size_t len = sizeof(boottime);
    int mib[2] = { CTL_KERN, KERN_BOOTTIME };
    if( sysctl(mib, 2, &boottime, &len, NULL, 0) < 0 )
    {
        return -1.0;
    }
    time_t bsec = boottime.tv_sec, csec = time(NULL);

    return difftime(csec, bsec);
}

答案 2 :(得分:2)

如果有人试图使用sysctl.h以编程方式执行此操作并且期望返回类似于您在命令行中看到的字符串,则返回的值是16字节数组,而不是字符串:

sysctlbyname("kern.boottime", value, &size, NULL, 0);

从[0]索引开始以十六进制放入value的内容的示例:

a9 af c6 4e 0 0 0 0 0 0 0 0 28 be 92 55

前4个字节(可能是前8个字节,直到2012年1月才知道)是小端字节顺序的纪元时间。

答案 3 :(得分:1)

正确的方法:

CFTimeInterval getSystemUptime(void)
{
    enum { NANOSECONDS_IN_SEC = 1000 * 1000 * 1000 };
    static double multiply = 0;
    if (multiply == 0)
    {
        mach_timebase_info_data_t s_timebase_info;
        kern_return_t result = mach_timebase_info(&s_timebase_info);
        assert(result == noErr);
        // multiply to get value in the nano seconds
        multiply = (double)s_timebase_info.numer / (double)s_timebase_info.denom;
        // multiply to get value in the seconds
        multiply /= NANOSECONDS_IN_SEC;
    }
    return mach_absolute_time() * multiply;
}

你也可以使用QuartzCore.framework中的CACurrentMediaTime()(可能有相同的代码) - 自OS X v10.5和iOS 2.0起可用

答案 4 :(得分:0)

在DriverServices.h中声明了一个函数UpTime。我相信这相当于另一个函数mach_absolute_time。两者似乎都没有记录。

答案 5 :(得分:0)

不幸的是,“sysctl kern.boottime”返回时间戳的秒数,而不是秒数。多次调用不会增加第二次计数,但必须是启动日期本身epoc的秒数。

答案 6 :(得分:0)

一个简单的Lua脚本,可以完全满足您的要求:

local now=tonumber(io.popen("date +%s"):read())
local boottime=tonumber(io.popen("sysctl -n kern.boottime"):read():match("sec = (%d+)"))
local uptime=now-boottime