일정한 간격으로 이벤트를 발생시키는 대기 루프의 성능을 평가 중입니다. 나는 다음과 같은 코드를 사용하여 몇 가지 이상한 행동을 발견했습니다 :바쁜 대기 루프의 가변 성능?
테스트 시스템 (듀얼 14 코어 E5-2683 V3의 @의 2.00Ghz, 256기가바이트 DDR4), 루프의 20 만 반복에#include <stdio.h>
#include <stdlib.h>
#include <unistd.h>
#include <time.h>
int timespec_subtract(struct timespec *, struct timespec, struct timespec);
int main(int argc, char *argv[]) {
int iterations = atoi(argv[1])+1;
struct timespec t[2], diff;
for (int i = 0; i < iterations; i++) {
clock_gettime(CLOCK_MONOTONIC, &t[0]);
static volatile int i;
for (i = 0; i < 200000; i++)
;
clock_gettime(CLOCK_MONOTONIC, &t[1]);
timespec_subtract(&diff, t[1], t[0]);
printf("%ld\n", diff.tv_sec * 1000000000 + diff.tv_nsec);
}
}
약이 1ms이다. 아니면하지 : 시간은 세 번째를 아래로 이동하면
1030854
1060237
1012797
1011479
1025307
1017299
1011001
1038725
1017361
... (about 700 lines later)
638466
638546
638446
640422
638468
638457
638468
638398
638493
640242
... (about 200 lines later)
606460
607013
606449
608813
606542
606484
606990
606436
606491
606466
... (about 3000 lines later)
404367
404307
404309
404306
404270
404370
404280
404395
404342
406005
, 그들은 때때로 수백 반복 약 450us까지 점프를 제외하고 (약 2 또는 3 마이크로 초 이내) 대부분 일관성을 유지. 이 동작은 유사한 시스템과 많은 실행에서 반복 가능합니다.
저는 바쁜 루프가 컴파일러에 의해 최적화 될 수 있다는 것을 알고 있습니다 만, 저는 그것이 그 문제라고 생각하지 않습니다. 무효화가 일어나지 않아야하고 갑자기 최적화를 설명하지 않기 때문에 캐시가 영향을 미쳐야한다고 생각하지 않습니다. 나는 또한 눈에 띄는 효과가없는 루프 카운터에 대해 레지스터 int를 사용하여 시도했다.
무슨 일이 일어나고 있는지, 그리고 어떻게하면 더 일관성있게 만드나요?
편집 : usleep, nanosleep 또는 10k 반복에 대한 대기 중 대기로이 프로그램을 실행하는 경우 모두 time -v
으로 ~ 20000 개의 비 독자적 컨텍스트 스위치가 표시됩니다.
점프 아마 컨텍스트 스위치입니다 전화 usleep/절전 지연에서 공제 할 수있는 시간 간격을 계산하는 gettimeofday를 사용할 수 있습니다. – Mysticial
죄송합니다. 귀하의 접근 방식은 완전히 잘못되었습니다. 그런 식으로 모든 PC 시스템에서 신뢰할 수있는 타이밍을 얻을 수는 없습니다. 확실히 XY 문제입니다. ** 실제로 ** 수행하고 싶은 내용과 모든 관련 세부 사항을 기재하십시오. – Olaf
내가 실제로하고 싶은 것은 질문 제목에 언급 한 바쁜 루프의 성능이 왜 바뀌는지를 이해하는 것입니다. 내 프로그램 타이밍을 정하는 대체 방법을 알고 있습니다. – Rakurai