파일 지원 공유 메모리를 사용할 때 이상한 성능 동작이 발견되었습니다(예: 사용자 정의 파일을 열고 이를 프로세스 공간에 mmap()하는 것). 공유 메모리의 일부를 memcpy()할 때 밀리초 지연이 관찰되는 경우가 있습니다. 구체적으로, 일반적으로 2048바이트를 복사하는 데 0.4us가 걸리지만, 같은 수의 바이트를 복사하는 데 약 10~20밀리초가 걸리는 경우도 있습니다. 이는 언제든지 무작위로 발생할 수 있습니다. 다음 2048 프레임의 데이터는 정상 시간으로 돌아갑니다.
커널 버전은 2.6.27.23-0.1-preempt입니다.
무슨 일이 일어나고 있는지와 지연 원인에 대한 단서를 제공해 주신 모든 분들께 감사드립니다. 나는 심지어 shm_open()을 사용해 본 다음 mmap()을 사용해 보았으나 아무런 차이가 없었습니다.
호출은 mmap
다음과 같습니다.
int fd = ::open("somefile", flags, 0666);
if(fd != -1) {
myBasePointer = ::mmap(0, sizeInBytes,
PROT_READ|PROT_WRITE, MAP_SHARED,
fd, offsetInBytes);
}
한 프로세스는 파일을 생성하고 mmap
저장하고, 다른 프로세스는 파일을 열고 mmap
해당 주소 공간에 넣습니다. 파일은 일반 파일 시스템의 일반 파일입니다.
답변1
아이디어 1: 페이지가 항상 실제 RAM으로 지원되도록 mmap 호출에 MAP_LOCKED를 추가해 보세요. RAM이 많더라도 어떤 이유로든 필요한 부품이 페이지 아웃될 수 있습니다. 대기 시간에 민감한 것으로 보이므로 현재 하드웨어에서 사용 가능한 RAM 용량에 관계없이 이 플래그를 지정하는 것이 좋습니다.
아이디어 2: 페이지 테이블 항목이 오류 시간이 아닌 mmap 시간에 생성되도록 MAP_POPULATE도 지정합니다. 내가 아는 한 이것은 첫 번째 페이지 오류에서만 지연을 일으키고 후속 페이지 오류에서는 발생하지 않습니다. 그러나 그것은 또 다른 좋은 수비 훈련이었습니다.
아이디어 3: 실제 파일로 지원되는 대신 익명 공유 맵을 사용하여 파일 시스템을 제거하면 지연이 사라질까요? 도움이 된다면 항상 익명 공유 영역의 내용을 보조 스레드의 파일에 쓸 수 있습니다(아마도 낮은 빈도로).
아이디어 4: 최신 커널을 사용해 보세요. 귀하가 질문한 이후 Linux 커널이 많이 변경되었습니다.
마지막으로 memcpy 대기 시간을 어떻게 측정합니까? 귀하는 다음 사항에 해당하지 않는다고 확신하십니까?
- 현재 시간을 파악하는 데 따른 큰 지연도 포함되나요? 예를 들어 시스템 호출을 호출하는 경우 시스템 호출이 지연되거나 지연됩니다.
- NTP 수정으로 인한 클럭 점프는 포함되지 않습니다.
- 잠금 대기 시간 포함(2k의 memcpy는 원자적이지 않음)
- 정확성보다 정밀도가 더 높은 시간 측정 방법을 사용하시나요?