在 windows 每 100 微秒生成一次中断

Generating interrupt each 100 microsecond on windows

我想在 windows 上每 100 微秒生成一次中断。实际上我无法在 windows 上执行此操作,因为 windows 不能保证中断少于 500 微秒。所以,我生成了 2 个线程。其中一个用于定时器计数器(查询性能计数器),另一个线程是实际工作。当计时器计数器为 100 微秒时,它会更改另一个线程(实际工作)的状态。但是我有竞争条件的问题,因为我不希望线程互相等待,它们必须总是 运行。所以实际上我需要中断。我如何使用 C++ 在 windows 上编写如此快速的中断?

为了避免在这么短的时间内让两个线程进行通信 windows,我将工作和计时器都放在一个线程的循环中。

  • 在线程启动时对时钟进行采样,并在每个循环中增加 100μs。
  • 睡眠到计算的时间。通常情况下,人们会使用 std::this_thread::sleep_until 来做这样的睡眠,但在这种情况下,当小睡时间如此短时,它往往变得有点太不准确了,所以我建议在一个紧密的循环中忙等待,只检查时间.
  • 做你的工作。

在此示例中,工作线程运行了 10 秒,但没有做任何实际工作。在我的机器上,我可以在整个循环开始花费超过 100 微秒的时间之前,在您应该完成工作的插槽中添加由 ~3000 个添加组成的工作,因此您最好快速完成您的目标。

示例:

#include <atomic>
#include <chrono>
#include <iostream>
#include <thread>

using namespace std::chrono_literals;

static std::atomic<bool> running = true;

using myclock = std::chrono::steady_clock;

void worker() {
    int loops = 0;
    auto sleeper = myclock::now();
    while(running) {
        ++loops; // count loops to check that it's good enough afterwards

        // add 100us to the sleeper time_point
        sleeper += 100us;

        // busy-wait until it's time to do some work
        while(myclock::now() < sleeper);

        // do your work here
    }
    std::cout << loops << " (should be ~100000)\n";
}

int main() {
    auto th = std::thread(worker);

    // let the thread work for 10 seconds
    std::this_thread::sleep_for(10s);

    running = false;
    th.join();
}

可能的输出:

99996 (should be ~100000)

启动线程需要几个时钟周期,因此不必担心循环数未完全达到目标。将线程运行时间加倍,您仍应保持接近目标循环数。重要的是一旦启动 漂亮 好(但不是 实时-好)运行.