⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 simx86p.pas

📁 汇编编程艺术
💻 PAS
📖 第 1 页 / 共 4 页
字号:
unit Simx86p;

interface

uses
  SysUtils, WinTypes, WinProcs, Messages, Classes, Graphics, Controls,
  Forms, Dialogs, Patterns, Menus, StdCtrls, TabNotBk, ExtCtrls, VBXCtrl,
  Switch, Spin, GetInput, Printers;

type

  TMem = array [0..$ffef] of byte;
  TMemPtr = ^TMem;

  TSIMx86Form = class(TForm)
    Simx86Pages: TTabbedNotebook;
    SourceCode: TMemo;
    MainMenu: TMainMenu;
    File1: TMenuItem;
    Edit: TMenuItem;
    New: TMenuItem;
    Open: TMenuItem;
    Save: TMenuItem;
    SaveAs: TMenuItem;
    Cut: TMenuItem;
    Copy: TMenuItem;
    Paste: TMenuItem;
    Delete: TMenuItem;
    EditBreak: TMenuItem;
    BeforeQuit: TMenuItem;
    PrintMenuItem: TMenuItem;
    SelectAll: TMenuItem;
    OpenDialog: TOpenDialog;
    SaveDialog: TSaveDialog;
    StartAdrs: TEdit;
    StartAdrsLbl: TLabel;
    ASMbtn: TButton;

    Mem01: TEdit;
    Mem02: TEdit;
    Mem03: TEdit;
    Mem04: TEdit;
    Mem05: TEdit;
    Mem00: TEdit;
    Mem06: TEdit;
    Mem07: TEdit;

    AdrsEntry: TEdit;
    Label0: TLabel;
    Label1: TLabel;
    Label2: TLabel;
    Label3: TLabel;
    Label4: TLabel;
    Label5: TLabel;
    Label6: TLabel;
    Label7: TLabel;
    Lbl8: TLabel;
    Lbl10: TLabel;
    Lbl18: TLabel;
    Lbl20: TLabel;
    Lbl28: TLabel;
    Lbl30: TLabel;
    Lbl38: TLabel;
    Mem10: TEdit;
    Mem11: TEdit;
    Mem12: TEdit;
    Mem13: TEdit;
    Mem14: TEdit;
    Mem15: TEdit;
    Mem16: TEdit;
    Mem17: TEdit;
    Mem27: TEdit;
    Mem26: TEdit;
    Mem25: TEdit;
    Mem24: TEdit;
    Mem23: TEdit;
    Mem22: TEdit;
    Mem21: TEdit;
    Mem20: TEdit;
    Mem30: TEdit;
    Mem31: TEdit;
    Mem32: TEdit;
    Mem33: TEdit;
    Mem34: TEdit;
    Mem35: TEdit;
    Mem36: TEdit;
    Mem37: TEdit;
    Mem47: TEdit;
    Mem46: TEdit;
    Mem45: TEdit;
    Mem44: TEdit;
    Mem43: TEdit;
    Mem42: TEdit;
    Mem41: TEdit;
    Mem40: TEdit;
    Mem50: TEdit;
    Mem51: TEdit;
    Mem52: TEdit;
    Mem53: TEdit;
    Mem54: TEdit;
    Mem55: TEdit;
    Mem56: TEdit;
    Mem57: TEdit;
    Mem67: TEdit;
    Mem66: TEdit;
    Mem65: TEdit;
    Mem64: TEdit;
    Mem63: TEdit;
    Mem62: TEdit;
    Mem61: TEdit;
    Mem60: TEdit;
    Mem70: TEdit;
    Mem71: TEdit;
    Mem72: TEdit;
    Mem73: TEdit;
    Mem74: TEdit;
    Mem75: TEdit;
    Mem76: TEdit;
    Mem77: TEdit;
    IntVect: TEdit;
    IntVectLbl: TLabel;
    ResetVectLbl: TLabel;
    ResetVect: TEdit;
    Label8: TLabel;
    DisAsm: TListBox;
    Output: TListBox;
    InPort0: TBiSwitch;
    InPort2: TBiSwitch;
    InPort4: TBiSwitch;
    InPort6: TBiSwitch;
    OutPort8: TShape;
    OutPortA: TShape;
    OutPortC: TShape;
    OutPortE: TShape;
    FFF8Lbl: TLabel;
    FFFALbl: TLabel;
    FFFCLbl: TLabel;
    FFFELbl: TLabel;
    RunBtn: TButton;
    StepBtn: TButton;
    HaltBtn: TButton;
    InterruptBtn: TButton;
    OutputLbl: TLabel;
    RunningLite: TPanel;
    AXValue: TEdit;
    AXLbl: TLabel;
    BXValue: TEdit;
    DXValue: TEdit;
    CXValue: TEdit;
    IPValue: TEdit;
    BXLbl: TLabel;
    CXLbl: TLabel;
    DXLbl: TLabel;
    IPLbl: TLabel;
    Instruction: TLabel;
    DisAsmAdrs: TEdit;
    EqualFlag: TCheckBox;
    LessThanFlag: TCheckBox;
    ResetBtn: TButton;
    Input: TListBox;
    InputLbl: TLabel;
    SpinButton: TSpinButton;
    ClrMemBtn: TButton;
    PrintDialog: TPrintDialog;
    N1: TMenuItem;
    Quit: TMenuItem;

    procedure QuitClick(Sender: TObject);
    procedure CutClick(Sender: TObject);
    procedure CopyClick(Sender: TObject);
    procedure PasteClick(Sender: TObject);
    procedure DeleteClick(Sender: TObject);
    procedure SelectAllClick(Sender: TObject);
    procedure NewClick(Sender: TObject);
    procedure OpenClick(Sender: TObject);
    procedure SaveAsClick(Sender: TObject);
    procedure HexChange(Sender: TObject);
    procedure FormCreate(Sender: TObject);
    procedure AdrsEntryChange(Sender: TObject);
    procedure StartAdrsChange(Sender: TObject);
    procedure ASMbtnClick(Sender: TObject);
    procedure Simx86PagesChange(Sender: TObject; NewTab: Integer;
      var AllowChange: Boolean);
    procedure ClrMemBtnClick(Sender: TObject);
    procedure DisAsmAdrsChange(Sender: TObject);
    procedure SpinButtonDownClick(Sender: TObject);
    procedure SpinButtonUpClick(Sender: TObject);
    procedure ResetBtnClick(Sender: TObject);
    procedure RunBtnClick(Sender: TObject);
    procedure HaltBtnClick(Sender: TObject);
    procedure InterruptBtnClick(Sender: TObject);
    procedure IntVectChange(Sender: TObject);
    procedure IPValueChange(Sender: TObject);
    procedure StepBtnClick(Sender: TObject);
    procedure PrintMenuItemClick(Sender: TObject);
    procedure SaveClick(Sender: TObject);
  private
    { Private declarations }
  public
    { Public declarations }
  end;


var
  SIMx86Form: TSIMx86Form;
  MemEntry: array[0..7,0..7] of TEdit;






implementation

type

    TSymPtr = ^TSym;

    TSym = record
             value:word;
             defined:boolean;
           end;




const
	MaxCodeAdrs = 4095;

var

  HasOpcode:Boolean;
  Opcode:word;
  HasReg:Boolean;
  RegCode:word;
  HasOperand:Boolean;
  OperandCode:word;
  HasValue:Boolean;
  OperandValue:word;
  StoreMem:boolean;

  Halted:boolean;
  Running:boolean;
  PendingInt:boolean;
  InInt:boolean;
  IntAdrs:word;

  Val:byte;

  AX: word;
  BX: word;
  CX: word;
  DX: word;
  IP: word;

  LineNum:integer;
  Adrs:word;
  MemAdrs:word;
  MemWS:integer;
  AbortAsm:Boolean;
  NoError:Boolean;
  Memory: TMemPtr;
  SymTbl: array ['A'..'Z'] of TSym;


  SaveAX:word;
  SaveBX:word;
  SaveCX:word;
  SaveDX:word;
  SaveIP:word;
  SaveEqual:boolean;
  SaveLess:boolean;

  Reg:byte;
  RegMem:byte;
  Operation:byte;
  InstrSize:word;

  Op1:^word;
  Op2v:word;
  offset:word;

  Filename:string;







{$F+}
function ProcessLbl(Pat:TPatPtr):boolean; forward;
function GetLbl(Pat:TPatPtr):boolean; forward;
function ConvertHex(Pat:TPatPtr):boolean; forward;

procedure SetJmp(Pat:TPatPtr); forward;
procedure SetJa(Pat:TPatPtr); forward;
procedure SetJae(Pat:TPatPtr); forward;
procedure SetJb(Pat:TPatPtr); forward;
procedure SetJbe(Pat:TPatPtr); forward;
procedure SetJe(Pat:TPatPtr); forward;
procedure SetJne(Pat:TPatPtr); forward;

procedure SetNot(Pat:TPatPtr); forward;
procedure SetAnd(Pat:TPatPtr); forward;
procedure SetOr(Pat:TPatPtr); forward;
procedure SetCmp(Pat:TPatPtr); forward;
procedure SetSub(Pat:TPatPtr); forward;
procedure SetAdd(Pat:TPatPtr); forward;
procedure SetMovReg(Pat:TPatPtr); forward;
procedure SetMovMem(Pat:TPatPtr); forward;


procedure SetIret(Pat:TPatPtr); forward;
procedure SetHalt(Pat:TPatPtr); forward;
procedure SetBrk(Pat:TPatPtr); forward;
procedure SetPut(Pat:TPatPtr); forward;
procedure SetGet(Pat:TPatPtr); forward;

procedure SetAX(Pat:TPatPtr); forward;
procedure SetBX(Pat:TPatPtr); forward;
procedure SetCX(Pat:TPatPtr); forward;
procedure SetDX(Pat:TPatPtr); forward;

procedure SetAX2(Pat:TPatPtr); forward;
procedure SetBX2(Pat:TPatPtr); forward;
procedure SetCX2(Pat:TPatPtr); forward;
procedure SetDX2(Pat:TPatPtr); forward;

procedure SetBXInd(Pat:TPatPtr); forward;
procedure SetBXIndx(Pat:TPatPtr); forward;
procedure SetABS(Pat:TPatPtr); forward;
procedure SetImm(Pat:TPatPtr); forward;


{$F-}

const

     { WS1- Matches a string containing one or more white-   }
     {      space characters.                                }

     WS1:TPattern = (mf:OneOrMoreCset; m:(cset:[' ',#9]);
                     Next:NIL; Alt:NIL; Success:NIL);

     { WS0- Matches a string containing zero or more white-  }
     {      space characters.                                }

     WS0:TPattern=(mf:SpanCset; m:(cset:[' ',#9]);
                      Next:NIL; Alt:NIL; Success:NIL);


     { A Pattern that matches whitespace at the end of a line }

     SkipToEOS:TPattern=(mf:EOS; m:(ch:' ');
                       Next:NIL; Alt:NIL; Success:NIL);

     WSeoln:TPattern=(mf:SpanCset; m:(cset:[' ',#9]);
                       Next:@SkipToEOS; Alt:NIL; Success:NIL);



     { Match an x86 register mode here.                       }


     TryDX:Tpattern=(mf:Matchistr; m:(str:'DX');
                        Next:NIL; Alt:NIL; Success:SetDX);

     TryCX:Tpattern=(mf:Matchistr; m:(str:'CX');
                        Next:NIL; Alt:@TryDX; Success:SetCX);

     TryBX:Tpattern=(mf:Matchistr; m:(str:'BX');
                        Next:NIL; Alt:@TryCX; Success:SetBX);

     TryReg:Tpattern=(mf:Matchistr; m:(str:'AX');
                        Next:NIL; Alt:@TryBX; Success:SetAX);


     { Match an x86 addressing mode here                     }

     TryImm:TPattern=( mf:ConvertHex; m:(ch:' ');
                      Next:@WSEoln; Alt:NIL; Success:SetImm);

     TryDX2:Tpattern=(mf:Matchistr; m:(str:'DX');
                        Next:@WSeoln; Alt:@TryImm; Success:SetDX2);

     TryCX2:Tpattern=(mf:Matchistr; m:(str:'CX');
                        Next:@WSeoln; Alt:@TryDX2; Success:SetCX2);

     TryBX2:Tpattern=(mf:Matchistr; m:(str:'BX');
                        Next:@WSeoln; Alt:@TryCX2; Success:SetBX2);

     TryReg2:Tpattern=(mf:Matchistr; m:(str:'AX');
                        Next:@WSeoln; Alt:@TryBX2; Success:SetAX2);



     BXBrack:TPattern=( mf:MatchChar; m:(ch:']');
                      Next:NIL; Alt:NIL; Success:NIL);

     BXBrackWS:TPattern=( mf:SpanCset; m:(cset:[' ',#9]);
                      Next:@BXBrack; Alt:NIL; Success:NIL);

     BXEnd:TPattern=( mf:MatchiStr; m:(str:'BX');
                      Next:@BXBrackWS; Alt:NIL; Success:NIL);

     TryABS:TPattern=( mf:Succeed; m:(ch:' ');
                       Next:@BXBrackWS; Alt:NIL; Success:SetABS);

     BXPlus:TPattern=( mf:MatchChar; m:(ch:'+');
                      Next:@BXEnd; Alt:@TryABS; Success:SetBXIndx);

     BXPlusWS:TPattern=( mf:SpanCset; m:(cset:[' ',#9]);
                      Next:@BXPlus; Alt:NIL; Success:NIL);

     BXIndex:TPattern=( mf:ConvertHex; m:(ch:' ');
                        Next:@BXPlusWS; Alt:@BXEnd; Success:NIL);


     BXBracket:TPattern=( mf:MatchiStr; m:(str:'BX');
                          Next:@BXBrackWS; Alt:@BXIndex; Success:SetBXInd);


     BXIndWS:TPattern=(mf:SpanCset; m:(cset:[' ',#9]);
                      Next:@BXBracket; Alt:NIL; Success:NIL);

     DoMem:TPattern=( mf:MatchChar; m:(ch:'[');
                      Next:@BXIndWS; Alt:@TryReg2; Success:NIL);


     { Generic Two-operand instructions }

     TryOr:TPattern=(mf:MatchiStr; m:(str:'OR');
                        Next:NIL; Alt:NIL; Success:SetOr);

     TryAnd:TPattern=(mf:MatchiStr; m:(str:'AND');
                        Next:NIL; Alt:@TryOr; Success:SetAnd);

     TryCmp:TPattern=(mf:MatchiStr; m:(str:'CMP');
                        Next:NIL; Alt:@TryAnd; Success:SetCmp);

     TrySub:TPattern=(mf:MatchiStr; m:(str:'SUB');
                        Next:NIL; Alt:@TryCmp; Success:SetSub);

     TryAdd:TPattern=( mf:MatchiStr; m:(str:'ADD');
                       Next:NIL; Alt:@TrySub; Success:SetAdd);



     { Handle label definitions at the beginning of the line    }

     Lbl:TPattern=(mf:ProcessLbl; m:(ch:' ');
                   Next:NIL; Alt:NIL; Success:NIL);



     { A statement may be one of the following:                 }
     {                                                          }
     {       1: A Blank Line.                                   }
     {       2: An optional label in column 1 followed by an    }
     {          instruction.                                    }
     {       3: Whitespace followed by an instruction.          }
     {       4: An instruction starting in column 1.            }
     {                                                          }
     { The following patterns match one of the above.           }

     { Zero-Operand Instructions here: }


     TryBrk:TPattern=( mf:MatchiStr; m:(str:'BRK');
                      Next:@WSeoln; Alt:NIL; Success:SetBrk);

     TryIRet:TPattern=( mf:MatchiStr; m:(str:'IRET');
                      Next:@WSeoln; Alt:@TryBrk; Success:SetIret);

     TryHalt:TPattern=( mf:MatchiStr; m:(str:'HALT');
                      Next:@WSeoln; Alt:@TryIRet; Success:SetHalt);

     TryPut:TPattern=( mf:MatchiStr; m:(str:'PUT');
                      Next:@WSeoln; Alt:@TryHalt; Success:SetPut);

     TryGet:TPattern=( mf:MatchiStr; m:(str:'GET');
                      Next:@WSeoln; Alt:@TryPut; Success:SetGet);

     { Jump Instructions here: }

     JmpLbl2:TPattern=(mf:GetLbl; m:(ch:' ');
                        Next:NIL; Alt:NIL; Success:NIL);

     JmpLbl:TPattern=(mf:OneOrMoreCset; m:(cset:[' ',#9]);
                        Next:@JmpLbl2; Alt:NIL; Success:NIL);

     TryJne:TPattern=(mf:MatchiStr; m:(str:'JNE');
                        Next:@JmpLbl; Alt:@TryGet; Success:SetJne);

     TryJe:TPattern=(mf:MatchiStr; m:(str:'JE');
                        Next:@JmpLbl; Alt:@TryJne; Success:SetJe);

     TryJb:TPattern=(mf:MatchiStr; m:(str:'JB');
                        Next:@JmpLbl; Alt:@TryJe; Success:SetJb);

     TryJbe:TPattern=(mf:MatchiStr; m:(str:'JBE');
                        Next:@JmpLbl; Alt:@TryJb; Success:SetJbe);

     TryJa:TPattern=(mf:MatchiStr; m:(str:'JA');
                        Next:@JmpLbl; Alt:@TryJbe; Success:SetJa);

     TryJae:TPattern=(mf:MatchiStr; m:(str:'JAE');
                        Next:@JmpLbl; Alt:@TryJa; Success:SetJae);

     TryJmp:TPattern=(mf:MatchiStr; m:(str:'JMP');
                        Next:@JmpLbl; Alt:@TryJae; Success:SetJmp);



     { not reg/mem here: }

     GenMemMode:TPattern=( mf:MatchSub; m:(Pat:@DoMem);
                          Next:@WSeoln; Alt:NIL; Success:NIL);


     NotWS:TPattern=(mf:SpanCset; m:(cset:[' ',#9]);
                     Next:@GenMemMode; Alt:NIL; Success:NIL);

     TryNotInstr:TPattern=( mf:MatchiStr; m:(str:'NOT');
                           Next:@NotWS; Alt:@TryJmp; Success:SetNot);



     { instr reg, mem here: }

     WSComma2:TPattern=( mf:SpanCset; m:(cset:[' ',',',#9]);
                         Next:@GenMemMode; Alt:NIL; Success:NIL);

     GenRegMem:TPattern=(mf:MatchSub; m:(Pat:@TryReg);
                     Next:@WSComma2; Alt:NIL; Success:NIL);

     InstrWS:TPattern=(mf:SpanCset; m:(cset:[' ',#9]);
                     Next:@GenRegMem; Alt:NIL; Success:NIL);

     TryGeneric:TPattern=( mf:MatchSub; m:(Pat:@TryAdd);
                           Next:@InstrWS; Alt:@TryNotInstr; Success:NIL);



     { mov mem, reg here: }

     MovReg:TPattern=(mf:MatchSub; m:(Pat:@TryReg);
                     Next:@WSeoln; Alt:NIL; Success:SetMovMem);

     WSComma3:TPattern=( mf:SpanCset; m:(cset:[' ',',',#9]);
                       Next:@MovReg; Alt:NIL; Success:NIL);

     MemReg:TPattern=( mf:MatchSub; m:(Pat:@DoMem);
                       Next:@WSComma3; Alt:NIL; Success:NIL);


     { mov reg, mem here: }

     MemMode:TPattern=( mf:MatchSub; m:(Pat:@DoMem);
                       Next:@WSeoln; Alt:NIL; Success:SetMovReg);

     WSComma:TPattern=( mf:SpanCset; m:(cset:[' ',',',#9]);
                       Next:@MemMode; Alt:NIL; Success:NIL);

     RgMem:TPattern=(mf:MatchSub; m:(Pat:@TryReg);
                     Next:@WSComma; Alt:@MemReg; Success:NIL);

     { Generic mov here: }

     MovWS:TPattern=(mf:SpanCset; m:(cset:[' ',#9]);
                     Next:@RgMem; Alt:NIL; Success:NIL);

     TryMnemonic:TPattern=(mf:MatchiStr; m:(str:'MOV');
                      Next:@MovWS; Alt:@TryGeneric; Success:NIL);




     TryEOS:TPattern=(mf:EOS; m:(ch:' ');
                      Next:NIL; Alt:@TryMnemonic; Success:NIL);

     TryWS:TPattern =(mf:SpanCset; m:(cset:[' ',#9]);
                      Next:@TryEOS; Alt:NIL; Success:NIL);

     stmt:TPattern = (mf:MatchSub; m:(Pat:@Lbl);
                      Next:@TryMnemonic; Alt:@TryWS; Success:NIL);








{ System initialization }


procedure TSIMx86Form.FormCreate(Sender: TObject);
var 	i:	word;
	ch:	char;
begin


    { Allocate Storage for the x86 memory space }

    system.new(Memory);

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -