Я пытаюсь преобразовать Delphi TBits.GetBit в встроенный ассемблер для 64-разрядной версии. Источник VCL выглядит так:Доступ к полям класса Delphi в 64-битном встроенном ассемблере
function TBits.GetBit(Index: Integer): Boolean;
{$IFNDEF X86ASM}
var
LRelInt: PInteger;
LMask: Integer;
begin
if (Index >= FSize) or (Index < 0) then
Error;
{ Calculate the address of the related integer }
LRelInt := FBits;
Inc(LRelInt, Index div BitsPerInt);
{ Generate the mask }
LMask := (1 shl (Index mod BitsPerInt));
Result := (LRelInt^ and LMask) <> 0;
end;
{$ELSE X86ASM}
asm
CMP Index,[EAX].FSize
JAE TBits.Error
MOV EAX,[EAX].FBits
BT [EAX],Index
SBB EAX,EAX
AND EAX,1
end;
{$ENDIF X86ASM}
Я начал конвертировать 32-битный ASM-код в 64-разрядный. После некоторого поиска я узнал, что мне нужно изменить ссылки EAX на RAX для 64-битного компилятора. Я закончил с этим для первой строки:
CMP Index,[RAX].FSize
Это компилируется, но дает нарушение прав доступа при его запуске. Я попробовал несколько комбинаций (например, MOV ECX,[RAX].FSize
) и получил такое же нарушение доступа при попытке доступа к [RAX].FSize
. Когда я смотрю на ассемблер, который генерируется компилятором Delphi, похоже, что мой [RAX].FSize
должен быть правильным.
Unit72.pas.143: MOV ECX,[RAX].FSize
00000000006963C0 8B8868060000 mov ecx,[rax+$00000668]
И Delphi сгенерированный код:
Unit72.pas.131: if (Index >= FSize) or (Index < 0) then
00000000006963CF 488B4550 mov rax,[rbp+$50]
00000000006963D3 8B4D58 mov ecx,[rbp+$58]
00000000006963D6 3B8868060000 cmp ecx,[rax+$00000668]
00000000006963DC 7D06 jnl TForm72.GetBit + $24
00000000006963DE 837D5800 cmp dword ptr [rbp+$58],$00
00000000006963E2 7D09 jnl TForm72.GetBit + $2D
В обоих случаях полученный ассемблер использует [rax+$00000668]
для FSIZE. Каков правильный способ доступа к классу в Delphi 64bit Assembler?
Это может показаться странным для оптимизации, но ассемблер для 64-битной версии паскаля выглядит не очень эффективным. Мы называем эту процедуру большим количеством раз, и для выполнения в любом случае требуется в 5 раз больше времени, в зависимости от различных факторов.
У вас есть версия pascal под рукой? –
@DavidHeffernan Положите его в вопрос. Не хотел ставить слишком много источников Delphi VCL в вопрос. 64-разрядная версия не то же самое. – Graymatter
Это код VCL, не так ли? В этом случае я могу найти его. –