多任务处理和测量时差
Multitasking and measuring time difference
我知道抢占式多任务 OS 可以在任何时候中断进程 "code position"。
给定以下代码:
int main() {
while( true ) {
doSthImportant(); // needs to be executed at least each 20 msec
// start of critical section
int start_usec = getTime_usec();
doSthElse();
int timeDiff_usec = getTime_usec() - start_usec;
// end of critical section
evalUsedTime( timeDiff_usec );
sleep_msec( 10 );
}
}
我希望此代码通常会为 timeDiff_usec 产生正确的结果,尤其是在 doSthElse() 和getTime_usec() 不会花费太多时间,因此它们很少被 OS 调度程序打断。
但是程序会不时在 "critical section" 的某处中断。上下文切换将执行它应该执行的操作,但在这种情况下,程序仍会为 timeDiff_usec.
产生错误的结果
这是我现在想到的唯一示例,但我敢肯定还有其他情况,多任务处理可能会使程序(mer)陷入困境(因为时间不是唯一可能会更改的状态重新进入)。
- 有没有办法确保测量某个动作的时间正常工作?
- 还有哪些其他常见问题对多任务处理至关重要且需要考虑? (我没有考虑线程安全 - 但可能存在常见问题)。
编辑:
我更改了示例代码以使其更精确。
我想检查所花费的时间,以确保 doSthElse() 不会花费 50 毫秒左右,如果需要,我会寻找更好的解决方案。
- Is there a way to ensure that measuring the time for a certain action works fine?
这取决于您的操作系统和权限级别。在某些系统上,对于某些特权级别,您可以将进程或线程设置为具有优先级,以防止它被任何低优先级的东西抢占。例如,在 Linux 上,您可以使用 sched_setscheduler
来赋予线程实时优先级。 (如果你真的很认真,你还可以设置线程亲和力和 SMP 亲和力,以防止在 CPU 即 运行 你的线程上处理任何中断。)
您的系统还可以提供时间跟踪,以计算抢占时间。例如,POSIX 定义了 getrusage
函数,其中 returns 一个结构包含 ru_utime
(进程在“用户模式”中花费的时间)和 ru_stime
(进程在“内核模式”中花费的时间)。这些总和应该等于 CPU 花在该过程上的总时间,不包括该过程暂停的时间间隔。请注意,如果内核需要,例如,代表您的进程花费时间进行分页,则没有定义该时间中有多少(如果有的话)被您的进程收取。
无论如何,衡量花在一些关键行动上的时间的常用方法是在一个原本空闲的系统上重复计时(基本上是你的问题呈现的方式),扔掉离群值的测量值,然后取平均值(在消除之后离群值),或取测量值的中位数或第 95 个百分位数,具体取决于您需要测量的原因。
Which other common issues are critical with multitasking and need to be considered? (I'm not thinking of thread safety - but there might be common issues).
范围太广。有很多关于这个主题的书。
我知道抢占式多任务 OS 可以在任何时候中断进程 "code position"。
给定以下代码:
int main() {
while( true ) {
doSthImportant(); // needs to be executed at least each 20 msec
// start of critical section
int start_usec = getTime_usec();
doSthElse();
int timeDiff_usec = getTime_usec() - start_usec;
// end of critical section
evalUsedTime( timeDiff_usec );
sleep_msec( 10 );
}
}
我希望此代码通常会为 timeDiff_usec 产生正确的结果,尤其是在 doSthElse() 和getTime_usec() 不会花费太多时间,因此它们很少被 OS 调度程序打断。
但是程序会不时在 "critical section" 的某处中断。上下文切换将执行它应该执行的操作,但在这种情况下,程序仍会为 timeDiff_usec.
产生错误的结果这是我现在想到的唯一示例,但我敢肯定还有其他情况,多任务处理可能会使程序(mer)陷入困境(因为时间不是唯一可能会更改的状态重新进入)。
- 有没有办法确保测量某个动作的时间正常工作?
- 还有哪些其他常见问题对多任务处理至关重要且需要考虑? (我没有考虑线程安全 - 但可能存在常见问题)。
编辑: 我更改了示例代码以使其更精确。 我想检查所花费的时间,以确保 doSthElse() 不会花费 50 毫秒左右,如果需要,我会寻找更好的解决方案。
- Is there a way to ensure that measuring the time for a certain action works fine?
这取决于您的操作系统和权限级别。在某些系统上,对于某些特权级别,您可以将进程或线程设置为具有优先级,以防止它被任何低优先级的东西抢占。例如,在 Linux 上,您可以使用 sched_setscheduler
来赋予线程实时优先级。 (如果你真的很认真,你还可以设置线程亲和力和 SMP 亲和力,以防止在 CPU 即 运行 你的线程上处理任何中断。)
您的系统还可以提供时间跟踪,以计算抢占时间。例如,POSIX 定义了 getrusage
函数,其中 returns 一个结构包含 ru_utime
(进程在“用户模式”中花费的时间)和 ru_stime
(进程在“内核模式”中花费的时间)。这些总和应该等于 CPU 花在该过程上的总时间,不包括该过程暂停的时间间隔。请注意,如果内核需要,例如,代表您的进程花费时间进行分页,则没有定义该时间中有多少(如果有的话)被您的进程收取。
无论如何,衡量花在一些关键行动上的时间的常用方法是在一个原本空闲的系统上重复计时(基本上是你的问题呈现的方式),扔掉离群值的测量值,然后取平均值(在消除之后离群值),或取测量值的中位数或第 95 个百分位数,具体取决于您需要测量的原因。
Which other common issues are critical with multitasking and need to be considered? (I'm not thinking of thread safety - but there might be common issues).
范围太广。有很多关于这个主题的书。