Don't like ads? PRO users don't see any ads ;-)
Guest

DCPU udated specs

By: a guest on May 8th, 2012  |  syntax: None  |  size: 6.45 KB  |  hits: 25  |  expires: Never
download  |  raw  |  embed  |  report abuse  |  print
Text below is selected. Please press Ctrl+C to copy to your clipboard. (⌘+C on Mac)
  1. DCPU-16 Specification
  2. Copyright 2012 Mojang
  3. Version 1.1 (Check 0x10c.com for updated versions)
  4.  
  5. * 16 bit unsigned words
  6. * 0x10000 words of ram
  7. * 8 registers (A, B, C, X, Y, Z, I, J)
  8. * program counter (PC)
  9. * stack pointer (SP)
  10. * overflow (O)
  11.  
  12. In this document, anything within [brackets] is shorthand for "the value of the RAM at the location of the value inside the brackets".
  13. For example, SP means stack pointer, but [SP] means the value of the RAM at the location the stack pointer is pointing at.
  14.  
  15. Whenever the CPU needs to read a word, it reads [PC], then increases PC by one. Shorthand for this is [PC++].
  16. In some cases, the CPU will modify a value before reading it, in this case the shorthand is [++PC].
  17.  
  18. Instructions are 1-3 words long and are fully defined by the first word.
  19. In a basic instruction, the lower four bits of the first word of the instruction are the opcode,
  20. and the remaining twelve bits are split into two six bit values, called a and b.
  21. a is always handled by the processor before b, and is the lower six bits.
  22. In bits (with the least significant being last), a basic instruction has the format: bbbbbbaaaaaaoooo
  23.  
  24.  
  25.  
  26. Values: (6 bits)
  27.     0x00-0x07: register (A, B, C, X, Y, Z, I or J, in that order)
  28.     0x08-0x0f: [register]
  29.     0x10-0x17: [next word + register]
  30.          0x18: POP / [SP++]
  31.          0x19: PEEK / [SP]
  32.          0x1a: PUSH / [--SP]
  33.          0x1b: SP
  34.          0x1c: PC
  35.          0x1d: O
  36.          0x1e: [next word]
  37.          0x1f: next word (literal)
  38.     0x20-0x3f: literal value 0x00-0x1f (literal)
  39.    
  40. * "next word" really means "[PC++]". These increase the word length of the instruction by 1.
  41. * If any instruction tries to assign a literal value, the assignment fails silently. Other than that, the instruction behaves as normal.
  42. * All values that read a word (0x10-0x17, 0x1e, and 0x1f) take 1 cycle to look up. The rest take 0 cycles.
  43. * By using 0x18, 0x19, 0x1a as POP, PEEK and PUSH, there's a reverse stack starting at memory location 0xffff. Example: "SET PUSH, 10", "SET X, POP"
  44.  
  45.  
  46.  
  47. Basic opcodes: (4 bits)
  48.     0x0: non-basic instruction - see below
  49.     0x1: SET a, b - sets a to b
  50.     0x2: ADD a, b - sets a to a+b, sets O to 0x0001 if there's an overflow, 0x0 otherwise
  51.     0x3: SUB a, b - sets a to a-b, sets O to 0xffff if there's an underflow, 0x0 otherwise
  52.     0x4: MUL a, b - sets a to a*b, sets O to ((a*b)>>16)&0xffff
  53.     0x5: DIV a, b - sets a to a/b, sets O to ((a<<16)/b)&0xffff. if b==0, sets a and O to 0 instead.
  54.     0x6: MOD a, b - sets a to a%b. if b==0, sets a to 0 instead.
  55.     0x7: SHL a, b - sets a to a<<b, sets O to ((a<<b)>>16)&0xffff
  56.     0x8: SHR a, b - sets a to a>>b, sets O to ((a<<16)>>b)&0xffff
  57.     0x9: AND a, b - sets a to a&b
  58.     0xa: BOR a, b - sets a to a|b
  59.     0xb: XOR a, b - sets a to a^b
  60.     0xc: IFE a, b - performs next instruction only if a==b
  61.     0xd: IFN a, b - performs next instruction only if a!=b
  62.     0xe: IFG a, b - performs next instruction only if a>b
  63.     0xf: IFB a, b - performs next instruction only if (a&b)!=0
  64.    
  65. * SET, AND, BOR and XOR take 1 cycle, plus the cost of a and b
  66. * ADD, SUB, MUL, SHR, and SHL take 2 cycles, plus the cost of a and b
  67. * DIV and MOD take 3 cycles, plus the cost of a and b
  68. * IFE, IFN, IFG, IFB take 2 cycles, plus the cost of a and b, plus 1 if the test fails
  69.    
  70.  
  71.    
  72. Non-basic opcodes always have their lower four bits unset, have one value and a six bit opcode.
  73. In binary, they have the format: aaaaaaoooooo0000
  74. The value (a) is in the same six bit format as defined earlier.
  75.  
  76. Non-basic opcodes: (6 bits)
  77.          0x00: reserved for future expansion
  78.          0x01: JSR a - pushes the address of the next instruction to the stack, then sets PC to a
  79.     0x02-0x3f: reserved
  80.    
  81. * JSR takes 2 cycles, plus the cost of a.
  82.  
  83.  
  84.  
  85. FAQ:
  86.  
  87. Q: Why is there no JMP or RET?
  88. A: They're not needed! "SET PC, <target>" is a one-instruction JMP.
  89.    For small relative jumps in a single word, you can even do "ADD PC, <dist>" or "SUB PC, <dist>".
  90.    For RET, simply do "SET PC, POP"
  91.    
  92.  
  93. Q: How does the overflow (O) work?
  94. A: O is set by certain instructions (see above), but never automatically read. You can use its value in instructions, however.
  95.    For example, to do a 32 bit add of 0x12345678 and 0xaabbccdd, do this:
  96.       SET [0x1000], 0x5678    ; low word
  97.       SET [0x1001], 0x1234    ; high word
  98.       ADD [0x1000], 0xccdd    ; add low words, sets O to either 0 or 1 (in this case 1)
  99.       ADD [0x1001], O         ; add O to the high word
  100.       ADD [0x1001], 0xaabb    ; add high words, sets O again (to 0, as 0xaabb+0x1235 is lower than 0x10000)
  101.  
  102. Q: How do I do 32 or 64 bit division using O?
  103. A: This is left as an exercise for the reader.
  104.      
  105. Q: How about a quick example?
  106. A: Sure! Here's some sample assembler, and a memory dump of the compiled code:
  107.  
  108.         ; Try some basic stuff
  109.                       SET A, 0x30              ; 7c01 0030
  110.                       SET [0x1000], 0x20       ; 7de1 1000 0020
  111.                       SUB A, [0x1000]          ; 7803 1000
  112.                       IFN A, 0x10              ; c00d
  113.                          SET PC, crash         ; 7dc1 001a [*]
  114.                      
  115.         ; Do a loopy thing
  116.                       SET I, 10                ; a861
  117.                       SET A, 0x2000            ; 7c01 2000
  118.         :loop         SET [0x2000+I], [A]      ; 2161 2000
  119.                       SUB I, 1                 ; 8463
  120.                       IFN I, 0                 ; 806d
  121.                          SET PC, loop          ; 7dc1 000d [*]
  122.        
  123.         ; Call a subroutine
  124.                       SET X, 0x4               ; 9031
  125.                       JSR testsub              ; 7c10 0018 [*]
  126.                       SET PC, crash            ; 7dc1 001a [*]
  127.        
  128.         :testsub      SHL X, 4                 ; 9037
  129.                       SET PC, POP              ; 61c1
  130.                        
  131.         ; Hang forever. X should now be 0x40 if everything went right.
  132.         :crash        SET PC, crash            ; 7dc1 001a [*]
  133.        
  134.         ; [*]: Note that these can be one word shorter and one cycle faster by using the short form (0x00-0x1f) of literals,
  135.         ;      but my assembler doesn't support short form labels yet.    
  136.  
  137.   Full memory dump:
  138.  
  139.         0000: 7c01 0030 7de1 1000 0020 7803 1000 c00d
  140.         0008: 7dc1 001a a861 7c01 2000 2161 2000 8463
  141.         0010: 806d 7dc1 000d 9031 7c10 0018 7dc1 001a
  142.         0018: 9037 61c1 7dc1 001a 0000 0000 0000 0000