Карта сайта Kansoftware
НОВОСТИУСЛУГИРЕШЕНИЯКОНТАКТЫ
KANSoftWare

Параллельное программирование в Delphi: решение проблемы с маской аффинности и многопоточностью

Delphi , Компоненты и Классы , Потоки

Параллельное программирование в Delphi: решение проблемы с маской аффинности и многопоточностью

Параллельное программирование в среде Delphi может быть довольно сложной задачей, особенно когда речь заходит о распределении потоков по ядрам процессора. В данном случае мы сталкиваемся с проблемой, когда при попытке запустить несколько потоков на разных ядрах, возникает ошибка ERROR_INVALID_PARAMETER (ошибка 87) в результате неверного определения маски аффинности.

Проблема и контекст

Рассмотрим код, который пытается создать несколько потоков для выполнения задачи параллельно, используя различные ядра процессора:

function SingleProcessorMask(const ProcessorIndex: Integer): DWORD_PTR;
begin
  Result:= 1; Result:= Result shl ProcessorIndex;
end;

procedure TForm2.BtnCreateLookup5x5to3x3UsingSpeculativeExplorationClick(Sender: TObject);
var
  ThreadCount: Integer;
  Threads: TArray<TThread>;
  CurrentProcessor: Integer;
  i, a: Integer;
  Done: Boolean;
begin
  ThreadCount := System.CpuCount;
  SetLength(Threads, ThreadCount);
  CurrentProcessor := GetCurrentProcessorNumber;
  a := 0;
  for i := 1 to ThreadCount - 1 do
  begin
    Threads[i] := TThread.CreateAnonymousThread(
      procedure
      begin
        CreateLookupUsingGridSolver(i, ThreadCount);
      end
    );
    Threads[i].FreeOnTerminate := False;
    if CurrentProcessor = a then Inc(a); // Пропуск текущего процессора.
    Inc(a);
    // Здесь происходит попытка установки маски аффинности, которая приводит к ошибке.
    if SetThreadAffinityMask(Threads[i].Handle, SingleProcessorMask(a)) = 0 then RaiseLastOSError;
    Threads[i].Start;
  end;
  // Остальная часть процедуры опущена для экономии места.
end;

При выполнении данного кода возникает ошибка ERROR_INVALID_PARAMETER, несмотря на то, что код запускается от имени администратора и на разных устройствах с различным количеством ядер.

Решение проблемы

Проблема заключается в том, что маска аффинности потока не может включать ядра, которые не разрешены для процесса. Это означает, что маска аффинности потока должна быть подмножеством маски аффинности процесса. Следовательно, необходимо сначала установить маску аффинности процесса, чтобы включить все доступные ядра:

var
  ProcessAffinityMask, SystemAffinityMask, AllowedThreadMask: DWORD_PTR;
begin
  if not GetProcessAffinityMask(GetCurrentProcess, ProcessAffinityMask, SystemAffinityMask) then
    RaiseLastOSError;
  // Установка маски аффинности процесса для использования всех доступных ядер.
  if not SetProcessAffinityMask(GetCurrentProcess, SystemAffinityMask) then
    RaiseLastOSError;
  ProcessAffinityMask := SystemAffinityMask;
  AllowedThreadMask := DWORD_PTR(-1) and ProcessAffinityMask;
  // Остальная часть кода...
end;

После этого можно корректно установить маски аффинности для каждого потока, убедившись, что они не выходят за пределы разрешенных для процесса ядер.

Альтернативный ответ

В альтернативном ответе подчеркивается, что проблема может быть связана с неверным расчетом маски аффинности для потоков. Важно, чтобы маска аффинности потока была подмножеством маски аффинности процесса. Если процесс не настроен на использование всех доступных ядер, то и потокам не удастся использовать эти ядра.

Подтвержденный ответ

Проблема заключается в том, что разработчик пытается создать потоки, которые будут работать на ядрах, не включенных в маску аффинности процесса. Для корректной работы необходимо сначала установить маску аффинности процесса для использования всех доступных ядер, а затем уже распределять потоки по этим ядрам, соблюдая ограничения, установленные для процесса.

Заключение

При работе с многопоточностью в Delphi важно правильно управлять масками аффинности, чтобы обеспечить корректное распределение потоков по ядрам процессора. Следование правилам, установленным операционной системой, позволит избежать ошибок, связанных с неверной настройкой аффинности.

Создано по материалам из источника по ссылке.

Параллельное программирование в Delphi сталкивается с проблемой настройки маски аффинности потоков для корректного распределения по ядрам процессора.


Комментарии и вопросы

Получайте свежие новости и обновления по Object Pascal, Delphi и Lazarus прямо в свой смартфон. Подпишитесь на наш Telegram-канал delphi_kansoftware и будьте в курсе последних тенденций в разработке под Linux, Windows, Android и iOS




Материалы статей собраны из открытых источников, владелец сайта не претендует на авторство. Там где авторство установить не удалось, материал подаётся без имени автора. В случае если Вы считаете, что Ваши права нарушены, пожалуйста, свяжитесь с владельцем сайта.


:: Главная :: Потоки ::


реклама


©KANSoftWare (разработка программного обеспечения, создание программ, создание интерактивных сайтов), 2007
Top.Mail.Ru

Время компиляции файла: 2024-12-22 20:14:06
2024-12-26 14:33:32/0.0034279823303223/0