Hi all,
I have de-obfuscated Oscar Toledo's emulator [1].
I started out by running the C pre-processor to expand the '#defines'
then adjusting some formatting.
The whole emulator runs inside a 'for' loop. The initialisation inside
the 'for' opens all the files and loads the 64Kbytes of memory from file C.
The halt instruction (hlt, 0x76), 118) stops the emulator when
encountered so it is used in the 'for' loop exit condition.
The bulk of the work is done in the 3rd clause of the for loop.
We see a succession of ...?...?...?...?... ... ...:...:...:...:...
K&R 2nd edition has this to say about the ? operator:
"
expr1 ? expr2 : expr3
the expression expr1 is evaluated first. If it is non-zero (true), then
the expression expr2 is evaluated, and it is the value of the
conditional expression. Otherwise expr3 is evaluated, and that is the
value Only one of expr2 and expr3 is evaluated.
"
The way Oscar Toledo did it is: if the 8080 instruction he got from the
memory array makes 'expr1' evaluate to zero then the program flows sends
it to evaluate 'expr3'.
Once I realised that, I started matching the first '?' to the last ':'
and writing those clue comments "/*001*/" up and down the file and
continued from there until I had all of them done. Next was the
formatting related to all those commas. To help me identify which 8080
opcode was being done I looked at a 8080 manual where one of the pages
is a summary of all of them. Lots of decimal to binary to hex
conversions later and I had all opcodes identified.
As I went along I also added comments.
After all that, one comes to the conclusion that the emulator is really
simple and easy to understand and just really nice to study.
Some of the things I really like:
- all in one file
- small variable names
- no unnecessary functions and function calls
[1]
https://nanochess.org/emulator.html
(note: my newsgroup client wraps lines at 72 columns. Some editing may
be required if you want to use the code below.)
#include <stdio.h>
unsigned char o[10],l[78114],*c=l,*k=l+64506; // 0xFBFA
e,V,v,u,x,y,z,Z;
main(r,U)char**U;
{
for(
v =fopen(((u =fopen(((e =fopen(((r-2?0:(V
=fopen((1[U]),"rb+")),"C")),"rb+")
,system("stty raw -echo min 0")
,fread(l,78114,1,e)
,fclose((e)),
"B")),"rb+"),"A")),"rb+")
// At the end of initialisation
// v file pointer to file A
// u file pointer to file B
// V file pointer to file in the command line
// array l contains contents of File C (why 78114?)
;
118-(x=*c++) // 0x76 stop instruction, exits for loop
// the x variable contains the current 8080 opcode being evaluated
// the c variable is the current program counter
/*
o[0] = B register o[1] = C register
o[2] = D register o[3] = E register
o[4] = H register o[5] = L register
o[6] = Flags o[7] = A or accumulator
O[8] = SP high byte o[9] = SP low byte
DB 00 Reads key pressed status
DB 01 Reads key
DB 02 Reads byte from file (Carry=EOF)
D3 xx Writes byte from acc. to console
ED ED 02 Reads sector (128 bytes)
ED ED 03 Writes sector (128 bytes)
*/
;
/*001*/ (y=x/8%8,z=(x&199)-4 )? // 4 INR increment register
// y=0 -> B
// y=1 -> C
// y=2 -> D
// y=3 -> E
// y=4 -> H
// y=5 -> L
// y=6 -> MEMORY POINTED BY HL
// y=7 -> A
/*002*/ (z-= 1 )? // 5 DCR decrement register pair
/*003*/ (z-= 1 )? // 6 MVI move immediate
/*004*/ (z-= 186 )? // 192 RETURN ON FLAG FAMILY
// y=0 -> RNZ
// y=1 -> RZ
// y=2 -> RNC
// y=3 -> RC
// y=4 -> RPO
// y=5 -> RPE
// y=6 -> RP
// y=7 -> RM
/*005*/ (z-= 2 )? // 194 JUMP ON FLAG FAMILY
// y=0 -> RNZ
// y=1 -> RZ
// y=2 -> RNC
// y=3 -> RC
// y=4 -> RPO
// y=5 -> RPE
// y=6 -> RP
// y=7 -> RM
/*006*/ (z-= 2 )? // 196 CALL ON FLAG FAMILY
// y=0 -> RNZ
// y=1 -> RZ
// y=2 -> RNC
// y=3 -> RC
// y=4 -> RPO
// y=5 -> RPE
// y=6 -> RP
// y=7 -> RM
/*007*/ (z-= 3 )? // 199 RST Restart
// y=0 -> JUMP TO ADDR 0
// y=1 -> JUMP TO ADDR 8
// y=2 -> JUMP TO ADDR 16
// y=3 -> JUMP TO ADDR 24
// y=4 -> JUMP TO ADDR 32
// y=5 -> JUMP TO ADDR 40
// y=6 -> JUMP TO ADDR 48
// y=7 -> JUMP TO ADDR 56
/*008*/ (z-= 0,r=(y>5)*2+y,z=(x&207)-1 )? // 1 LXI load register pair
immediate
// y=0 -> BC
// y=2 -> DE
// y=4 -> HL
// y=6 -> SP
/*009*/ (z-= 2 )? // 3 INX increment register pair
// y=0 -> BC
// y=2 -> DE
// y=4 -> HL
// y=6 -> SP
/*010*/ (z-= 6 )? // 9 DAD add register pair to HL
// y=1 -> BC
// y=3 -> DE
// y=5 -> HL
// y=7 -> SP
/*011*/ (z-= 2 )? // 11 DCX increment register pair
// y=0 -> BC
// y=2 -> DE
// y=4 -> HL
// y=6 -> SP
/*012*/ (z-= 182 )? // 193 POP register pair from STACK
// y=0 -> BC
// y=2 -> DE
// y=4 -> HL
// y=6 -> A and Flags
/*013*/ (z-= 4)? // 197 PUSH register pair to STACK
// y=0 -> BC
// y=2 -> DE
// y=4 -> HL
// y=6 -> A and Flags
/*014*/ x/8!=16+0&198+0*8!=x? // 128 ADD r add register to A or 198
ADI add immediate to A
/*015*/ x/8!=16+1&198+1*8!=x? // 136 ADC r add register to A with
carry 206 ACI add immediate to A with carry
/*016*/ x/8!=16+2&198+2*8!=x? // 144 SUB r subtract register 214 SUI
subract immediate from A
/*017*/ x/8!=16+3&198+3*8!=x? // 152 SBB r subtract register with
borrow 222 SUB subract immediate from A with borrow
/*018*/ x/8!=16+4&198+4*8!=x? // 160 ANA r and register with A 230 ANI
and immediate with A
/*019*/ x/8!=16+5&198+5*8!=x? // 168 XRA r exclusive or register with
A 238 XRI exclusive or immediate with A
/*020*/ x/8!=16+6&198+6*8!=x? // 176 ORA r or register with A 246 ORI
or immediate with A
/*021*/ x/8!=16+7&198+7*8!=x? // 184 CMP r compare register with A 254
CPI compare immediate with A
/*022*/ (z=x-2 )? // 2 STAX B store A indirect
/*023*/ (z-= 5 )? // 7 RLC rotate A left
/*024*/ (z-= 3 )? // 10 LDAX B load A indirect
/*025*/ (z-= 5 )? // 15 RRC rotate A right
/*026*/ (z-= 3 )? // 18 STAX D store A indirect
/*027*/ (z-= 5 )? // 23 RAL rotate A left through carry
/*028*/ (z-= 3 )? // 26 LDAX D load A indirect
/*029*/ (z-= 5 )? // 31 RAR rotate A right through carry
/*030*/ (z-= 3 )? // 34 SHLD store H and L direct
/*031*/ (z-= 5 )? // 39 DAA decimal adjust A
/*032*/ (z-= 3 )? // 42 LHLD load H and L direct
/*033*/ (z-= 5 )? // 47 CMA complement A
/*034*/ (z-= 3 )? // 50 STA store A direct
/*035*/ (z-= 5 )? // 55 STC set carry
/*036*/ (z-= 3 )? // 58 LDA load A direct
/*037*/ (z-= 5 )? // 63 CMC complement carry
/*038*/ (z-= 3 +129 )? // 195 JMP jump unconditional
/*039*/ (z-= 6 )? // 201 RET return
/*040*/ (z-= 4 )? // 205 CALL Call unconditional
/*041*/ (z-= 6 )? // 211 0xD3 OUT Output
/*042*/ (z-= 8 )? // 219 0xDB IN Input
/*043*/ (z-= 8 )? // 227 XTHL exchange top of stack with HL /*044*/ (z-= 6 )? // 233 PCHL HL to program counter
/*045*/ (z-= 2 )? // 235 XCHG exchange HL with DE
/*046*/ (z-= 2 )? // 237 0xED - read or write sectors to disk /*047*/ (z-= 12)? // 249 SPHL HL to stack pointer
/*048*/ x/64-1? // 64 MOV r1,r2 MOV M,r MOV r,M
/*NO */ ((0 )):
/*048*/ (( // 64 MOV r1,r2 MOV M,r MOV r,M
*((7&y)-6?&o[y&7]:&l[o[5]+256*o[5 -1]])=*((7&x)-6?&o[x&7]:&l[o[5]+256*o[5 -1]])
)):
/*047*/ (( // 249 SPHL HL to stack pointer
9[o]=*((7&5)-6?&o[5&7]:&l[o[5]+256*o[5 -1]])
,8[o]=*((7&4)-6?&o[4&7]:&l[o[5]+256*o[5 -1]])
)):
/*046*/ (( // 237 0xED - read or write sectors to disk
237==*c++? // 2nd also 0xED? Skip it
((int (*)())(2-*c++?fwrite:fread)) //if 3rd byte is 2
read, otherwise write
(l+*k+1[k]*256,128,1,(fseek(y=5[k]-1?u:v // 0=A:, 1=B:
,((3[k]|4[k]<<8)<<7|2[k])<<7
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=0)
,y
)
)
:0
)):
// 0[k] = FBFA - Low source/target address
// 1[k] = FBFB - High source/target
address
// 2[k] = FBFC - Sector (0-127)
// 3[k] = FBFD - Cylinder (low byte)
// 4[k] = FBFE - Cylinder (high byte)
// 5[k] = FBFF - Drive (1/2)
/*045*/ (( // 235 XCHG exchange HL with DE
y=*((7&5)-6?&o[5&7]:&l[o[5]+256*o[5 -1]])
,z=*((7&4)-6?&o[4&7]:&l[o[5]+256*o[5 -1]])
,*((7&5)-6?&o[5&7]:&l[o[5]+256*o[5 -1]])=*((7&3)-6?&o[3&7]:&l[o[5]+256*o[5 -1]])
,*((7&4)-6?&o[4&7]:&l[o[5]+256*o[5 -1]])=*((7&2)-6?&o[2&7]:&l[o[5]+256*o[5 -1]])
,*((7&3)-6?&o[3&7]:&l[o[5]+256*o[5 -1]])=y
,*((7&2)-6?&o[2&7]:&l[o[5]+256*o[5 -1]])=z
)):
/*044*/ (( // 233 PCHL HL to program counter
c=l+o[5]+256*o[5 -1]
)):
/*043*/ (( // 227 XTHL exchange top of stack with HL
y=l[x=o[9]+256*o[9 -1]]
,z=l[++x]
,x[l]=*((7&4)-6?&o[4&7]:&l[o[5]+256*o[5 -1]])
,l[--x]=*((7&5)-6?&o[5&7]:&l[o[5]+256*o[5 -1]])
,*((7&5)-6?&o[5&7]:&l[o[5]+256*o[5 -1]])=y
,*((7&4)-6?&o[4&7]:&l[o[5]+256*o[5 -1]])=z
)):
/*042*/ (( // 219 IN Input
2-*c?Z||read(0,&Z,1)
,1&*c++?*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=Z,Z=0
:(*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=!!Z)
:(c++
,*((7&7)-6?&o[7&7]
:&l[o[5]+256*o[5 -1]]
)
=r=V?fgetc(V):-1
,6[o]=6[o]&~1|r<0
)
)):
/*041*/ (( // 211 OUT Output
++c,write(1,&7[o],1)
)):
/*040*/ (( // 205 CALL Call unconditional
z=c+2-l
,254>(9[o]-=2)||--8[o],l[o[9]+256*o[9 -1]]=z
,l[1+o[9]+256*o[9 -1]]=z>>8
,c=l+(c+=2,0[c-2]|1[c-2]<<8)
)):
/*039*/ (( // 201 RET return
z=l[o[9]+256*o[9 -1]]|l[o[9]+256*o[9
-1]+1]<<8,1<(9[o]+=2)||++8[o]
,c=l+z
)):
/*038*/ (( // 195 JMP jump unconditional
c=l+(c+=2,0[c-2]|1[c-2]<<8)
)):
/*037*/ (( // 63 CMC complement carry
6[o]^=1
)):
/*036*/ (( // 58 LDA load A direct
*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5
-1]])=(c+=2,0[c-2]|1[c-2]<<8)[l]
)):
/*035*/ (( // 55 STC set carry
6[o]|=1
)):
/*034*/ (( // 50 STA store A direct
(c+=2,0[c-2]|1[c-2]<<8)[l]=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5
-1]])
)):
/*033*/ (( // 47 CMA complement A
*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=~*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])
)):
/*032*/ (( // 42 LHLD load H and L direct
*((7&5)-6?&o[5&7]:&l[o[5]+256*o[5 -1]])=l[x=(c+=2,0[c-2]|1[c-2]<<8)]
,*((7&4)-6?&o[4&7]:&l[o[5]+256*o[5 -1]])=l[++x]
)):
/*031*/ (( // 39 DAA decimal adjust A
6[o]|=6[o]&16|9<*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])%16?*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])+=6
,16:0
,z=6[o]|=1&6[o]|*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])>159?*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])+=96
,1:0
,y=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])
,6[o]=6[o]<<8>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
)):
/*030*/ (( // 34 SHLD store H and L direct
l[x=(c+=2,0[c-2]|1[c-2]<<8)]=*((7&5)-6?&o[5&7]:&l[o[5]+256*o[5 -1]])
,l[++x]=*((7&4)-6?&o[4&7]:&l[o[5]+256*o[5 -1]])
)):
/*029*/ (( // 31 RAR rotate A right through carry
x=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])%2
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])/2+6[o]%2*128,6[o]=6[o]&~1|x
)):
/*028*/ (( // 26 LDAX D load A indirect
*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=l[o[3]+256*o[3 -1]]
)):
/*027*/ (( // 23 RAL rotate A left through carry
x=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]]) /128
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])*2+6[o]%2,6[o]=6[o]&~1|x
)):
/*026*/ (( // 18 STAX D store A indirect
l[o[3]+256*o[3 -1]]=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])
)):
/*025*/ (( // 15 RRC rotate A right
6[o]=6[o]&~1|1&*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])/2|*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])<<7
)):
/*024*/ (( // 10 LDAX B load A indirect
*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=l[o[1]+256*o[1 -1]]
)):
/*023*/ (( // 7 RLC rotate A left
6[o]=~1&6[o]|*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])>>7
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])*2|*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])>>7
)):
/*022*/ (( // 2 STAX B store A indirect
l[o[1]+256*o[1 -1]]=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])
)):
/*021*/ (( // 184 CMP r compare register with A 254 CPI compare
immediate with A
x=64&x?*c++:*((7&x)-6?&o[x&7]:&l[o[5]+256*o[5 -1]])
, y =y=(z=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])%16 - x%16 - 0
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])- x - 0
)
,6[o]=y>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
)):
/*020*/ (( // 176 ORA r or register with A 246 ORI or immediate with A
x=64&x?*c++:*((7&x)-6?&o[x&7]:&l[o[5]+256*o[5 -1]])
, z=0
,y=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])|=x
,6[o]=y>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
)):
/*019*/ (( // 168 XRA r exclusive or register with A 238 XRI exclusive
or immediate with A
x=64&x?*c++:*((7&x)-6?&o[x&7]:&l[o[5]+256*o[5 -1]])
, z=0
,y=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])^=x
,6[o]=y>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
)):
/*018*/ (( // 160 ANA r and register with A 230 ANI and immediate with A
x=64&x?*c++:*((7&x)-6?&o[x&7]:&l[o[5]+256*o[5 -1]])
, z=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])*2|2*x
,y=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])&=x
,6[o]=y>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
)):
/*017*/ (( // 152 SBB r subtract register with borrow 222 SUB subract
immediate from A with borrow
x=64&x?*c++:*((7&x)-6?&o[x&7]:&l[o[5]+256*o[5 -1]])
, *((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])
=y=(z=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])%16 - x%16 -
6[o]%2
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])- x - 6[o]%2
)
,6[o]=y>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
)):
/*016*/ (( // 144 SUB r subtract register 214 SUI subract immediate from A
x=64&x?*c++:*((7&x)-6?&o[x&7]:&l[o[5]+256*o[5 -1]])
, *((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])
=y=(z=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])%16 - x%16 - 0
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])- x - 0
)
,6[o]=y>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
)):
/*015*/ (( // 136 ADC r add register to A with carry 206 ACI add
immediate to A with carry
x=64&x?*c++:*((7&x)-6?&o[x&7]:&l[o[5]+256*o[5 -1]])
, *((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])
=y=(z=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])%16 + x%16
+ 6[o]%2
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])+ x + 6[o]%2
)
,6[o]=y>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
)):
/*014*/ (( // 128 ADD r add register to A or 198 ADI add immediate to A
x=64&x?*c++:*((7&x)-6?&o[x&7]:&l[o[5]+256*o[5 -1]])
, *((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])
=y=
(z=*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])%16 + x%16 + 0
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])+ x + 0
)
,6[o]=y>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
)):
/*013*/ (( // PUSH B, PUSH D, PUSH H, PUSH PSW
z=r-8?o[r+1]+256*o[r+1
-1]:6[o]|*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])<<8
,254>(9[o]-=2)||--8[o]
,l[o[9]+256*o[9 -1]]=z
,l[1+o[9]+256*o[9 -1]]=z>>8
)):
/*012*/ (( // POP B, POP D, POP H, POP PSW
z=l[o[9]+256*o[9 -1]]|l[o[9]+256*o[9 -1]+1]<<8
,1<(9[o]+=2)||++8[o]
,r-8?o[r+1]=z,r[o]=z>>8
:( 6[o]=~40&z|2
,*((7&7)-6?&o[7&7]:&l[o[5]+256*o[5 -1]])=z>>8
)
)):
/*011*/ (( // DCX
r[o]--||--o[r-1]
)):
/*010*/ (( // DAD
*((7&5)-6?&o[5&7]:&l[o[5]+256*o[5 -1]]) // L register
=z=*((7&5)-6?&o[5&7]:&l[o[5]+256*o[5 -1]])+r[o]
,*((7&4)-6?&o[4&7]:&l[o[5]+256*o[5 -1]]) //H register
=z=*((7&4)-6?&o[4&7]:&l[o[5]+256*o[5 -1]])+o[r-1]+z/256
,6[o]=~1&6[o]|z>>8 // update carry flag if needed
)):
/*009*/ (( // INX
++o[r+1]||r[o]++
)):
/*008*/ (( //LXI
o[r+1]=*c++
,r[o]=*c++
)):
/*007*/ (( // RST Restart
z=c-l
,254>(9[o]-=2)||--8[o]
,l[o[9]+256*o[9 -1]]=z
,l[1+o[9]+256*o[9 -1]]=z>>8
,c=y*8+l
)):
/*006*/ (( // CALL ON FLAG FAMILY
x=(c+=2,0[c-2]|1[c-2]<<8)
,(y&1?~6[o]:6[o])>>"\6\0\2\7"[y/2]&1?0: //Test flags
( z=c-l
,254>(9[o]-=2)||--8[o] // Update SP
,l[o[9]+256*o[9 -1]]=z // Update STACK with return
address
,l[1+o[9]+256*o[9 -1]]=z>>8 // Update STACK with return
address
,c=l+x // update PC
)
)):
/*005*/ (( // JUMP ON FLAG FAMILY
x=(c+=2,0[c-2]|1[c-2]<<8) // wow!! index 0 and index 1 to
the array of bytes pointed by c-2
,(y&1?~6[o]:6[o])>>"\6\0\2\7"[y/2]&1?0:( c=l+x)
)):
/*004*/ (( // RETURN ON FLAG FAMILY
(y&1?~6[o]:6[o])
>>"\6\0\2\7"[y/2]&1?0: //wow, an array of chars
indexed. This tests each flag
( z=l[o[9]+256*o[9 -1]]|l[o[9]+256*o[9 -1]+1]<<8 // z=
value pointed by the stack pointer
,1<(9[o]+=2)||++8[o] // update SP
,c=l+z // Update PC
)
)):
/*003*/ (( // MVI
*((7&y)-6?&o[y&7]:&l[o[5]+256*o[5 -1]])=*c++
)):
/*002*/ (( // DCR
r=y
,x=0
,*((7&r)-6?&o[r&7]:&l[o[5]+256*o[5 -1]])
=y
=(z=*((7&y)-6?&o[y&7]:&l[o[5]+256*o[5 -1]])%16 - x%16 - 1
,*((7&y)-6?&o[y&7]:&l[o[5]+256*o[5 -1]])- x - 1
)
,6[o]=6[o]<<8>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
)):
/*001*/ (( // INR
r=y
,x=0
,*((7&r)-6?&o[r&7]:&l[o[5]+256*o[5 -1]])
=y
=(z=*((7&y)-6?&o[y&7]:&l[o[5]+256*o[5 -1]])%16 + x%16 + 1
,*((7&y)-6?&o[y&7]:&l[o[5]+256*o[5 -1]])+ x + 1
)
,6[o]=6[o]<<8>>8&1|128&y|!(y&255)*64|16&z|2
,y^=y>>4
,y^=y<<2
,y^=~y>>1
,6[o]|=y&4
))
);
system("stty cooked echo");
fclose(((fclose(((V?fclose((V)):0,u))),v)));
}
--- SoupGate-Win32 v1.05
* Origin: fsxNet Usenet Gateway (21:1/5)