Changeset 184 for branches/virtualcpu4
- Timestamp:
- Apr 25, 2019, 4:20:43 PM (6 years ago)
- Location:
- branches/virtualcpu4
- Files:
-
- 3 added
- 11 edited
Legend:
- Unmodified
- Added
- Removed
-
branches/virtualcpu4/Forms/UFormDisassembler.lfm
r181 r184 1 1 object FormDisassembler: TFormDisassembler 2 Left = 6873 Height = 6914 Top = 4165 Width = 7212 Left = 587 3 Height = 576 4 Top = 248 5 Width = 601 6 6 Caption = 'Disassembler' 7 ClientHeight = 6918 ClientWidth = 7219 DesignTimePPI = 1 447 ClientHeight = 576 8 ClientWidth = 601 9 DesignTimePPI = 120 10 10 OnCreate = FormCreate 11 11 OnDestroy = FormDestroy 12 LCLVersion = '2.0.0.4' 12 OnShow = FormShow 13 LCLVersion = '2.0.2.0' 13 14 object ListView1: TListView 14 Left = 8 15 Height = 675 16 Top = 8 17 Width = 705 18 Align = alClient 19 BorderSpacing.Around = 8 15 Left = 7 16 Height = 521 17 Top = 7 18 Width = 587 19 Align = alCustom 20 Anchors = [akTop, akLeft, akRight, akBottom] 21 BorderSpacing.Around = 7 20 22 Columns = < 21 23 item 22 24 Caption = 'Address' 23 Width = 10025 Width = 83 24 26 end 25 27 item 26 28 Caption = 'Opcode' 27 Width = 1 5029 Width = 125 28 30 end 29 31 item 30 32 Caption = 'Assembly' 31 Width = 44033 Width = 367 32 34 end> 33 35 OwnerData = True 36 ParentFont = False 34 37 ReadOnly = True 35 38 RowSelect = True … … 38 41 OnData = ListView1Data 39 42 end 43 object ButtonReload: TButton 44 Left = 7 45 Height = 31 46 Top = 536 47 Width = 94 48 Anchors = [akLeft, akBottom] 49 Caption = 'Reload' 50 OnClick = ButtonReloadClick 51 TabOrder = 1 52 end 40 53 end -
branches/virtualcpu4/Forms/UFormDisassembler.pas
r181 r184 6 6 7 7 uses 8 Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ComCtrls, 8 Classes, SysUtils, Forms, Controls, Graphics, Dialogs, ComCtrls, StdCtrls, 9 9 UDisassembler; 10 10 … … 14 14 15 15 TFormDisassembler = class(TForm) 16 ButtonReload: TButton; 16 17 ListView1: TListView; 18 procedure ButtonReloadClick(Sender: TObject); 17 19 procedure FormCreate(Sender: TObject); 18 20 procedure FormDestroy(Sender: TObject); 21 procedure FormShow(Sender: TObject); 19 22 procedure ListView1Data(Sender: TObject; Item: TListItem); 20 23 private … … 39 42 end; 40 43 44 procedure TFormDisassembler.ButtonReloadClick(Sender: TObject); 45 begin 46 Disassembler.Process; 47 Reload; 48 end; 49 41 50 procedure TFormDisassembler.FormDestroy(Sender: TObject); 42 51 begin 43 52 Disassembler.Free; 53 end; 54 55 procedure TFormDisassembler.FormShow(Sender: TObject); 56 begin 57 ButtonReload.Click; 44 58 end; 45 59 -
branches/virtualcpu4/Forms/UFormMain.lfm
r183 r184 82 82 TabOrder = 6 83 83 end 84 object ButtonAssembler: TButton 85 Left = 309 86 Height = 32 87 Top = 128 88 Width = 154 89 Caption = 'Assembler' 90 OnClick = ButtonAssemblerClick 91 ParentFont = False 92 TabOrder = 7 93 end 84 94 end -
branches/virtualcpu4/Forms/UFormMain.pas
r183 r184 14 14 15 15 TFormMain = class(TForm) 16 ButtonAssembler: TButton; 16 17 ButtonScreen: TButton; 17 18 ButtonDisassembler: TButton; … … 21 22 ButtonStart: TButton; 22 23 ButtonStop: TButton; 24 procedure ButtonAssemblerClick(Sender: TObject); 23 25 procedure ButtonConsoleClick(Sender: TObject); 24 26 procedure ButtonCpuStateClick(Sender: TObject); … … 47 49 48 50 uses 49 UFormDisassembler, UFormMemory, UFormCpuState, UFormScreen, UFormConsole; 51 UFormDisassembler, UFormMemory, UFormCpuState, UFormScreen, UFormConsole, 52 UFormAssembler; 50 53 51 54 { TFormMain } … … 61 64 FormDisassembler := TFormDisassembler.Create(Self); 62 65 FormDisassembler.Disassembler.Cpu := Machine.Cpu; 63 FormDisassembler.Disassembler.Process;64 66 FormDisassembler.Show; 65 67 FormDisassembler.Reload; … … 99 101 FormConsole.Machine := Machine; 100 102 FormConsole.Show; 103 end; 104 105 procedure TFormMain.ButtonAssemblerClick(Sender: TObject); 106 begin 107 if not Assigned(FormAssembler) then 108 FormAssembler := TFormAssembler.Create(Self); 109 FormAssembler.Assembler.InstructionWriter.Cpu := Machine.Cpu; 110 FormAssembler.Show; 101 111 end; 102 112 -
branches/virtualcpu4/UAssembler.pas
r181 r184 6 6 7 7 uses 8 Classes, SysUtils ;8 Classes, SysUtils, fgl, UCpu, UOpcode, UInstructionWriter; 9 9 10 10 type 11 TErrorEvent = procedure (Text: string) of object; 12 13 { TParser } 14 15 TParser = class 16 private 17 FOnError: TErrorEvent; 18 procedure Error(Text: string); 19 public 20 Text: string; 21 procedure Expect(Text: string); 22 function ReadNext: string; 23 function EndOfText: Boolean; 24 property OnError: TErrorEvent read FOnError write FOnError; 25 end; 26 27 TLabel = class 28 Name: string; 29 Address: QWord; 30 end; 31 32 TLabels = class(TFPGObjecTList<TLabel>) 33 34 end; 35 11 36 { TAssembler } 12 37 13 38 TAssembler = class 39 private 40 FOnError: TErrorEvent; 41 OpcodeDefs: TOpcodeDefs; 42 procedure Error(Text: string); 43 procedure ParseParam(Param: TOpcodeParam); 44 public 45 Parser: TParser; 46 Labels: TLabels; 14 47 Source: TStringList; 15 Dest: array of Byte;48 InstructionWriter: TInstructionWriter; 16 49 procedure Compile; 50 constructor Create; 51 destructor Destroy; override; 52 property OnError: TErrorEvent read FOnError write FOnError; 17 53 end; 18 54 … … 20 56 implementation 21 57 58 { TParser } 59 60 procedure TParser.Error(Text: string); 61 begin 62 if Assigned(FOnError) then FOnError(Text); 63 end; 64 65 procedure TParser.Expect(Text: string); 66 var 67 Next: string; 68 begin 69 Next := ReadNext; 70 if Next <> Text then 71 Error('Expected ' + Text + ' but ' + Next + ' found'); 72 end; 73 74 function TParser.ReadNext: string; 75 var 76 P: Integer; 77 begin 78 Text := Trim(Text); 79 P := 1; 80 if (Length(Text) > 0) and (Text[P] = ',') then begin 81 Result := Text[P]; 82 Delete(Text, 1, 1); 83 end else begin 84 while (P <= Length(Text)) and (Text[P] <> ' ') and (Text[P] <> ',') do Inc(P); 85 Result := Copy(Text, 1, P - 1); 86 Delete(Text, 1, P - 1); 87 end; 88 end; 89 90 function TParser.EndOfText: Boolean; 91 begin 92 Result := Text = ''; 93 end; 94 22 95 { TAssembler } 23 96 97 procedure TAssembler.Error(Text: string); 98 begin 99 if Assigned(FOnError) then FOnError(Text); 100 end; 101 102 procedure TAssembler.ParseParam(Param: TOpcodeParam); 103 var 104 Reg: TRegIndex; 105 Addr: QWord; 106 Next: string; 107 begin 108 if Param = prReg then begin 109 Next := Parser.ReadNext; 110 if (Length(Next) > 1) and (Next[1] = 'R') then 111 Reg := StrToInt(Copy(Next, 2, Length(Next))) 112 else Error('Expected register name but found ' + Next); 113 InstructionWriter.Write8(Reg); 114 end else 115 if Param = prData then begin 116 Next := Parser.ReadNext; 117 InstructionWriter.WriteData(StrToInt(Next)); 118 end else 119 if Param = prAddr then begin 120 Next := Parser.ReadNext; 121 InstructionWriter.WriteAddress(StrToInt(Next)); 122 end else 123 if Param = prAddrRel then begin 124 Next := Parser.ReadNext; 125 InstructionWriter.WriteAddress(StrToInt(Next)); 126 end; 127 end; 128 24 129 procedure TAssembler.Compile; 130 var 131 I: Integer; 132 NewLabel: TLabel; 133 Next: string; 134 OpcodeDef: TOpcodeDef; 25 135 begin 136 InstructionWriter.Init; 137 Labels.Clear; 138 for I := 0 to Source.Count - 1 do begin 139 Parser.Text := Source[I]; 140 Next := Parser.ReadNext; 141 if (Length(Next) > 0) and (Next[Length(Next)] = ':') then begin 142 NewLabel := TLabel.Create; 143 NewLabel.Name := Copy(Next, 1, Length(Next) - 1); 144 //NewLabel.Address := ; 145 Labels.Add(NewLabel); 146 Next := Parser.ReadNext; 147 end; 148 OpcodeDef := OpcodeDefs.SearchByName(Next); 149 if Assigned(OpcodeDef) then begin 150 InstructionWriter.Write8(Byte(OpcodeDef.Opcode)); 151 ParseParam(OpcodeDef.Param1); 152 if OpcodeDef.Param2 <> prNone then begin 153 Parser.Expect(','); 154 ParseParam(OpcodeDef.Param2); 155 if OpcodeDef.Param3 <> prNone then begin 156 Parser.Expect(','); 157 ParseParam(OpcodeDef.Param3); 158 end; 159 end; 160 end else Error('Unknown instruction ' + Next); 161 end; 162 end; 26 163 164 constructor TAssembler.Create; 165 begin 166 OpcodeDefs := TOpcodeDefs.Create; 167 Source := TStringList.Create; 168 Labels := TLabels.Create; 169 Parser := TParser.Create; 170 Parser.OnError := Error; 171 InstructionWriter := TInstructionWriter.Create; 172 end; 173 174 destructor TAssembler.Destroy; 175 begin 176 FreeAndNil(InstructionWriter); 177 FreeAndNil(Parser); 178 FreeAndNil(Labels); 179 FreeAndNil(Source); 180 FreeAndNil(OpcodeDefs); 181 inherited Destroy; 27 182 end; 28 183 -
branches/virtualcpu4/UCpu.pas
r183 r184 138 138 end; 139 139 140 TOpcodeParam = (prNone, prReg, prData, prAddr, prAddrRel);141 TOpcodeDef = record142 Name: string;143 Param1: TOpcodeParam;144 Param2: TOpcodeParam;145 Param3: TOpcodeParam;146 Prefix: Boolean;147 end;148 149 140 const 150 141 BitWidthBytes: array[TBitWidth] of Byte = (0, 1, 2, 4, 8); 151 142 BitWidthText: array[TBitWidth] of string = ('None', '8-bit', '16-bit', '32-bit', '64-bit'); 152 OpcodeDef: array[TOpcode] of TOpcodeDef = (153 (Name: 'NOP'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: False),154 (Name: 'HALT'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: False),155 (Name: 'LD'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),156 (Name: 'LDI'; Param1: prReg; Param2: prData; Param3: prNone; Prefix: False),157 (Name: 'JP'; Param1: prAddr; Param2: prNone; Param3: prNone; Prefix: False),158 (Name: 'JPZ'; Param1: prAddr; Param2: prNone; Param3: prNone; Prefix: False),159 (Name: 'JPNZ'; Param1: prAddr; Param2: prNone; Param3: prNone; Prefix: False),160 (Name: 'JR'; Param1: prAddrRel; Param2: prNone; Param3: prNone; Prefix: False),161 (Name: 'JRZ'; Param1: prAddrRel; Param2: prNone; Param3: prNone; Prefix: False),162 (Name: 'JRNZ'; Param1: prAddrRel; Param2: prNone; Param3: prNone; Prefix: False),163 (Name: 'NEG'; Param1: prReg; Param2: prNone; Param3: prNone; Prefix: False),164 (Name: 'CLR'; Param1: prReg; Param2: prNone; Param3: prNone; Prefix: False),165 (Name: 'LDM'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),166 (Name: 'STM'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),167 (Name: 'EX'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),168 (Name: 'PUSH'; Param1: prReg; Param2: prNone; Param3: prNone; Prefix: False),169 (Name: 'POP'; Param1: prReg; Param2: prNone; Param3: prNone; Prefix: False),170 (Name: 'CALL'; Param1: prAddr; Param2: prNone; Param3: prNone; Prefix: False),171 (Name: 'RET'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: False),172 (Name: 'ADD'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),173 (Name: 'ADDI'; Param1: prReg; Param2: prData; Param3: prNone; Prefix: False),174 (Name: 'SUB'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),175 (Name: 'SUBI'; Param1: prReg; Param2: prData; Param3: prNone; Prefix: False),176 (Name: 'INC'; Param1: prReg; Param2: prNone; Param3: prNone; Prefix: False),177 (Name: 'DEC'; Param1: prReg; Param2: prNone; Param3: prNone; Prefix: False),178 (Name: 'IN'; Param1: prReg; Param2: prAddr; Param3: prNone; Prefix: False),179 (Name: 'OUT'; Param1: prAddr; Param2: prReg; Param3: prNone; Prefix: False),180 (Name: 'SHL'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),181 (Name: 'SHR'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),182 (Name: 'DP8'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: True),183 (Name: 'DP16'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: False),184 (Name: 'DP32'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: True),185 (Name: 'DP64'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: True),186 (Name: 'DS'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: False),187 (Name: 'AS'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: False),188 (Name: 'TEST'; Param1: prReg; Param2: prNone; Param3: prNone; Prefix: False),189 (Name: 'AND'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),190 (Name: 'OR'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),191 (Name: 'XOR'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),192 (Name: 'LDDR'; Param1: prReg; Param2: prReg; Param3: prReg; Prefix: False),193 (Name: 'LDDR'; Param1: prReg; Param2: prReg; Param3: prReg; Prefix: False),194 (Name: 'MUL'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),195 (Name: 'DIV'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),196 (Name: 'MOD'; Param1: prReg; Param2: prReg; Param3: prNone; Prefix: False),197 (Name: 'AP8'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: True),198 (Name: 'AP16'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: True),199 (Name: 'AP32'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: True),200 (Name: 'AP64'; Param1: prNone; Param2: prNone; Param3: prNone; Prefix: True),201 (Name: 'CON'; Param1: prReg; Param2: prNone; Param3: prNone; Prefix: True)202 );203 143 204 144 implementation -
branches/virtualcpu4/UDisassembler.pas
r183 r184 6 6 7 7 uses 8 Classes, SysUtils, UMemory, fgl, UCpu, UInstructionReader, Math ;8 Classes, SysUtils, UMemory, fgl, UCpu, UInstructionReader, Math, UOpcode; 9 9 10 10 type … … 19 19 TDisassembler = class(TInstructionReader) 20 20 private 21 OpcodeDefs: TOpcodeDefs; 21 22 public 22 23 Output: TFPGObjectList<TDisassemblerLine>; … … 48 49 AddressRel: TAddressSigned; 49 50 Reg: TRegIndex; 51 OpcodeDef: TOpcodeDef; 50 52 begin 51 53 Init; … … 57 59 Opcode := Read8; 58 60 if Opcode <= Integer(High(TOpcode)) then begin 59 Prefix := OpcodeDef[TOpcode(Opcode)].Prefix; 61 OpcodeDef := OpcodeDefs.SearchByOpcode(TOpcode(Opcode)); 62 Prefix := OpcodeDef.Prefix; 60 63 case TOpcode(Opcode) of 61 64 opDataPrefix8: DataSize := bw8; … … 71 74 Line.Address := IP - 1; 72 75 Line.Opcode := IntToHex(Opcode, 2); 73 Line.Instruction := OpcodeDef [TOpcode(Opcode)].Name;74 case OpcodeDef [TOpcode(Opcode)].Param1 of76 Line.Instruction := OpcodeDef.Name; 77 case OpcodeDef.Param1 of 75 78 prReg: begin 76 79 Reg := Read8; … … 94 97 end; 95 98 end; 96 case OpcodeDef [TOpcode(Opcode)].Param2 of99 case OpcodeDef.Param2 of 97 100 prReg: begin 98 101 Reg := Read8; … … 116 119 end; 117 120 end; 118 case OpcodeDef [TOpcode(Opcode)].Param3 of121 case OpcodeDef.Param3 of 119 122 prReg: begin 120 123 Reg := Read8; … … 156 159 constructor TDisassembler.Create; 157 160 begin 161 OpcodeDefs := TOpcodeDefs.Create; 158 162 Output := TFPGObjectList<TDisassemblerLine>.Create; 159 163 end; … … 161 165 destructor TDisassembler.Destroy; 162 166 begin 163 Output.Free; 167 FreeAndNil(Output); 168 FreeAndNil(OpcodeDefs); 164 169 inherited Destroy; 165 170 end; -
branches/virtualcpu4/UInstructionReader.pas
r182 r184 42 42 AddrSizeBase := Cpu.AddrSizeBase; 43 43 AddrSize := AddrSizeBase; 44 IP := 0; 45 Prefix := False; 44 46 end; 45 47 -
branches/virtualcpu4/UInstructionWriter.pas
r183 r184 329 329 AddrSizeBase := Cpu.AddrSizeBase; 330 330 AddrSize := AddrSizeBase; 331 IP := 0; 332 Prefix := False; 331 333 end; 332 334 -
branches/virtualcpu4/virtucpu4.lpi
r183 r184 71 71 </Item1> 72 72 </RequiredPackages> 73 <Units Count="1 4">73 <Units Count="16"> 74 74 <Unit0> 75 75 <Filename Value="virtucpu4.lpr"/> … … 146 146 <IsPartOfProject Value="True"/> 147 147 </Unit13> 148 <Unit14> 149 <Filename Value="UOpcode.pas"/> 150 <IsPartOfProject Value="True"/> 151 </Unit14> 152 <Unit15> 153 <Filename Value="Forms\UFormAssembler.pas"/> 154 <IsPartOfProject Value="True"/> 155 <ComponentName Value="FormAssembler"/> 156 <ResourceBaseClass Value="Form"/> 157 </Unit15> 148 158 </Units> 149 159 </ProjectOptions> -
branches/virtualcpu4/virtucpu4.lpr
r181 r184 10 10 SysUtils, Forms, UFormMain, UCpu, UMachine, UMemory, UFormDisassembler, 11 11 UFormMemory, UFormCpuState, UFormScreen, UFormConsole, UDisassembler, 12 UAssembler, UInstructionReader 12 UAssembler, UInstructionReader, UOpcode, UFormAssembler 13 13 { you can add units after this }; 14 14
Note:
See TracChangeset
for help on using the changeset viewer.