操作简单浪费时间?

发布于 2024-11-29 23:49:17 字数 195 浏览 2 评论 0 原文

我正在寻找一个简单的操作/例程,如果连续重复,它会“浪费”时间。

我正在研究 gprof 如何配置应用程序,因此这种“时间浪费者”需要在用户空间中浪费时间,并且不需要外部库。 IE 中,调用 sleep(20) 会“浪费”20 秒的时间,但是 gprof 不会记录这个时间,因为它发生在另一个库中。

对于可以重复浪费时间的简单任务有什么建议吗?

I'm looking for a simple operation / routine which can "waste" time if repeated continuously.

I'm researching how gprof profiles applications, so this "time waster" needs to waste time in the user space and should not require external libraries. IE, calling sleep(20) will "waste" 20 seconds of time, but gprof will not record this time because it occurred within another library.

Any recommendations for simple tasks which can be repeated to waste time?

如果你对这篇内容有疑问,欢迎到本站社区发帖提问 参与讨论,获取更多帮助,或者扫码二维码加入 Web 技术交流群。

扫码二维码加入Web技术交流群

发布评论

需要 登录 才能够评论, 你可以免费 注册 一个本站的账号。

评论(4

物价感观 2024-12-06 23:49:17

Another variant on Tomalak's solution is to set up an alarm, and so in your busy-wait loop, you don't need to keep issuing a system call, but instead just check if the signal has been sent.

苹果你个爱泡泡 2024-12-06 23:49:17

“浪费”时间而不释放 CPU 的最简单方法是紧密循环。

如果您不需要限制浪费的持续时间(例如,您可以通过在完成时简单地终止进程来控制它),那么请使用 C 风格*:(

for (;;) {}

但请注意,标准允许实现假设程序最终会终止,因此从技术上讲,这个循环(至少在 C++0x 中)具有未定义的行为,可以进行优化!**

否则,您可以手动计时:

time_t s = time(0);
while (time(0) - s < 20) {}

或者,而不是重复发出time 系统调用(这将导致在内核中花费一些时间),如果在 GNU 兼容系统上,您可以使用 signal.h "alarms" 结束循环:

alarm(20);
while (true) {}

文档页面上甚至还有一个非常相似的示例对于“处理程序返回”

(当然,这些方法都会让您在干预时间内 CPU 使用率达到 100%,并使毛茸茸的独角兽从您的耳朵里掉下来。)


* {} 而不是尾随 ;使用故意的,为了清楚起见。最终,没有理由在这样的上下文中编写分号;这是一个可怕的习惯,当您在“真实”代码中使用它时,它会成为维护陷阱。

** 请参阅 [n3290: 1.10/2][n3290:1.10/24]

The simplest way to "waste" time without yielding CPU is a tight loop.

If you don't need to restrict the duration of your waste (say, you control it by simply terminating the process when done), then go C style*:

for (;;) {}

(Be aware, though, that the standard allows the implementation to assume that programs will eventually terminate, so technically speaking this loop — at least in C++0x — has Undefined Behaviour and could be optimised out!**

Otherwise, you could time it manually:

time_t s = time(0);
while (time(0) - s < 20) {}

Or, instead of repeatedly issuing the time syscall (which will lead to some time spent in the kernel), if on a GNU-compatible system you could make use of signal.h "alarms" to end the loop:

alarm(20);
while (true) {}

There's even a very similar example on the documentation page for "Handler Returns".

(Of course, these approaches will all send you to 100% CPU for the intervening time and make fluffy unicorns fall out of your ears.)


* {} rather than trailing ; used deliberately, for clarity. Ultimately, there's no excuse for writing a semicolon in a context like this; it's a terrible habit to get into, and becomes a maintenance pitfall when you use it in "real" code.

** See [n3290: 1.10/2] and [n3290: 1.10/24].

清旖 2024-12-06 23:49:17

一个简单的循环就可以了。
如果您正在研究 gprof 的工作原理,我假设您已经慢慢地、仔细地阅读了这篇论文< /a>.
我还假设您熟悉
这些问题

A simple loop would do.
If you're researching how gprof works, I assume you've read the paper, slowly and carefully.
I also assume you're familiar with these issues.

错爱 2024-12-06 23:49:17

这是一个繁忙的循环,在现代硬件上每次迭代运行一个周期,至少 >clanggcc 或可能任何具有至少一些优化标志的合理编译器:

void busy_loop(uint64_t iters) {
    volatile int sink;
    do {
        sink = 0;
    } while (--iters > 0);
    (void)sink;
}

这个想法只是存储到易失性 水槽每次迭代。这可以防止循环被优化,并使每次迭代都有可预测的工作量(至少一个存储)。现代硬件每个周期可以执行一次存储,并且循环开销通常可以在同一周期中并行完成,因此通常每次迭代实现一个周期。因此,您可以通过除以 CPU 速度(以 GHz 为单位)来估算给定数量的迭代所需的挂钟时间(以纳秒为单位)。例如,当 iters == 6,000,000,000 时,3 GHz CPU 需要大约 2 秒(20 亿纳秒)才能进入 busy_loop

Here's a busy loop which runs at one cycle per iteration on modern hardware, at least as compiled by clang or gcc or probably any reasonable compiler with at least some optimization flag:

void busy_loop(uint64_t iters) {
    volatile int sink;
    do {
        sink = 0;
    } while (--iters > 0);
    (void)sink;
}

The idea is just to store to the volatile sink every iteration. This prevents the loop from being optimized away, and makes each iteration have a predictable amount of work (at least one store). Modern hardware can do one store per cycle, and the loop overhead generally can complete in parallel in that same cycle, so usually achieves one cycle per iteration. So you can ballpark the wall-clock time in nanoseconds a given number of iters will take by dividing by your CPU speed in GHz. For example, a 3 GHz CPU will take about 2 seconds (2 billion nanos) to busy_loop when iters == 6,000,000,000.

~没有更多了~
我们使用 Cookies 和其他技术来定制您的体验包括您的登录状态等。通过阅读我们的 隐私政策 了解更多相关信息。 单击 接受 或继续使用网站,即表示您同意使用 Cookies 和您的相关数据。
原文