Rdtsc
Den aktuella versionen av sidan har ännu inte granskats av erfarna bidragsgivare och kan skilja sig väsentligt från
versionen som granskades den 29 december 2019; kontroller kräver
5 redigeringar .
rdtsc ( Read Time Stamp Counter ) är en assemblerinstruktion för x86- och x86_64-plattformar som läser TSC-räknaren ( Time Stamp Counter ) och returnerar antalet 64-bitars klockcykler i EDX: EAX- registren sedan den senaste processoråterställningen .
rdtsc stöds på Pentium (och kompatibla) och nyare processorer. Opkod : 0F 31 [1] .
rdtscp [2] har stöds sedan Intel Nehalem och AMD Family 0x0F [3] . Opkod: 0F 01 F9 [4] .
Användning
rdtsc används oftast:
- att mäta tid;
- för noggrann mätning av tidsintervall, inklusive under optimering (mätning av den tid som krävs för att utföra specifika instruktioner eller deras uppsättning);
- för anti-debugging ändamål; [5] [6]
- som en entropikälla för pseudo-slumptalsgeneratorer . [7]
Fördelar
Jämfört med operativsystem -försedda API :er som WINAPI::QueryPerformanceCounter() eller gettimeofday() kan rdtsc/rdtscp-instruktioner ge följande fördelar:
- Bättre noggrannhet, särskilt för arkitekturer och äldre operativsystem som inte har fullt HPET- stöd . Sådana operativsystem använder en systemtimer med låg noggrannhet (ibland upp till en schemaläggare, OsTimeSlice, i storleksordningen enheter eller tiotals millisekunder).
- Mindre overhead: rdtsc/rdtscp-instruktioner körs i ungefär ett dussin klockcykler, vilket är mycket snabbare än systemanrop.
- Behöver inte byta till Ring0 privilegierat läge eller hypervisor på de flesta system (om kommandot är tillåtet i operativsystemet).
Användningsproblem
- Det bör finnas programlägen som inte kräver detta kommando, eftersom RDTSC / RDTSCP potentiellt kan vara otillgängliga eller förbjudna för användning på slutsystemet där applikationen kommer att användas:
- på mycket gamla processorer (till exempel 80486 ) eller på system som inte fullt ut implementerar x86-arkitekturen.
- instruktionen kan potentiellt omvandlas till en privilegierad instruktion (den 3:e biten i CR4-kontrollregistret ställs in av operativsystemet), och dess användning kommer att resultera i att ett undantag kastas i programmet.
- instruktionen kan fångas upp av virtualiseringssystem, dess användning kommer att leda till ett hypercall.
- Energisparläget kan påverka klockantalet:
- När frekvensen ändras dynamiskt av processorn (minska och öka frekvensen i SpeedStep, Turbo Boost, Cool&Quiet och liknande teknologier), ändras hastigheten på TSC-räknaren.
- Att försätta en processor i djupt viloläge C3 stoppar TSC-räknaren på äldre processorer.
- I moderna Intel-processorer ( Nehalem och nyare) och AMD (förmodligen sedan K10 Barcelona/Phenom) är TSC-räknaren oberoende av användningen av energisparteknik och ökar med en konstant frekvens, oavsett vilken frekvens processorn körs med och om den var igång eller sov. En sådan räknare kallas invariant ( invariant TSC ).
- Noggranna mätningar kanske inte är möjliga med en enda exekvering av det uppmätta fragmentet av instruktioner på grund av påverkan av processorcacheminne vid åtkomst till minne. Det löses traditionellt genom att upprepade gånger mäta ett programfragment eller genom att upprepa det uppmätta fragmentet i en loop.
- RDTSC kan beställas om med uppmätta instruktioner på Out-of-Order-processorer. Omordning kan inaktiveras genom att lägga till serialiseringskommandon (t.ex. CLD/CLC för Pentium -modellerna P5, P54 [8] eller cpuid för nyare modeller) eller genom att använda RDTSCP.
- Mätningar med kort fragmentvaraktighet kan vara instabila i system med flera kärnor och flera processorer, eller vid användning av HyperThreading på grund av ömsesidig påverkan från andra trådar och belastningen på delade processorenheter.
- TSC-räknarna kan i sällsynta fall vara osynkroniserade på vissa flerkärniga eller multiprocessorsystem, i synnerhet:
- Vid initialisering av processorer.
- Det är möjligt för räknare att bli osynkroniserade på tidiga flerkärniga system på grund av felaktig initiering av processorer av vissa BIOS. Fixat genom att uppdatera BIOS eller uppdatera operativsystemet. Det finns program för att kontrollera detta fel. [9]
- Operativsystemet kan byta tråd mellan olika kärnor som har osynkroniserade räknare. På applikationsnivå kan du spåra fakta om en kärnändring på flerkärniga system med hjälp av RDTSCP-instruktionen, som, som fungerar på samma sätt som RDTSC, dessutom returnerar numret på den logiska processorn i ECX-registret.
För att lösa många problem rekommenderas att fixa tråden på en specifik processor ( cpu-affinitet ) och inaktivera automatiska frekvensändringsteknologier (energisparande tekniker och dynamiska prestandaförändringar).
Anteckningar
- ↑ Handbok för programvaruutvecklare för Intel® 64 och IA-32 Architectures . — Vol. 2 (Instruktionsuppsättningsreferens). - S. 4-301.
- ↑ En serialiseringsversion av rdtsc-instruktionen, som också läser IA32_TSC_AUX MSR, som ofta lagrar kärnnumret.
- ↑ rdtscp . Hämtad 1 november 2011. Arkiverad från originalet 2 januari 2012. (obestämd)
- ↑ Handbok för programvaruutvecklare för Intel® 64 och IA-32 Architectures . — Vol. 2 (Instruktionsuppsättningsreferens). - S. 4-303.
- ↑ Windows Anti-Debug Referens | Symantec Connect Community . Datum för åtkomst: 30 december 2011. Arkiverad från originalet den 14 januari 2012. (obestämd)
- ↑ Bild 58 Timing Based Anti-Debugging Arkiverad 4 mars 2012.
- ↑ Tom St. Denis, Simon Johnson, Kryptografi för utvecklare Arkiverad 9 oktober 2021 på Wayback Machine .
- ↑ Hur man optimerar för Pentium-familjen av mikroprocessorer Arkiverad 6 januari 2012 på Wayback Machine // 1996-2000 av Agner Fog. Kapitel "30. Testar hastighet", arkiverad 19 november 2011.
- ↑ ICE-affinitet . Hämtad 19 oktober 2011. Arkiverad från originalet 7 september 2011. (obestämd)
Länkar