From ad8728bdf4821b5a5695e23c78a9f2d8d475bc30 Mon Sep 17 00:00:00 2001 From: Jaka Furlan Date: Sun, 30 Nov 2025 13:53:18 +0100 Subject: [PATCH] done? --- ass1/horner.log | 21 +++++++++ ass1/horner.lst | 38 ++++++++++++++++ ass1/horner.obj | 4 ++ ass1/poly.log | 21 +++++++++ ass1/poly.lst | 42 ++++++++++++++++++ ass1/poly.obj | 5 +++ ass1/test.asm | 4 ++ ass1/test.log | 13 ++++++ ass1/test.lst | 4 ++ ass1/test.obj | 3 ++ ass2/SICocaml/izvajalnik.cmi | Bin 3174 -> 3210 bytes ass2/SICocaml/izvajalnik.cmo | Bin 12039 -> 12033 bytes ass2/SICocaml/izvajalnik.ml | 8 +++- ass2/SICocaml/loader.ml | 51 ++++++++++++++++++++++ ass2/SICocaml/sicxeDune/bin/main.ml | 42 +++++------------- ass2/SICocaml/sicxeDune/lib/dune | 3 +- ass2/SICocaml/sicxeDune/lib/izvajalnik.ml | 44 ++++++++++++------- ass2/SICocaml/sicxeDune/lib/loader.ml | 49 +++++++++++++++++++++ ass2/SICocaml/sicxeDune/lib/pogajalnik.ml | 30 +++++++++++++ 19 files changed, 335 insertions(+), 47 deletions(-) create mode 100644 ass1/horner.log create mode 100644 ass1/horner.lst create mode 100644 ass1/horner.obj create mode 100644 ass1/poly.log create mode 100644 ass1/poly.lst create mode 100644 ass1/poly.obj create mode 100644 ass1/test.asm create mode 100644 ass1/test.log create mode 100644 ass1/test.lst create mode 100644 ass1/test.obj create mode 100644 ass2/SICocaml/loader.ml create mode 100644 ass2/SICocaml/sicxeDune/lib/loader.ml create mode 100644 ass2/SICocaml/sicxeDune/lib/pogajalnik.ml diff --git a/ass1/horner.log b/ass1/horner.log new file mode 100644 index 0000000..7f6c11d --- /dev/null +++ b/ass1/horner.log @@ -0,0 +1,21 @@ +***** Section ***** +Stats: size=61 blocks=61 symbols=10 literals=0 relocations=0 +Blocks + name start size #ins #dir #sto + 00000 0003D 16 8 1 +Symbols + name hex dec scope kind type description + halt 000025 37 local relative code label + poly 000000 0 exported relative code label + rez 00003A 58 local relative data label + start 000000 0 local relative code label + x 000037 55 local relative data label + x0 000034 52 local relative data label + x1 000031 49 local relative data label + x2 00002E 46 local relative data label + x3 00002B 43 local relative data label + x4 000028 40 local relative data label +Literals + label definition +Relocations + address length flag symbol diff --git a/ass1/horner.lst b/ass1/horner.lst new file mode 100644 index 0000000..4bb467e --- /dev/null +++ b/ass1/horner.lst @@ -0,0 +1,38 @@ +00000 poly START 0 +00000 772025 start LDT x4 +00003 6F2031 LDS x +00006 9845 MULR S,T +00008 032020 LDA x3 +0000B 9050 ADDR T,A . do sedaj izračunano (1x + 2) + +0000D 77201E LDT x2 +00010 9840 MULR S,A +00012 9050 ADDR T,A . do sedaj izračunano ((1x+2)x + 3) + +00014 77201A LDT x1 +00017 9840 MULR S,A +00019 9050 ADDR T,A . do sedaj izračunano (((1x+2)x + 3)x + 4) + +0001B 772016 LDT x0 +0001E 9840 MULR S,A +00020 9050 ADDR T,A . do sedaj izračunano (((1x+2)x + 3)x + 4)x + 5 + + +00022 0F2015 STA rez + +00025 3F2FFD halt J halt +00028 END start + + + . polinom +00028 000001 x4 WORD 1 +0002B 000002 x3 WORD 2 +0002E 000003 x2 WORD 3 +00031 000004 x1 WORD 4 +00034 000005 x0 WORD 5 + + . tocka +00037 000002 x WORD 2 + + . rezultat +0003A 000000 rez RESW 1 diff --git a/ass1/horner.obj b/ass1/horner.obj new file mode 100644 index 0000000..5c396f6 --- /dev/null +++ b/ass1/horner.obj @@ -0,0 +1,4 @@ +Hpoly 00000000003D +T0000001E7720256F20319845032020905077201E9840905077201A98409050772016 +T00001E1C984090500F20153F2FFD000001000002000003000004000005000002 +E000000 diff --git a/ass1/poly.log b/ass1/poly.log new file mode 100644 index 0000000..03eea94 --- /dev/null +++ b/ass1/poly.log @@ -0,0 +1,21 @@ +***** Section ***** +Stats: size=70 blocks=70 symbols=10 literals=0 relocations=0 +Blocks + name start size #ins #dir #sto + 00000 00046 20 8 1 +Symbols + name hex dec scope kind type description + halt 00002E 46 local relative code label + poly 000000 0 exported relative code label + rez 000043 67 local relative data label + start 000000 0 local relative code label + x 000040 64 local relative data label + x0 00003D 61 local relative data label + x1 00003A 58 local relative data label + x2 000037 55 local relative data label + x3 000034 52 local relative data label + x4 000031 49 local relative data label +Literals + label definition +Relocations + address length flag symbol diff --git a/ass1/poly.lst b/ass1/poly.lst new file mode 100644 index 0000000..3db26df --- /dev/null +++ b/ass1/poly.lst @@ -0,0 +1,42 @@ +00000 poly START 0 +00000 03203A start LDA x0 . pristejemo x0 v A + +00003 6B203A LDB x +00006 6F2037 LDS x +00009 77202E LDT x1 +0000C 9845 MULR S,T +0000E 9050 ADDR T,A . pristejemo x0 * x + +00010 772024 LDT x2 +00013 9834 MULR B,S . izracunamo x^2 +00015 9845 MULR S,T +00017 9050 ADDR T,A + +00019 772018 LDT x3 +0001C 9834 MULR B,S . izracunamo x^3 +0001E 9845 MULR S,T +00020 9050 ADDR T,A + +00022 77200C LDT x4 +00025 9834 MULR B,S . izracunamo x^4 +00027 9845 MULR S,T +00029 9050 ADDR T,A + +0002B 0F2015 STA rez + +0002E 3F2FFD halt J halt +00031 END start + + + . polinom +00031 000001 x4 WORD 1 +00034 000002 x3 WORD 2 +00037 000003 x2 WORD 3 +0003A 000004 x1 WORD 4 +0003D 000005 x0 WORD 5 + + . tocka +00040 000002 x WORD 2 + + . rezultat +00043 000000 rez RESW 1 diff --git a/ass1/poly.obj b/ass1/poly.obj new file mode 100644 index 0000000..ab21bac --- /dev/null +++ b/ass1/poly.obj @@ -0,0 +1,5 @@ +Hpoly 000000000046 +T0000001E03203A6B203A6F203777202E984590507720249834984590507720189834 +T00001E1E9845905077200C9834984590500F20153F2FFD0000010000020000030000 +T00003C0704000005000002 +E000000 diff --git a/ass1/test.asm b/ass1/test.asm new file mode 100644 index 0000000..6a588f4 --- /dev/null +++ b/ass1/test.asm @@ -0,0 +1,4 @@ +poly START 0 + END poly + +x1 WORD 1 diff --git a/ass1/test.log b/ass1/test.log new file mode 100644 index 0000000..73e0a7b --- /dev/null +++ b/ass1/test.log @@ -0,0 +1,13 @@ +***** Section ***** +Stats: size=3 blocks=3 symbols=2 literals=0 relocations=0 +Blocks + name start size #ins #dir #sto + 00000 00003 0 3 0 +Symbols + name hex dec scope kind type description + poly 000000 0 exported relative code label + x1 000000 0 local relative data label +Literals + label definition +Relocations + address length flag symbol diff --git a/ass1/test.lst b/ass1/test.lst new file mode 100644 index 0000000..ad6bbb8 --- /dev/null +++ b/ass1/test.lst @@ -0,0 +1,4 @@ +00000 poly START 0 +00000 END poly + +00000 000001 x1 WORD 1 diff --git a/ass1/test.obj b/ass1/test.obj new file mode 100644 index 0000000..bbd9486 --- /dev/null +++ b/ass1/test.obj @@ -0,0 +1,3 @@ +Hpoly 000000000003 +T00000003000001 +E000000 diff --git a/ass2/SICocaml/izvajalnik.cmi b/ass2/SICocaml/izvajalnik.cmi index 9627cf131c383f819a1e46aa49b3bae3fd72aa25..792e3f711fa27e1603a3234fc4ed29b0bd28cbee 100644 GIT binary patch delta 698 zcmXBKT}V@57zgm@f6jZ{TrNAFg)Ql#i9(n;^`eZ5t(c_E&rF-p#~DR7KPoJZ5N2b24YE%egJe06cucvR4lgO z(Sx8kXhg7lsnOVqN3Q}UKx2ZHNZscJ@RU@8CP5Dc+avYF=S#Bsa-YxdTb;*(`S+7a zreJ$(Ku5ag7;G$qHQa!vtDbkyO1z<_AZmIXYRq^VF zfgivx!3L!M@G0vz1jP>}AlQghCI7B8>&KyPg1T9-M^Z(+Ne${I)IO+J1$!wK=QC=9 z9)|iB>N~-fq`q)ByP&s#^@9xv_EYKxA7k}dXP~`+CWHniInPzCKC1_|qp*do+ASI3 zr?f^R0Q+6oA6WG^lAhsjwChGK99!ThwEAk2-pSSN`!jL)lERYd)7EkYRgiy@u63NNgkG~gp wPVW92{WL#5zO~{~ml-kJI!?Eim)`V7ZXf&CH!)YZ__fWw-X72AsWlV-0a<3j&Hw-a delta 663 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 delta 3141 zcmd5;ZBSI_6@H(+_wK@eUf2(oPk~)N1Y`J$iK#jmkV1sQ2pNnL2?{AhL@k6+XOb1G z1{34#dP!qy)y*`M*cPn;(^{IEwYBl18f{{1IwduBG}S>Tb%se3(~_R|y}KQq{_LOr zICGw7?{m(3-uFG{?j2n5+=}#ywl&?wbLY;jFDfl!%sbS?7~8Hewu-z(3#raGi&SZ0 zE*SftOdFJz&*vFVP~P{*J|vqUyG-^e*-f%3vaiStq>Cq0$=qZqWLaa$a)m*=A*--y zm*v#4OzRly)pB33lyINe8i7 z8}iP;fVSV;;FOVb5IIL9vH{TXXPPB>!Woa;ZOGjnkrx3vKB3)C-se=2_iN;R5|R4> z9e=Kkr1Uz!gzsbcZbsx?U;_IKwO~QgSWT)MZZ-}7NAOQZ6pGPFj!ElHt9Knk>I716 z&;uWsAZZVdT}(@W>jcs!k#3?V8^Cm8)xJv4cb!Ih2humugKc0s8Pe|0XkPFaWF{c< z9(wQ-FrAc?mqY0ehl9aUe{E$|=^=VJ3U&#ZWyq{2G8Q9^+L??wfh)-T7qYzc;3Sw% z(kO*d4u?Z>3yhiEx57A&`;{;*<-P;PKJGhV42q?48k;Jr%lKNC!2X7;?;vXjkxybo z<0)U$t7>ej63S~}*AU2h30XYuI%k|5=F%fP`!g_J;C>^Ff9L*tFj=|Z3R6D!+hD5X zemhK$N2_?`A+ckF1a=M?#mK0OC(spJf#WhDF#Di2I=c zVZ@0m*n)WSbY3|NEA?hF>;VhH6@hDlvh9tL%T!G~-;EqXJnbPQ55p{r(A%n|NK zVV>arEtu&jc%8MC71iR@&w{;yq)*{B&|2@sh>7a7P#4`X9)^oxf&K8t!|NyMAHj5z z&!wXMPs1YG|12y^`D*83p)Lx^AHbrwzrVJjk@vJ=66^rH@56hO$c-4e#WRVzFTo<} z{wpk^?yIm+-61(}4OSNildu-)8;MPnM7?|n$=^iss)!;{FYBa}a#}0(jYKC(qF#Oz z$xkAA3n{6Wb+U~sdEE*ath{gq60B4?0VAv<1Of`Z@~kJtPgYp32;hK?+KL})V|1>h zJg{Bx7~#pL74l;wk5;fz`6P|bl~e@w3OqC6sUTr-j8t)9zDVweO|M?e(hO3~1N#9y z)$pt&GCxK-c*xTK43o47Y#b^3kV0=zsVYiRjaCR!2nqu*z z6#qz!jPv+iBJ37yVF9LKJ0vm|!X8J7Xqe_W*TZoZ4jM#hH4|7()^_LY33!Ea0CwIm ziZlv4@0h#Z9wo3Jq2FW$_6yv{!9K;k1r9p9kZgyejQa#Qnz(nt(Z_uf9K+nFz;RgY zC%dYIdQCdT0!WxfVlrXR=_pC1jW|wnc`h7R=-BcK2a#Bb#1N^d(RK1uuKI#hiu5{E zS%9aYy0ol3_k3MK6DnPe>03#!`h{!|>MQ{^L*-jkq<=zf7vLz=0j)kKS9>MT>1>7V z8QAE(C`~gR|5AG=Z?PC-MY;|(DDJeFb|R;+F4!Y**a)XaG4Cl=KmSRnZ;J)Sp`Q7# z8J)*y?j%r*1e!N~DGAjgwXeFSp4U{)I$&P_ z`=f*xMsW*eO=uA^|F`Ow)Nx%6djj?qux}vza1=kwb?fwWje5Ez?Ax$!gnc*38l!k` zdHEtFY}R#6x^6k^ggp%VuSnMt#YcHM(VX%cBvKEA6nPz-;u_>$ILo#EnZ7_XtovX+ zOmRI-$G@jIXOobd;iS4LZWEjX0&IaZD8LY$`vrIbE^2eq?0`#jF}=!No#K~axHby# zGTd}r!B@+}uPzP;M@zeU`rEp@+B4hQwYq}%Bz_<-JqBqjq=N*%ufyZo0|ovv+9&0H z8t(0PB* Bytes.set state.memory (start + i) byte) bytes + +(* Parse a T record line like: TAAAAAALL[BYTECODES...] *) +let parse_text_record line = + (* Skip leading 'T' *) + let line = String.sub line 1 (String.length line - 1) in + if String.length line < 8 then failwith "T record too short"; + let start_str = String.sub line 0 6 in (*pridobi stolpce 2-7*) + let len_str = String.sub line 6 2 in (*pridobi stolpce 8-9*) + let start_addr = int_of_hex start_str in (*izračunaj star addr*) + let _ = int_of_hex len_str in (*izračunaj dolžino -> v bistvu je nikjer ne rabimo*) + let byte_str = String.sub line 8 (String.length line - 8) in (*pridobi stolpce 10-*) + (* Split the string into pairs of hex digits *) + let bytes = + let rec aux i acc = + if i >= String.length byte_str then List.rev acc (*ko si na koncu še obrni listo, ker si dodajal na začetek *) + else + let hex_pair = String.sub byte_str i 2 in (*pridobi par črk*) + aux (i + 2) (char_of_hex hex_pair :: acc) (*dodaj na začetek nov par*) + in + aux 0 [] + in + (start_addr, bytes) + +(* Load a SIC/XE object file into memory *) +let load_object_file (state : Processor.state) (filename : string) : unit = + let ic = open_in filename in + try + while true do + let line = input_line ic in + match line.[0] with + | 'T' -> + let addr, bytes = parse_text_record line in + write_bytes state addr bytes + | 'H' -> () (* header: can parse start addr/length if needed *) + | 'E' -> () (* end: can parse entry point if needed *) + | _ -> () + done + with + | End_of_file -> close_in ic diff --git a/ass2/SICocaml/sicxeDune/bin/main.ml b/ass2/SICocaml/sicxeDune/bin/main.ml index d3231ef..e6e4c5e 100644 --- a/ass2/SICocaml/sicxeDune/bin/main.ml +++ b/ass2/SICocaml/sicxeDune/bin/main.ml @@ -1,37 +1,19 @@ (* test_execute.ml *) -open Processor (* assuming your state, regs, and execute are defined here *) +let regs = Processor.{a = 0; x = 0; l = 0; b = 0; s = 0; t = 0; f = 0.0; pc = 0; sw = 0} +let memSize = 1 lsl 20 (*2^20*) +let memory = Bytes.make memSize '\x00' (*mutbale kos pomnilnika velikosti memSize*) +let state = Processor.{regs; memory} (* Test function *) -let test_execute () = - (* Create a dummy state *) - let mem_size = 1024 in - let memory = Bytes.make mem_size '\000' in - let regs = { - a = 0; b = 0; x = 0; l = 0; s = 0; t = 0; f = 0.0; - pc = 0; sw = 0 - } in - let state = { memory; regs } in +let test_runner () = + let khz = 0.001 in + Processor.print_memory state 50; + Loader.load_object_file state "/mnt/c/Programiranje/SPO/ass1/horner.obj"; + Processor.print_memory state 50; + Printf.printf "\n\n---Starting execution!---\n\n"; + Pogajalnik.run state khz - (* Example: Write a LDA instruction at address 0*) - Processor.write_instruction3 state 0 '\x01' '\x00' '\x23'; - - (* Write the operand value at 0x010 *) - Processor.writeMemAddr state 0x010 0x123456; - - (* Set PC to 0 *) - state.regs.pc <- 0; - - Printf.printf "Before execution:\n"; - Processor.print_regs state; - Processor.print_memory state 15; - - (* Execute instruction *) - Izvajalnik.execute state; - - Printf.printf "After execution:\n"; - Processor.print_regs state; - Processor.print_memory state 15 (* Run the test *) -let () = test_execute () +let () = test_runner () \ No newline at end of file diff --git a/ass2/SICocaml/sicxeDune/lib/dune b/ass2/SICocaml/sicxeDune/lib/dune index 2f1c957..039bb16 100644 --- a/ass2/SICocaml/sicxeDune/lib/dune +++ b/ass2/SICocaml/sicxeDune/lib/dune @@ -1,3 +1,4 @@ (library (name sicxeDune) - (wrapped false)) + (wrapped false) + (libraries unix)) diff --git a/ass2/SICocaml/sicxeDune/lib/izvajalnik.ml b/ass2/SICocaml/sicxeDune/lib/izvajalnik.ml index 1ff702c..afef4c1 100644 --- a/ass2/SICocaml/sicxeDune/lib/izvajalnik.ml +++ b/ass2/SICocaml/sicxeDune/lib/izvajalnik.ml @@ -1,4 +1,5 @@ -open OpcodeTable +open OpcodeTable +open Processor type nixbpe = { n : int; @@ -12,14 +13,6 @@ type nixbpe = { let string_of_nixbpe nixbpe = Printf.sprintf "n=%d,i=%d,x=%d,b=%d,p=%d,e=%d" nixbpe.n nixbpe.i nixbpe.x nixbpe.b nixbpe.p nixbpe.e - -(*kreiramo začetno stanje -> TODO prestavi v main*) -let regs = Processor.{a = 0; x = 0; l = 0; b = 0; s = 0; t = 0; f = 0.0; pc = 0; sw = 0} -let memSize = 1 lsl 20 (*2^20*) -let memory = Bytes.make memSize '\x00' (*mutbale kos pomnilnika velikosti memSize*) -let state = Processor.{regs; memory} - - (*----Funkcije izvajalnika----*) (*TODO - brali bomo vedno relativno od začetka instrukcije, PC bomo na koncu ukaza povečali za pravo velikost!*) @@ -56,7 +49,10 @@ let readDisp (state : Processor.state) : int = let byte2 = Char.code (Processor.readMem state 1) in let byte3 = Char.code (Processor.readMem state 2) in let disp_high = byte2 land 0x0F in - let disp = (disp_high lsl 8) lor byte3 in + let disp_low = byte3 in + let disp = (disp_high lsl 8) lor disp_low in + let hex_string = Printf.sprintf "%02X%02X" disp_high disp_low in + Printf.printf "[Izvajalnik/readDisp]prebral disp: 0x%s = 0x%04X = %d\n" hex_string disp disp; disp (*dobi address iz tip ukaza 4*) @@ -72,13 +68,31 @@ let readAddress (state : Processor.state) : int = address (*pridobi operand*) -let getOperand (state : Processor.state) (nixbpe : nixbpe) (disp : int) : int = +let getOperandF3 (state : Processor.state) (nixbpe : nixbpe) (disp : int) : int = let ea = if nixbpe.b = 1 && nixbpe.p = 0 then state.regs.b + disp (*B relativno*) - else if nixbpe.p = 1 && nixbpe.b = 0 then state.regs.pc + disp (*PC relativno*) + else if nixbpe.p = 1 && nixbpe.b = 0 then state.regs.pc + disp + 3(*PC relativno, ker PC povečamo šele po klicu te funkcije moramo tu +3*) else disp (*direktno*) in let ea = if nixbpe.x = 1 then ea + state.regs.x else ea in (*+ (X) po potrebi*) + Printf.printf "[Izvajalnik/getOperand]effective address: 0x%06X = %d\n" ea ea; + (*pridobi operand*) + let value = + if nixbpe.n = 1 && nixbpe.i = 1 then Processor.readMemAddr state ea (*direktno*) + else if nixbpe.n = 0 && nixbpe.i = 1 then disp (* immediate value *) + else if nixbpe.n = 1 && nixbpe.i = 0 then Processor.readMemAddr state (Processor.readMemAddr state ea) (* indirect *) + else failwith "Invalid addressing mode" + in + value + +let getOperandF4 (state : Processor.state) (nixbpe : nixbpe) (disp : int) : int = + let ea = + if nixbpe.b = 1 && nixbpe.p = 0 then state.regs.b + disp (*B relativno*) + else if nixbpe.p = 1 && nixbpe.b = 0 then state.regs.pc + disp + 4(*PC relativno, ker PC povečamo šele po klicu te funkcije moramo tu +4*) + else disp (*direktno*) + in + let ea = if nixbpe.x = 1 then ea + state.regs.x else ea in (*+ (X) po potrebi*) + Printf.printf "[Izvajalnik/getOperand]effective address: 0x%06X = %d\n" ea ea; (*pridobi operand*) let value = if nixbpe.n = 1 && nixbpe.i = 1 then Processor.readMemAddr state ea (*direktno*) @@ -133,7 +147,7 @@ let executeFormat2 (state: Processor.state) (mnemonic : OpcodeTable.mnemonic) : (*execute Format 3*) let executeFormat3 (state : Processor.state) (nixbpe : nixbpe) (mnemonic: OpcodeTable.mnemonic): unit = let disp = readDisp state in - let operand = getOperand state nixbpe disp in + let operand = getOperandF3 state nixbpe disp in (*debugging*) Printf.printf "[Izvajalnik/executeFormat3] Mnemonic: %s, nixbpe: %s, operand: %d = 0x%02X\n" (string_of_mnemonic mnemonic) (string_of_nixbpe nixbpe) operand operand; @@ -188,12 +202,12 @@ let executeFormat3 (state : Processor.state) (nixbpe : nixbpe) (mnemonic: Opcode let executeFormat4 (state : Processor.state) (nixbpe : nixbpe) (mnemonic: OpcodeTable.mnemonic): unit = let address = readAddress state in - let operand = getOperand state nixbpe address in + let operand = getOperandF4 state nixbpe address in (*debugging*) Printf.printf "[Izvajalnik/executeFormat4] Mnemonic: %s, nixbpe: %s, operand: %d = 0x%02X\n" (string_of_mnemonic mnemonic) (string_of_nixbpe nixbpe) operand operand; - Processor.pcIncrement state 3; + Processor.pcIncrement state 4; match mnemonic with | ADD -> IzvajalnikF4.add state operand | ADDF -> notImplemented "ADDF3" diff --git a/ass2/SICocaml/sicxeDune/lib/loader.ml b/ass2/SICocaml/sicxeDune/lib/loader.ml new file mode 100644 index 0000000..0f67c8a --- /dev/null +++ b/ass2/SICocaml/sicxeDune/lib/loader.ml @@ -0,0 +1,49 @@ +open Processor +(* Convert hex string to int *) +let int_of_hex s = int_of_string ("0x" ^ s) + +(* Convert two hex digits to a char *) +let char_of_hex s = Char.chr (int_of_hex s) + +(* Write a list of bytes (chars) to memory at a given start address *) +let write_bytes state start bytes = + List.iteri (fun i byte -> Bytes.set state.memory (start + i) byte) bytes + +(* Parse a T record line like: TAAAAAALL[BYTECODES...] *) +let parse_text_record line = + (* Skip leading 'T' *) + let line = String.sub line 1 (String.length line - 1) in + if String.length line < 8 then failwith "T record too short"; + let start_str = String.sub line 0 6 in (*pridobi stolpce 2-7*) + let len_str = String.sub line 6 2 in (*pridobi stolpce 8-9*) + let start_addr = int_of_hex start_str in (*izračunaj star addr*) + let _ = int_of_hex len_str in (*izračunaj dolžino -> v bistvu je nikjer ne rabimo*) + let byte_str = String.sub line 8 (String.length line - 8) in (*pridobi stolpce 10-*) + (* Split the string into pairs of hex digits *) + let bytes = + let rec aux i acc = + if i >= String.length byte_str then List.rev acc (*ko si na koncu še obrni listo, ker si dodajal na začetek *) + else + let hex_pair = String.sub byte_str i 2 in (*pridobi par črk*) + aux (i + 2) (char_of_hex hex_pair :: acc) (*dodaj na začetek nov par*) + in + aux 0 [] + in + (start_addr, bytes) + +(* Load a SIC/XE object file into memory *) +let load_object_file (state : Processor.state) (filename : string) : unit = + let ic = open_in filename in + try + while true do + let line = input_line ic in + match line.[0] with + | 'T' -> + let addr, bytes = parse_text_record line in + write_bytes state addr bytes + | 'H' -> () (* header: can parse start addr/length if needed *) + | 'E' -> () (* end: can parse entry point if needed *) + | _ -> () + done + with + | End_of_file -> close_in ic diff --git a/ass2/SICocaml/sicxeDune/lib/pogajalnik.ml b/ass2/SICocaml/sicxeDune/lib/pogajalnik.ml new file mode 100644 index 0000000..d7c493d --- /dev/null +++ b/ass2/SICocaml/sicxeDune/lib/pogajalnik.ml @@ -0,0 +1,30 @@ +(*pogajalnik bo izvajal exekucijo eno za drugo*) + +let run (state : Processor.state) (khz : float) : unit = + let perioda_sekunde = 1.0 /. (khz *. 1000.0) in + let rec loop state last_pc count= + + (*izvedi ukaz*) + Izvajalnik.execute state; + + (*printni stanje*) + Printf.printf "After execution:\n"; + Processor.print_regs state; + Processor.print_memory state 50; + flush stdout; + + (*spi*) + Unix.sleepf perioda_sekunde;(*mogoče spremeni na time of day approach , da se izogneš driftu*) + + (*preveri ali je PC obtičan na istem mestu*) + let current_pc = state.regs.pc in + let count, last_pc = + if current_pc = last_pc then (count + 1, last_pc) + else (1, current_pc) + in + (*Nehaj rekurzijo če je PC 5x na istem mestu*) + if count >= 5 then + Printf.printf "PC stuck at 0x%X 5 times. Ending loop.\n" current_pc + else + loop state last_pc count + in loop state state.regs.pc 0 \ No newline at end of file