Добро пожаловать в форум, Guest  >>   Войти | Регистрация | Поиск | Правила | В избранное | Подписаться
Все форумы / Delphi Новый топик    Ответить
 Узнать частоту ядра процессора  [new]
Ежов Дмитрий Сергеевич
Member

Откуда: Новокузнецк-Москва, Россия
Сообщений: 128
Я использую RdTSC вида

type
  TTicks64 = type Int64; // signed, so that deltas can be represented cleanly

  /// ////////////////////////////////////////////////////////////////////////////////////////////////
  // CPUID implements a full barrier; it doesn't influence the timing as it is called before RDTSC.
  // Full story: ia-32-ia-64-benchmark-code-execution-paper.pdf

function RdTSC0: TTicks64; // the 'before' tick
asm
  {$IFDEF CPUX64}
  xor   rax, rax
  push  rbx          // Delphi requires EBX/RBX to be preserved
  cpuid              // full fence
  pop   rbx
  rdtsc
  shl   rdx, 32
  or    rax, rdx
  {$ELSE}
  xor   eax, eax
  push  ebx
  cpuid
  pop   ebx
  rdtsc
  {$ENDIF}
end;

// --------------------------------------------------------------------------------------------------
// RDTSCP implements a sort of read fence: it waits until all preceding instructions in the stream
// have been executed but it doesn't keep later instruction from jumping the queue. That's why the
// RDTSCP is bracketed by CPUID from behind.

function RdTSC1: TTicks64; // the 'after' tick
asm
  {$IFDEF CPUX64}
  {$IFDEF ZX_dont_use_RDTSCP}
  rdtsc
  {$ELSE}
  rdtscp
  {$ENDIF}
  shl   rdx, 32
  or    rdx, rax
  xor   rax, rax
  push  rbx
  push  rdx
  cpuid
  pop   rax
  pop   rbx
  {$ELSE}
  {$IFDEF ZX_dont_use_RDTSCP}
  rdtsc
  {$ELSE}
  db    $0F, $01, $F9  // rdtscp; X2 understands the mnemonic for x64 but not for x86
  {$ENDIF}
  push  eax
  xor   eax, eax
  push  edx
  push  ebx
  cpuid
  pop   ebx
  pop   edx
  pop   eax
  {$ENDIF}
end;

// -------------------------------------------------------------------------------------------------
// for flank-to-flank measurements

function rdtscp: TTicks64;
asm
  {$IFDEF CPUX64}
  {$IFDEF ZX_dont_use_RDTSCP}
  rdtsc
  {$ELSE}
  rdtscp
  {$ENDIF}
  shl   rdx, 32
  or    rax, rdx
  {$ELSE}
  {$IFDEF ZX_dont_use_RDTSCP}
  rdtsc
  {$ELSE}
  db    $0F, $01, $F9  // rdtscp; X2 understands the mnemonic for x64 but not for x86
  {$ENDIF}
  {$ENDIF}
end;


и его вызовы вот так

procedure TForm1.Button1Click(Sender: TObject);
var
CounterStart: Int64;
CounterStop: Int64;
begin
CounterStart := rdtsc0;

sleep(1000);
CounterStop := rdtsc0;

ShowMessage(inttostr(round((CounterStop - CounterStart) / 1000 / 1000)));

end;

и получаю четко свою БАЗОВУЮ частоту ядра процессора: 3600 МГц для i5-8600k, хотя у меня высокая производительность и ядра работают на 4.2 ГГц.

Думал, может ядро засыпает. Нагружал все ядра проца CPU-Z в StressBenchmark, но все равно 3600 МГц.

Что я упускаю?
22 ноя 21, 16:12    [22399171]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
mayton
Member

Откуда: loopback
Сообщений: 52984
Тебе нужно узнать паспортные данные на железо? Или посмотреть мгновенное значение
которое показывает TaskManager Windows?
22 ноя 21, 17:01    [22399209]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
Ежов Дмитрий Сергеевич
Member

Откуда: Новокузнецк-Москва, Россия
Сообщений: 128
посмотреть мгновенное значение task manager
22 ноя 21, 17:30    [22399237]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
makhaon
Member

Откуда: A galaxy far far away
Сообщений: 3954
может тебе wmi будет удобнее чем ассемблер?
22 ноя 21, 18:14    [22399288]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
Ежов Дмитрий Сергеевич
Member

Откуда: Новокузнецк-Москва, Россия
Сообщений: 128
makhaon,

wmi - это зависимость от служб Windows. Вроде есть такая служба, при отключении которой, WMI запросы не работают. Не хотелось бы.
22 ноя 21, 18:33    [22399299]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
Dimitry Sibiryakov
Member

Откуда:
Сообщений: 54790

Вторая ссылка гугля:
https://stackoverflow.com/questions/7544049/win32-api-function-to-get-processors-current-speed

Posted via ActualForum NNTP Server 1.5

22 ноя 21, 18:44    [22399301]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
Ежов Дмитрий Сергеевич
Member

Откуда: Новокузнецк-Москва, Россия
Сообщений: 128
Dimitry Sibiryakov,
more the same (тех же щей)

function CallNtPowerInformation(InformationLevel: Byte; lpInputBuffer: Pointer; nInputBufferSize: Longint; lpOutputBuffer: Pointer; nOutputBufferSize: Longint): Byte; stdcall; external 'PowrProf.dll';
type
  TPINFO = record
    Number: UINT;
    MaxMh: UINT;
    CurrentMhz: UINT;
    MhzLimit: UINT;
    MaxIdleState: UINT;
    CurrentIdleState: UINT;
  end;

  Function DummyThread(Param:pointer):Cardinal;stdcall;
  var x:integer; y:real;
  begin
    x:=0;
    while true do begin
    y:=cos(x);
    inc(x);
    if x>100000 then x:=0;
    end;
  end;

procedure TForm1.Button1Click(Sender: TObject);
var
  SI:_SYSTEM_INFO;
  NumberOfProcessors:Cardinal;
  PINFO: Array of TPINFO;
  res: Byte;
  resBool:Boolean;
  PID:Cardinal;
  ProcessAffinityMask: Cardinal;
  hProcess,hThread:THandle;
begin
  hProcess:=GetCurrentProcess();
  ProcessAffinityMask:=0;
  ProcessAffinityMask:=ProcessAffinityMask or (1 shl 1);
  resBool:=SetProcessAffinityMask(hProcess,ProcessAffinityMask);
  if resBool=false then begin
    ShowMessage(_GetErrorMsg(GetLastError));
    exit;
  end;
  GetSystemInfo(SI);
  NumberOfProcessors:=SI.dwNumberOfProcessors;
  hThread:=CreateThread(nil,0,@DummyThread,nil,0,PID);
  sleep(3000);
  SetLength(PINFO, NumberOfProcessors);
  ZeroMemory(@PINFO[0], sizeOf(TPINFO) * NumberOfProcessors);
  res := CallNtPowerInformation(11, nil, 0, @PINFO[0], sizeOf(TPINFO) * NumberOfProcessors);
  ShowMessage('CurrentMhz:'+inttostr(PINFO[0].CurrentMhz)+'//MaxMh:'+inttostr(PINFO[0].MaxMh));
  TerminateThread(hThread,0);
end;
22 ноя 21, 20:29    [22399378]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
Ежов Дмитрий Сергеевич
Member

Откуда: Новокузнецк-Москва, Россия
Сообщений: 128
Ежов Дмитрий Сергеевич,

Вешаю приложение на 2 ядро, запускаю на нем нагружающий поток, меряю частоту, получаю базовую.

https://prnt.sc/20j1axs

Можно погрешить на кривую настройку компа, схемы питания, но ровно туже картину получаю на настроенном промышленном сервере.

https://prnt.sc/20j1kbd
22 ноя 21, 20:33    [22399383]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
Ежов Дмитрий Сергеевич
Member

Откуда: Новокузнецк-Москва, Россия
Сообщений: 128
Dimitry Sibiryakov,

QueryPerformanceFrequency()
вообще возвращает 10 Мгц.
22 ноя 21, 20:38    [22399392]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
_Vasilisk_
Member

Откуда: Украина, Харьков
Сообщений: 13358
Ежов Дмитрий Сергеевич
function CallNtPowerInformation(InformationLevel: Byte; lpInputBuffer: Pointer; nInputBufferSize: Longint;
  lpOutputBuffer: Pointer; nOutputBufferSize: Longint): Byte; stdcall; external 'PowrProf.dll';
  ........
  res := CallNtPowerInformation(11, nil, 0, @PINFO[0], sizeOf(TPINFO) * NumberOfProcessors);
  ShowMessage('CurrentMhz:'+inttostr(PINFO[0].CurrentMhz)+'//MaxMh:'+inttostr(PINFO[0].MaxMh));
end;
1. Выделенное заменить на Cardinal
2. Возвращаемое значение нужно анализировать
3. Нужно выводить информацию по всем процессорам
4. На основании чего делается вывод, что функция возвращает некорректное значение?
22 ноя 21, 20:41    [22399394]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
_Vasilisk_
Member

Откуда: Украина, Харьков
Сообщений: 13358
Ежов Дмитрий Сергеевич
QueryPerformanceFrequency() вообще возвращает 10 Мгц.
А GetTickCount случайное число. Только какое эти функции имеют отношение к частоте процессора?
22 ноя 21, 20:44    [22399398]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
Dimitry Sibiryakov
Member

Откуда:
Сообщений: 54790

Ежов Дмитрий Сергеевич
more the same

Остальные ядра тоже посмотри. Может, нулевое реально не в бусте.

Posted via ActualForum NNTP Server 1.5

22 ноя 21, 23:09    [22399470]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
Ежов Дмитрий Сергеевич
Member

Откуда: Новокузнецк-Москва, Россия
Сообщений: 128
Dimitry Sibiryakov,

все ядра на базовой частоте.
23 ноя 21, 11:24    [22399570]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
Ежов Дмитрий Сергеевич
Member

Откуда: Новокузнецк-Москва, Россия
Сообщений: 128
Если кому интересно, нашел вот такой проект
https://github.com/anrieff/libcpuid

пришлось поставить C#, полюбиться с развертыванием и понять.
Они ставят sys драйвер в режиме Ring0 как службу венды. Этот драйвер (автор Нориюки Миядзаки, разраб CrystalDiskInfo) позволяет читать служебные регистры проца, они в своем проекте их читают с разными фишечками для ранних интелов и AMD.

Пожалуй, тему отложим...
23 ноя 21, 19:30    [22399898]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
makhaon
Member

Откуда: A galaxy far far away
Сообщений: 3954
Ежов Дмитрий Сергеевич,

я ж сразу говорил WMI, но видно не очень нужно
23 ноя 21, 22:26    [22399975]     Ответить | Цитировать Сообщить модератору
 Re: Узнать частоту ядра процессора  [new]
Ежов Дмитрий Сергеевич
Member

Откуда: Новокузнецк-Москва, Россия
Сообщений: 128
makhaon,

да не, просто дождаться выходных, там победим.
24 ноя 21, 13:51    [22400179]     Ответить | Цитировать Сообщить модератору
Все форумы / Delphi Ответить