[试题]BASM不用call调用函数

[考题]BASM不用call调用函数
Delphi(Pascal) code
procedure TForm1.FormCreate(Sender: TObject);
asm
  mov eax,offset @@buf+8
  call ShowMessage
  ret
@@buf:
  db $ff,$ff,$ff,$ff,3,0,0,0,'abc',0
end;


上面是使用call的,如何不使用call而达到同样的效果呢?

------解决方案--------------------
call有2个动作

1. IP或CS和IP压入栈
2. 转移

所以1楼说的是对的

------解决方案--------------------
同意1楼,PUSH RET集合,PUSH JXXX结合都可以实现CALL,

来个很BT的,构造SEH来实现跳转,这在反调试上会用到,可以增加点跟踪难度,

Delphi(Pascal) code

procedure ExceptProc{ExceptionRecord,SEH,Context,DispatcherContext};assembler;
asm
  MOV  EAX , [ESP+12]
  MOV  EAX.TContext.Eip , Offset @@ExceptDone
  MOV  EAX , 1
  RET  $10;
  @@ExceptDone:
  XOR  EAX , EAX
  MOV  ESP , FS:[EAX+$14]
  POP  FS:[EAX]
  POP  EAX
  POPAD
end;

//P As TProcedure /Function xxx : integer/Boolean/More
Function ExceptDoProcedure(P : Pointer) : integer;assembler;
asm
  PUSH EAX                    //被执行函数
  PUSHAD                      //保护现场
  XOR  EAX          , EAX
  PUSH Offset ExceptProc      //异常处理函数
  PUSH FS:[EAX]               //SEH结构
  MOV  FS:[EAX]     , ESP
  MOV  FS:[EAX+$14] , ESP
  MOV  DS:[EAX]     , EAX;    //产生异常,触发SEH执行,进而转入P中执行
end;



//调用时
Function DoIt : integer;
begin
  ShowMessage('OK');
  Result := $100
end;

procedure TForm1.FormCreate(Sender: TObject);
begin
  Tag := ExceptDoProcedure(@DoIt);
  Caption := IntToHex(Tag , 8);
end;