changeset 18:256d24488e3f

assembler now handles EQU, ORG and DB
author james <jb302@eecs.qmul.ac.uk>
date Sat, 22 Feb 2014 20:30:58 +0000
parents 9bbdf7258cd8
children c9fbeb852ff2
files assembler/assembler.py assembler/language.py assembler/language.pyc emulator/a.out emulator/emu.c emulator/iset.c emulator/iset.h tests/full.asm tests/full.bin tests/test.asm tests/test.bin utils/gen_language.ipynb
diffstat 12 files changed, 944 insertions(+), 437 deletions(-) [+]
line wrap: on
line diff
--- a/assembler/assembler.py	Thu Jan 30 17:09:55 2014 +0000
+++ b/assembler/assembler.py	Sat Feb 22 20:30:58 2014 +0000
@@ -20,53 +20,75 @@
     
     asm = []
     label_index = {}
+    equ_index = {}
     pc = 0
     
     # <line> ::= [<statement>] [";"<comment>] <EOL>
     for line in source_code:
+        
+        try:
+            # remove EOL
+            line = line.strip()
+            
+            # remove comments
+            for i in range(len(line)):
+                if line[i] == ';':
+                    line = line[:i]
+                    break
+            
+            line = line.lower()
+            
+            # <statement> ::= [ <label> ":"] <mnemonic> [<arguments>]
+            #                 | <label> ":"
+            #                 | "EOF"
+            statement = line.split()
+            
+            if not statement: continue
+            # deal with org and db
+            elif statement[0] == 'org': 
+                asm.append([statement[0], statement[1:], ('',), ''])
+                pc = string_num(statement[1])
+                continue
+            elif statement[0] == 'db':
+                asm.append([statement[0], statement[1:], ('',), ''])
+                pc = pc + len(statement[1:])
+                continue
 
-        # remove EOL
-        line = line.strip()
+            # store equates
+            if (len(statement) >= 3) and (statement[1] == 'equ'):
+                equ_index[statement[0]] = statement[2]
+                continue
+
+            # if needed update index and remove label 
+            if statement[0][-1:] == ':':
+                label_index[statement[0][:-1]] = pc;
+                del statement[0]
+                
+            if not statement: continue
+            
+            # <statement> ::= <mnemonic> [<arguments>]
+            mnemonic = statement[0]
+            arguments = ''.join(statement[1:]).split(',')
+            
+            # replace equated arguments
+            # because this happens on the first pass
+            # equates must be assigned before they are used
+            i = 0
+            for a in arguments:
+                if a in equ_index:
+                    arguments[i] = equ_index[a]
+                i = i + 1
+
+            symbols, constants = tokenize(arguments)
+            width = iset[mnemonic][symbols][1]
+
+            asm.append([mnemonic, arguments, symbols, constants])
+            pc = pc + width
         
-        # remove comments
-        for i in range(len(line)):
-            if line[i] == ';':
-                line = line[:i]
-                break
-        
-        line = line.lower()
-        
-        # <statement> ::= [ <label> ":"] <mnemonic> [<arguments>]
-        #                 | <label> ":"
-        #                 | "end"
-        # skip empty statements
-        statement = line.split()
-        
-        # skip empty statements
-        if not statement: continue
-        
-        # if needed update index and remove label 
-        label = None
-        if statement[0][-1:] == ':':
-            label_index[statement[0][:-1]] = pc;
-            del statement[0]
-            
-        # return things that return False if empty
-        if not statement:
-            asm.append(['', [], [], ''])
-            continue
-        
-        # <statement> ::= <mnemonic> [<arguments>]
-        mnemonic = statement[0]
-        arguments = ''.join(statement[1:]).split(',')
+        except:
+            print ' ** first pass error **\nline:\n', line
+            raise
 
-        symbols, constants = tokenize(arguments)
-        width = iset[mnemonic][symbols][1]
-
-        asm.append([mnemonic, arguments, symbols, constants])
-        
-        pc = pc + width
-    
     return asm, label_index
 
 # take preprocessed asm and write machine code to binary file
@@ -74,38 +96,57 @@
     pc = 0
 
     for line in asm:
+        f.seek(pc)
         mne, args, sym, const = line
     
-        # skip instructionless lines
-        if not mne: continue
-
-        # replace labels with addresses
-        i = 0
-        for a in args:
-            if a in label_index:
-                args[i] = num_string(label_index[a])
-                val = tokenize([args[i]])[1]
-                const = const + val
-            i = i + 1
-        
-        # assemble to file
-        # need to make sure 16 bit arguments are padded
-        f.seek(pc)
-        op, width = iset[mne][sym]
         try:
+            if mne == 'org':
+                pc = string_num(args[0])
+                continue
+            elif mne == 'db':
+                data = ''
+                for a in args:
+                    data = data + struct.pack('>B', string_num(a))
+                f.write(data)
+                pc = pc + len(data)
+                continue
+            
+            # replace labels with addresses
+            i = 0
+            for a in args:
+                
+                if not a: continue
+                # labeled pointer uglyness
+                elif (a[0] == '@') and (a[1:] in label_index):
+                    args[i] = '@' + num_string(label_index[a[1:]])
+                    const = const + tokenize([args[i]])[1]
+                elif a in label_index:
+                    # check if constant needs to be a relative address
+                    r = list(sym)
+                    r.insert(i, 'rel8')
+                    r.pop(i + 1)
+                    if tuple(r) in iset[mne].keys():
+                        # relative addresses can be negative
+                        args[i] = num_string(label_index[a] - pc)
+                    else:
+                        args[i] = num_string(label_index[a])
+                    const = const + tokenize([args[i]])[1]
+                i = i + 1
+            
+            # assemble to file
+            op, width = iset[mne][sym]
             f.write(struct.pack('>B', op))
             # pad if needed
             for i in range(width - len(const) - 1):
                 f.write(struct.pack('>B', 0))
             f.write(const)
+            
+            pc = pc + width
+        
         except:
-            # will raise a symbol error when any unrecognised
-            # mnemonic or argument format is found
-            print 'syntax error: %s %s' % (mne, sym)
-            return 'symbol_error'
-        pc = pc + width
-        
-    f.seek(0)    
+            print '** second pass error **\nline:\n', line
+            raise
+
     return f
     
 if __name__ == '__main__':
--- a/assembler/language.py	Thu Jan 30 17:09:55 2014 +0000
+++ b/assembler/language.py	Sat Feb 22 20:30:58 2014 +0000
@@ -10,316 +10,342 @@
 def num_string(num):
     return hex(num)
 
+def string_num(string):
+    return int(string, BASE)
 
 # valid arguments for this instruction set
 vargs = ('', '@a+dptr', 'dptr', 'bs', '@a+pc', 
          'a', 'c','r0', 'r1', 'r2', 'r3', 'ie',
-         'sp', 'flags', 'dpl', 'dph')
+         'sp', 'flags', 'dpl', 'dph', '@dptr',
+         'sph', 'spl')
 
 # dictionary embedded dictionaries?
 # for every mnemonic in the instruction set index
 # there is an index of possible argument formats ('symbol')
 # for that mnemonic and a corresponding op code and it's length
-iset = { 'add': {    ('a', '#data8'): [166, 2],
-                     ('a', '@dptr'): [167, 1],
-                     ('a', 'dph'): [164, 1],
-                     ('a', 'dpl'): [165, 1],
-                     ('a', 'r0'): [160, 1],
-                     ('a', 'r1'): [161, 1],
-                     ('a', 'r2'): [162, 1],
-                     ('a', 'r3'): [163, 1]},
-         'addc': {    ('a', '#data8'): [174, 2],
-                      ('a', '@dptr'): [175, 1],
-                      ('a', 'dph'): [172, 1],
-                      ('a', 'dpl'): [173, 1],
-                      ('a', 'r0'): [168, 1],
-                      ('a', 'r1'): [169, 1],
-                      ('a', 'r2'): [170, 1],
-                      ('a', 'r3'): [171, 1]},
-         'anl': {    ('a', '#data8'): [134, 2],
-                     ('a', '@dptr'): [135, 1],
-                     ('a', 'dph'): [132, 1],
-                     ('a', 'dpl'): [133, 1],
-                     ('a', 'r0'): [128, 1],
-                     ('a', 'r1'): [129, 1],
-                     ('a', 'r2'): [130, 1],
-                     ('a', 'r3'): [131, 1]},
-         'cjne': {    ('a', '#data8', 'label'): [223, 3],
-                      ('a', '#data8', 'rel8'): [223, 3],
-                      ('r0', '#data', 'label'): [212, 2],
-                      ('r0', '#data', 'rel8'): [212, 2],
-                      ('r1', '#data', 'label'): [213, 2],
-                      ('r1', '#data', 'rel8'): [213, 2],
-                      ('r2', '#data', 'label'): [214, 2],
-                      ('r2', '#data', 'rel8'): [214, 2],
-                      ('r3', '#data', 'label'): [215, 2],
-                      ('r3', '#data', 'rel8'): [215, 2]},
-         'clr': {    ('bs',): [11, 1], ('c',): [9, 1], ('ie',): [13, 1]},
-         'cpl': {    ('a',): [15, 1], ('c',): [14, 1]},
-         'da': {    ('a',): [250, 1]},
-         'dec': {    ('a',): [159, 1], ('dptr',): [157, 1]},
-         'div': {    ('r0', 'r1'): [249, 1]},
-         'djnz': {    ('r0', 'label'): [208, 2],
-                      ('r0', 'rel8'): [208, 2],
-                      ('r1', 'label'): [209, 2],
-                      ('r1', 'rel8'): [209, 2],
-                      ('r2', 'label'): [210, 2],
-                      ('r2', 'rel8'): [210, 2],
-                      ('r3', 'label'): [211, 2],
-                      ('r3', 'rel8'): [211, 2]},
-         'hlt': {    ('',): [255, 1]},
-         'in': {    ('a', 'port_addr'): [252, 2]},
-         'inc': {    ('a',): [158, 1], ('dptr',): [156, 1]},
-         'int': {    ('vect8',): [254, 2]},
-         'jc': {    ('label',): [226, 2], ('rel8',): [226, 2]},
-         'jmp': {    ('@a+dptr',): [221, 1], ('@dptr',): [222, 1]},
-         'jnc': {    ('label',): [227, 2], ('rel8',): [227, 2]},
-         'jns': {    ('label',): [231, 2], ('rel8',): [231, 2]},
-         'jnz': {    ('label',): [225, 2], ('rel8',): [225, 2]},
-         'jpe': {    ('label',): [229, 2], ('rel8',): [229, 2]},
-         'jpo': {    ('label',): [228, 2], ('rel8',): [228, 2]},
-         'js': {    ('label',): [230, 2], ('rel8',): [230, 2]},
-         'jz': {    ('label',): [224, 2], ('rel8',): [224, 2]},
-         'laf': {    ('',): [18, 1]},
-         'lcall': {    ('addr16',): [217, 3], ('label',): [217, 3]},
-         'ljmp': {    ('addr16',): [216, 3], ('label',): [216, 3]},
-         'mov': {    ('@addr16', 'a'): [29, 3],
-                     ('@dptr', 'a'): [31, 1],
-                     ('@dptr', 'dph'): [36, 1],
-                     ('@dptr', 'dpl'): [37, 1],
-                     ('@dptr', 'r0'): [32, 1],
-                     ('@dptr', 'r1'): [33, 1],
-                     ('@dptr', 'r2'): [34, 1],
-                     ('@dptr', 'r3'): [35, 1],
-                     ('@dptr', 'sph'): [38, 1],
-                     ('@dptr', 'spl'): [39, 1],
-                     ('a', '#data8'): [21, 2],
-                     ('a', '@a+dptr'): [26, 1],
-                     ('a', '@a+pc'): [27, 1],
-                     ('a', '@addr16'): [28, 3],
-                     ('a', '@dptr'): [30, 1],
-                     ('a', 'addr16'): [24, 3],
-                     ('a', 'dph'): [60, 1],
-                     ('a', 'dpl'): [61, 1],
-                     ('a', 'label'): [24, 3],
-                     ('a', 'r0'): [56, 1],
-                     ('a', 'r1'): [57, 1],
-                     ('a', 'r2'): [58, 1],
-                     ('a', 'r3'): [59, 1],
-                     ('a', 'sph'): [62, 1],
-                     ('a', 'spl'): [63, 1],
-                     ('addr16', 'a'): [25, 3],
-                     ('dph', '#data8'): [44, 2],
-                     ('dph', '@dptr'): [100, 1],
-                     ('dph', 'a'): [52, 1],
-                     ('dph', 'dpl'): [101, 1],
-                     ('dph', 'r0'): [96, 1],
-                     ('dph', 'r1'): [97, 1],
-                     ('dph', 'r2'): [98, 1],
-                     ('dph', 'r3'): [99, 1],
-                     ('dph', 'sph'): [102, 1],
-                     ('dph', 'spl'): [103, 1],
-                     ('dpl', '#data8'): [45, 2],
-                     ('dpl', '@dptr'): [109, 1],
-                     ('dpl', 'a'): [53, 1],
-                     ('dpl', 'dph'): [108, 1],
-                     ('dpl', 'r0'): [104, 1],
-                     ('dpl', 'r1'): [105, 1],
-                     ('dpl', 'r2'): [106, 1],
-                     ('dpl', 'r3'): [107, 1],
-                     ('dpl', 'sph'): [110, 1],
-                     ('dpl', 'spl'): [111, 1],
-                     ('dptr', '#data16'): [23, 3],
-                     ('dptr', 'sp'): [19, 1],
-                     ('r0', '#data8'): [40, 2],
-                     ('r0', '@dptr'): [64, 1],
-                     ('r0', 'a'): [48, 1],
-                     ('r0', 'dph'): [68, 1],
-                     ('r0', 'dpl'): [69, 1],
-                     ('r0', 'r1'): [65, 1],
-                     ('r0', 'r2'): [66, 1],
-                     ('r0', 'r3'): [67, 1],
-                     ('r0', 'sph'): [70, 1],
-                     ('r0', 'spl'): [71, 1],
-                     ('r1', '#data8'): [41, 2],
-                     ('r1', '@dptr'): [73, 1],
-                     ('r1', 'a'): [49, 1],
-                     ('r1', 'dph'): [76, 1],
-                     ('r1', 'dpl'): [77, 1],
-                     ('r1', 'r0'): [72, 1],
-                     ('r1', 'r2'): [74, 1],
-                     ('r1', 'r3'): [75, 1],
-                     ('r1', 'sph'): [78, 1],
-                     ('r1', 'spl'): [79, 1],
-                     ('r2', '#data8'): [42, 2],
-                     ('r2', '@dptr'): [82, 1],
-                     ('r2', 'a'): [50, 1],
-                     ('r2', 'dph'): [84, 1],
-                     ('r2', 'dpl'): [85, 1],
-                     ('r2', 'r0'): [80, 1],
-                     ('r2', 'r1'): [81, 1],
-                     ('r2', 'r3'): [83, 1],
-                     ('r2', 'sph'): [86, 1],
-                     ('r2', 'spl'): [87, 1],
-                     ('r3', '#data8'): [43, 2],
-                     ('r3', '@dptr'): [91, 1],
-                     ('r3', 'a'): [51, 1],
-                     ('r3', 'dph'): [92, 1],
-                     ('r3', 'dpl'): [93, 1],
-                     ('r3', 'r0'): [88, 1],
-                     ('r3', 'r1'): [89, 1],
-                     ('r3', 'r2'): [90, 1],
-                     ('r3', 'sph'): [94, 1],
-                     ('r3', 'spl'): [95, 1],
-                     ('sp', '#data16'): [22, 3],
-                     ('sp', 'dptr'): [20, 1],
-                     ('sph', '#data8'): [46, 2],
-                     ('sph', '@dptr'): [118, 1],
-                     ('sph', 'a'): [54, 1],
-                     ('sph', 'dph'): [116, 1],
-                     ('sph', 'dpl'): [117, 1],
-                     ('sph', 'r0'): [112, 1],
-                     ('sph', 'r1'): [113, 1],
-                     ('sph', 'r2'): [114, 1],
-                     ('sph', 'r3'): [115, 1],
-                     ('sph', 'spl'): [119, 1],
-                     ('spl', '#data8'): [47, 2],
-                     ('spl', '@dptr'): [127, 1],
-                     ('spl', 'a'): [55, 1],
-                     ('spl', 'dph'): [124, 1],
-                     ('spl', 'dpl'): [125, 1],
-                     ('spl', 'r0'): [120, 1],
-                     ('spl', 'r1'): [121, 1],
-                     ('spl', 'r2'): [122, 1],
-                     ('spl', 'r3'): [123, 1],
-                     ('spl', 'sph'): [126, 1]},
-         'mul': {    ('r0', 'r1'): [248, 1]},
-         'nop': {    ('',): [0, 1]},
-         'orl': {    ('a', '#data8'): [142, 2],
-                     ('a', '@dptr'): [143, 1],
-                     ('a', 'dph'): [140, 1],
-                     ('a', 'dpl'): [141, 1],
-                     ('a', 'r0'): [136, 1],
-                     ('a', 'r1'): [137, 1],
-                     ('a', 'r2'): [138, 1],
-                     ('a', 'r3'): [139, 1]},
-         'out': {    ('port_addr', 'a'): [253, 2]},
-         'pcall': {    ('addr11',): [207, 2], ('label',): [207, 2]},
-         'pjmp': {    ('addr11',): [199, 2], ('label',): [199, 2]},
-         'pop': {    ('a',): [246, 1],
-                     ('dph',): [244, 1],
-                     ('dpl',): [245, 1],
-                     ('flags',): [247, 1],
-                     ('r0',): [240, 1],
-                     ('r1',): [241, 1],
-                     ('r2',): [242, 1],
-                     ('r3',): [243, 1]},
-         'push': {    ('a',): [238, 1],
-                      ('dph',): [236, 1],
-                      ('dpl',): [237, 1],
-                      ('flags',): [239, 1],
-                      ('r0',): [232, 1],
-                      ('r1',): [233, 1],
-                      ('r2',): [234, 1],
-                      ('r3',): [235, 1]},
-         'reserved': {    ('',): [251, 1]},
-         'ret': {    ('',): [218, 1]},
-         'reti': {    ('',): [219, 1]},
-         'rl': {    ('a',): [152, 1]},
-         'rlc': {    ('a',): [153, 1]},
-         'rr': {    ('a',): [154, 1]},
-         'rrc': {    ('a',): [155, 1]},
-         'set': {    ('bs',): [10, 1], ('c',): [8, 1], ('ie',): [12, 1]},
-         'sfa': {    ('',): [17, 1]},
-         'sjmp': {    ('label',): [220, 2], ('rel8',): [220, 2]},
-         'sub': {    ('a', '#data8'): [182, 2],
-                     ('a', '@dptr'): [183, 1],
-                     ('a', 'dph'): [180, 1],
-                     ('a', 'dpl'): [181, 1],
-                     ('a', 'r0'): [176, 1],
-                     ('a', 'r1'): [177, 1],
-                     ('a', 'r2'): [178, 1],
-                     ('a', 'r3'): [179, 1]},
-         'subb': {    ('a', '#data8'): [190, 2],
-                      ('a', '@dptr'): [191, 1],
-                      ('a', 'dph'): [188, 1],
-                      ('a', 'dpl'): [189, 1],
-                      ('a', 'r0'): [184, 1],
-                      ('a', 'r1'): [185, 1],
-                      ('a', 'r2'): [186, 1],
-                      ('a', 'r3'): [187, 1]},
-         'xcsd': {    ('',): [16, 1]},
-         'xrl': {    ('a', '#data8'): [150, 2],
-                     ('a', '@dptr'): [151, 1],
-                     ('a', 'dph'): [148, 1],
-                     ('a', 'dpl'): [149, 1],
-                     ('a', 'r0'): [144, 1],
-                     ('a', 'r1'): [145, 1],
-                     ('a', 'r2'): [146, 1],
-                     ('a', 'r3'): [147, 1]}}
+iset =  {    'add': {    ('a', '#data8'): [166, 2],
+                         ('a', '@dptr'): [167, 1],
+                         ('a', 'dph'): [164, 1],
+                         ('a', 'dpl'): [165, 1],
+                         ('a', 'r0'): [160, 1],
+                         ('a', 'r1'): [161, 1],
+                         ('a', 'r2'): [162, 1],
+                         ('a', 'r3'): [163, 1]},
+             'addc': {    ('a', '#data8'): [174, 2],
+                          ('a', '@dptr'): [175, 1],
+                          ('a', 'dph'): [172, 1],
+                          ('a', 'dpl'): [173, 1],
+                          ('a', 'r0'): [168, 1],
+                          ('a', 'r1'): [169, 1],
+                          ('a', 'r2'): [170, 1],
+                          ('a', 'r3'): [171, 1]},
+             'anl': {    ('a', '#data8'): [134, 2],
+                         ('a', '@dptr'): [135, 1],
+                         ('a', 'dph'): [132, 1],
+                         ('a', 'dpl'): [133, 1],
+                         ('a', 'r0'): [128, 1],
+                         ('a', 'r1'): [129, 1],
+                         ('a', 'r2'): [130, 1],
+                         ('a', 'r3'): [131, 1]},
+             'cjne': {    ('a', '#data8', 'label'): [223, 3],
+                          ('a', '#data8', 'rel8'): [223, 3],
+                          ('r0', '#data8', 'label'): [212, 2],
+                          ('r0', '#data8', 'rel8'): [212, 2],
+                          ('r1', '#data8', 'label'): [213, 2],
+                          ('r1', '#data8', 'rel8'): [213, 2],
+                          ('r2', '#data8', 'label'): [214, 2],
+                          ('r2', '#data8', 'rel8'): [214, 2],
+                          ('r3', '#data8', 'label'): [215, 2],
+                          ('r3', '#data8', 'rel8'): [215, 2]},
+             'clr': {    ('bs',): [11, 1], ('c',): [9, 1], ('ie',): [13, 1]},
+             'cpl': {    ('a',): [15, 1], ('c',): [14, 1]},
+             'da': {    ('a',): [250, 1]},
+             'dec': {    ('a',): [159, 1], ('dptr',): [157, 1]},
+             'div': {    ('r0', 'r1'): [249, 1]},
+             'djnz': {    ('r0', 'label'): [208, 2],
+                          ('r0', 'rel8'): [208, 2],
+                          ('r1', 'label'): [209, 2],
+                          ('r1', 'rel8'): [209, 2],
+                          ('r2', 'label'): [210, 2],
+                          ('r2', 'rel8'): [210, 2],
+                          ('r3', 'label'): [211, 2],
+                          ('r3', 'rel8'): [211, 2]},
+             'hlt': {    ('',): [255, 1]},
+             'in': {    ('a', 'port_addr'): [252, 2]},
+             'inc': {    ('a',): [158, 1], ('dptr',): [156, 1]},
+             'int': {    ('vect8',): [254, 2]},
+             'jc': {    ('label',): [226, 2], ('rel8',): [226, 2]},
+             'jmp': {    ('@a+dptr',): [221, 1], ('@dptr',): [222, 1]},
+             'jnc': {    ('label',): [227, 2], ('rel8',): [227, 2]},
+             'jns': {    ('label',): [231, 2], ('rel8',): [231, 2]},
+             'jnz': {    ('label',): [225, 2], ('rel8',): [225, 2]},
+             'jpe': {    ('label',): [229, 2], ('rel8',): [229, 2]},
+             'jpo': {    ('label',): [228, 2], ('rel8',): [228, 2]},
+             'js': {    ('label',): [230, 2], ('rel8',): [230, 2]},
+             'jz': {    ('label',): [224, 2], ('rel8',): [224, 2]},
+             'laf': {    ('',): [18, 1]},
+             'lcall': {    ('addr16',): [217, 3], ('label',): [217, 3]},
+             'ljmp': {    ('addr16',): [216, 3], ('label',): [216, 3]},
+             'mov': {    ('@addr16', 'a'): [29, 3],
+                         ('@dptr', 'a'): [31, 1],
+                         ('@dptr', 'dph'): [36, 1],
+                         ('@dptr', 'dpl'): [37, 1],
+                         ('@dptr', 'r0'): [32, 1],
+                         ('@dptr', 'r1'): [33, 1],
+                         ('@dptr', 'r2'): [34, 1],
+                         ('@dptr', 'r3'): [35, 1],
+                         ('@dptr', 'sph'): [38, 1],
+                         ('@dptr', 'spl'): [39, 1],
+                         ('@label', 'a'): [29, 3],
+                         ('a', '#data8'): [21, 2],
+                         ('a', '@a+dptr'): [26, 1],
+                         ('a', '@a+pc'): [27, 1],
+                         ('a', '@addr16'): [28, 3],
+                         ('a', '@dptr'): [30, 1],
+                         ('a', '@label'): [28, 3],
+                         ('a', 'addr16'): [24, 3],
+                         ('a', 'dph'): [60, 1],
+                         ('a', 'dpl'): [61, 1],
+                         ('a', 'label'): [24, 3],
+                         ('a', 'r0'): [56, 1],
+                         ('a', 'r1'): [57, 1],
+                         ('a', 'r2'): [58, 1],
+                         ('a', 'r3'): [59, 1],
+                         ('a', 'sph'): [62, 1],
+                         ('a', 'spl'): [63, 1],
+                         ('addr16', 'a'): [25, 3],
+                         ('dph', '#data8'): [44, 2],
+                         ('dph', '@dptr'): [100, 1],
+                         ('dph', 'a'): [52, 1],
+                         ('dph', 'dpl'): [101, 1],
+                         ('dph', 'r0'): [96, 1],
+                         ('dph', 'r1'): [97, 1],
+                         ('dph', 'r2'): [98, 1],
+                         ('dph', 'r3'): [99, 1],
+                         ('dph', 'sph'): [102, 1],
+                         ('dph', 'spl'): [103, 1],
+                         ('dpl', '#data8'): [45, 2],
+                         ('dpl', '@dptr'): [109, 1],
+                         ('dpl', 'a'): [53, 1],
+                         ('dpl', 'dph'): [108, 1],
+                         ('dpl', 'r0'): [104, 1],
+                         ('dpl', 'r1'): [105, 1],
+                         ('dpl', 'r2'): [106, 1],
+                         ('dpl', 'r3'): [107, 1],
+                         ('dpl', 'sph'): [110, 1],
+                         ('dpl', 'spl'): [111, 1],
+                         ('dptr', '#data16'): [23, 3],
+                         ('dptr', 'sp'): [19, 1],
+                         ('label', 'a'): [25, 3],
+                         ('r0', '#data8'): [40, 2],
+                         ('r0', '@dptr'): [64, 1],
+                         ('r0', 'a'): [48, 1],
+                         ('r0', 'dph'): [68, 1],
+                         ('r0', 'dpl'): [69, 1],
+                         ('r0', 'r1'): [65, 1],
+                         ('r0', 'r2'): [66, 1],
+                         ('r0', 'r3'): [67, 1],
+                         ('r0', 'sph'): [70, 1],
+                         ('r0', 'spl'): [71, 1],
+                         ('r1', '#data8'): [41, 2],
+                         ('r1', '@dptr'): [73, 1],
+                         ('r1', 'a'): [49, 1],
+                         ('r1', 'dph'): [76, 1],
+                         ('r1', 'dpl'): [77, 1],
+                         ('r1', 'r0'): [72, 1],
+                         ('r1', 'r2'): [74, 1],
+                         ('r1', 'r3'): [75, 1],
+                         ('r1', 'sph'): [78, 1],
+                         ('r1', 'spl'): [79, 1],
+                         ('r2', '#data8'): [42, 2],
+                         ('r2', '@dptr'): [82, 1],
+                         ('r2', 'a'): [50, 1],
+                         ('r2', 'dph'): [84, 1],
+                         ('r2', 'dpl'): [85, 1],
+                         ('r2', 'r0'): [80, 1],
+                         ('r2', 'r1'): [81, 1],
+                         ('r2', 'r3'): [83, 1],
+                         ('r2', 'sph'): [86, 1],
+                         ('r2', 'spl'): [87, 1],
+                         ('r3', '#data8'): [43, 2],
+                         ('r3', '@dptr'): [91, 1],
+                         ('r3', 'a'): [51, 1],
+                         ('r3', 'dph'): [92, 1],
+                         ('r3', 'dpl'): [93, 1],
+                         ('r3', 'r0'): [88, 1],
+                         ('r3', 'r1'): [89, 1],
+                         ('r3', 'r2'): [90, 1],
+                         ('r3', 'sph'): [94, 1],
+                         ('r3', 'spl'): [95, 1],
+                         ('sp', '#data16'): [22, 3],
+                         ('sp', 'dptr'): [20, 1],
+                         ('sph', '#data8'): [46, 2],
+                         ('sph', '@dptr'): [118, 1],
+                         ('sph', 'a'): [54, 1],
+                         ('sph', 'dph'): [116, 1],
+                         ('sph', 'dpl'): [117, 1],
+                         ('sph', 'r0'): [112, 1],
+                         ('sph', 'r1'): [113, 1],
+                         ('sph', 'r2'): [114, 1],
+                         ('sph', 'r3'): [115, 1],
+                         ('sph', 'spl'): [119, 1],
+                         ('spl', '#data8'): [47, 2],
+                         ('spl', '@dptr'): [127, 1],
+                         ('spl', 'a'): [55, 1],
+                         ('spl', 'dph'): [124, 1],
+                         ('spl', 'dpl'): [125, 1],
+                         ('spl', 'r0'): [120, 1],
+                         ('spl', 'r1'): [121, 1],
+                         ('spl', 'r2'): [122, 1],
+                         ('spl', 'r3'): [123, 1],
+                         ('spl', 'sph'): [126, 1]},
+             'mul': {    ('r0', 'r1'): [248, 1]},
+             'nop': {    ('',): [0, 1]},
+             'orl': {    ('a', '#data8'): [142, 2],
+                         ('a', '@dptr'): [143, 1],
+                         ('a', 'dph'): [140, 1],
+                         ('a', 'dpl'): [141, 1],
+                         ('a', 'r0'): [136, 1],
+                         ('a', 'r1'): [137, 1],
+                         ('a', 'r2'): [138, 1],
+                         ('a', 'r3'): [139, 1]},
+             'out': {    ('port_addr', 'a'): [253, 2]},
+             'pcall': {    ('addr11',): [207, 2], ('label',): [207, 2]},
+             'pjmp': {    ('addr11',): [199, 2], ('label',): [199, 2]},
+             'pop': {    ('a',): [246, 1],
+                         ('dph',): [244, 1],
+                         ('dpl',): [245, 1],
+                         ('flags',): [247, 1],
+                         ('r0',): [240, 1],
+                         ('r1',): [241, 1],
+                         ('r2',): [242, 1],
+                         ('r3',): [243, 1]},
+             'push': {    ('a',): [238, 1],
+                          ('dph',): [236, 1],
+                          ('dpl',): [237, 1],
+                          ('flags',): [239, 1],
+                          ('r0',): [232, 1],
+                          ('r1',): [233, 1],
+                          ('r2',): [234, 1],
+                          ('r3',): [235, 1]},
+             'reserved': {    ('',): [251, 1]},
+             'ret': {    ('',): [218, 1]},
+             'reti': {    ('',): [219, 1]},
+             'rl': {    ('a',): [152, 1]},
+             'rlc': {    ('a',): [153, 1]},
+             'rr': {    ('a',): [154, 1]},
+             'rrc': {    ('a',): [155, 1]},
+             'set': {    ('bs',): [10, 1], ('c',): [8, 1], ('ie',): [12, 1]},
+             'sfa': {    ('',): [17, 1]},
+             'sjmp': {    ('label',): [220, 2], ('rel8',): [220, 2]},
+             'sub': {    ('a', '#data8'): [182, 2],
+                         ('a', '@dptr'): [183, 1],
+                         ('a', 'dph'): [180, 1],
+                         ('a', 'dpl'): [181, 1],
+                         ('a', 'r0'): [176, 1],
+                         ('a', 'r1'): [177, 1],
+                         ('a', 'r2'): [178, 1],
+                         ('a', 'r3'): [179, 1]},
+             'subb': {    ('a', '#data8'): [190, 2],
+                          ('a', '@dptr'): [191, 1],
+                          ('a', 'dph'): [188, 1],
+                          ('a', 'dpl'): [189, 1],
+                          ('a', 'r0'): [184, 1],
+                          ('a', 'r1'): [185, 1],
+                          ('a', 'r2'): [186, 1],
+                          ('a', 'r3'): [187, 1]},
+             'xcsd': {    ('',): [16, 1]},
+             'xrl': {    ('a', '#data8'): [150, 2],
+                         ('a', '@dptr'): [151, 1],
+                         ('a', 'dph'): [148, 1],
+                         ('a', 'dpl'): [149, 1],
+                         ('a', 'r0'): [144, 1],
+                         ('a', 'r1'): [145, 1],
+                         ('a', 'r2'): [146, 1],
+                         ('a', 'r3'): [147, 1]}}
+
 
 # take a list of arguments
 # identify constant data:
 #       pack that data into a bit string
-# return data type symbols and data
+# return hashable data type symbols and data
 def tokenize(args):
     sym = []
     data = ''
     
+    i = 0
+
     for a in args:   
-
+    
+        is_neg = 0
+        # reserved words
+        if a in vargs:
+            sym.append(a)
+            continue
+        # check if value is negative and remove sign
+        elif a[0] == '-':
+            a = a[1:]
+            is_neg = 1
+        
         # immediate ints
-        if a[:3] == '#' + PREFIX:
+        if (a[:3] == '#' + PREFIX):
             # 8 bit ints
             if len(a[3:]) <= 2:
                 sym.append('#data8')
-                val = int(a[1:], BASE)
-                # big-endian byte
-                data = data + struct.pack('>B', val)
-            
+                if is_neg:
+                    val = string_num('-' + a[1:])
+                else:
+                    val = string_num(a[1:])
+                # signed big-endian byte
+                data = data + struct.pack('>b', val)
             # 16 bit ints
             elif len(a[3:]) <= 4:
                 sym.append('#data16')
-                val = int(a[1:], BASE)
-                # big-endian short
-                data = data + struct.pack('>H', val)
-
-            else:
-                # bad idea to return junk to throw errors later?
-                sym.append(a)
-                     
+                if is_neg:
+                    val = string_num('-' + a[1:])
+                else:
+                    val = string_num(a[1:])
+                # signed big-endian short
+                data = data + struct.pack('>h', val)
         # addresses
-        elif a[:2] == PREFIX:
+        elif (a[:2] == PREFIX):
             # 8 bit addresses
             if len(a[2:]) <= 2:
                 sym.append('rel8')
-                val = int(a, BASE)
-                data = data + struct.pack('>B', val)
-    
+                if is_neg:
+                    val = string_num('-' + a)
+                else:
+                    val = string_num(a)
+                # signed
+                data = data + struct.pack('>b', val)
             # 16 bit addresses
             elif len(a[2:]) <= 4:
                 sym.append('addr16')
-                val = int(a, BASE)
+                val = string_num(a)
                 data = data + struct.pack('>H', val)
-                
+        # pointers
+        elif a[0] == '@':
+            if a[:3] == '@' + PREFIX:
+                sym.append('@addr16')
+                val = string_num(a[1:])
+                data = data + struct.pack('>H', val)
+            # labeled pointers make for ugly code considering
+            # only two instructions can use them
             else:
-                # junk junk junk
-                sym.append(a)
-        
-        # pointers
-        elif a[:3] == '@' + PREFIX:
-            sym.append('@addr16')
-            val = int(a[1:], BASE)
-            data = data + struct.pack('>H', val)
-
-        elif a in vargs:
-            sym.append(a)
-
-        # return unknown stings are either labels or source code errors
+                sym.append('@label')
+        # ports
+        elif a[:3] == 'p' + PREFIX:
+            sym.append('port_addr')
+            val = string_num(a[1:])
+            data = data + struct.pack('>B', val)
+        # vectors
+        elif a[:3] == 'v' + PREFIX:
+            sym.append('vect8')
+            val = string_num(a[1:])
+            data = data + struct.pack('>B', val)
+        # unknown strings are either labels or source code errors
         else:
             sym.append('label')
-        
-
-
+    
     return tuple(sym), data
 
Binary file assembler/language.pyc has changed
Binary file emulator/a.out has changed
--- a/emulator/emu.c	Thu Jan 30 17:09:55 2014 +0000
+++ b/emulator/emu.c	Sat Feb 22 20:30:58 2014 +0000
@@ -49,15 +49,11 @@
     memset(&memory, 0, sizeof(memory));
 
     /* load program from stdin
-     * c must be signed since EOF is -1 on linux */
+     * c must be signed int since EOF is -1 on linux */
     WIDE i = 0;
-    BYTE c = getchar();
+    signed short int c = getchar();
     for(i ; i < 0x10000 ; i++) {
-        /* add HLT if EOF is reached */
-        if ((signed char) c == EOF) { 
-            memory[i] = 0xFF;
-            break; 
-        }
+        if (c == EOF) { break; }
         memory[i] = c;
         c = getchar();
     }
@@ -74,7 +70,9 @@
     boot();
     for (;;) { 
         step();
-        putchar(registers.flags);
+        //debug
+        //putchar(registers.flags);
+        putchar((BYTE)(registers.PC & 0x0F)); 
     }
 }
 
--- a/emulator/iset.c	Thu Jan 30 17:09:55 2014 +0000
+++ b/emulator/iset.c	Sat Feb 22 20:30:58 2014 +0000
@@ -1,7 +1,6 @@
 /* iset.c
  * op functions */
 #include <stdlib.h>
-#include <stdio.h> // debug
 #include "iset.h"
 #include "mem.h"
 
@@ -20,7 +19,7 @@
 /*
  * 0x08 - SET C
  * 0x0A - SET BS
- * 0x0c - SET IE */
+ * 0x0C - SET IE */
 void
 SET(void) {
     switch (op) {
--- a/emulator/iset.h	Thu Jan 30 17:09:55 2014 +0000
+++ b/emulator/iset.h	Sat Feb 22 20:30:58 2014 +0000
@@ -2,7 +2,10 @@
  * op function definitions */
 #ifndef ISET_H
 #define ISET_H
- 
+
+/* instruction pointers */
+void (*iset[256])(void);
+
 void
 JNS(void);
 
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/tests/full.asm	Sat Feb 22 20:30:58 2014 +0000
@@ -0,0 +1,260 @@
+#data8 EQU #0x42
+#data16 EQU #0x5757
+port_addr EQU P0x50
+vect8 EQU V0x56
+
+NOP
+SET C
+CLR C
+SET BS
+CLR BS
+SET IE
+CLR IE
+CPL C
+CPL A
+XCSD
+SFA
+LAF
+MOV DPTR, SP
+MOV SP, DPTR
+MOV A, #data8
+MOV SP, #data16
+MOV DPTR, #data16
+MOV A, addr16
+MOV addr16, A
+MOV A, @A+DPTR
+MOV A, @A+PC
+MOV A, @addr16
+MOV @addr16, A
+MOV A, @DPTR
+MOV @DPTR, A
+MOV @DPTR, R0
+MOV @DPTR, R1
+MOV @DPTR, R2
+MOV @DPTR, R3
+MOV @DPTR, DPH
+MOV @DPTR, DPL
+MOV @DPTR, SPH
+MOV @DPTR, SPL
+MOV R0, #data8
+MOV R1, #data8
+MOV R2, #data8
+MOV R3, #data8
+MOV DPH, #data8
+MOV DPL, #data8
+MOV SPH, #data8
+MOV SPL, #data8
+MOV R0, A
+MOV R1, A
+MOV R2, A
+MOV R3, A
+MOV DPH, A
+MOV DPL, A
+MOV SPH, A
+MOV SPL, A
+MOV A, R0
+MOV A, R1
+MOV A, R2
+MOV A, R3
+MOV A, DPH
+MOV A, DPL
+MOV A, SPH
+MOV A, SPL
+MOV R0, @DPTR
+MOV R0, R1
+MOV R0, R2
+MOV R0, R3
+MOV R0, DPH
+MOV R0, DPL
+MOV R0, SPH
+MOV R0, SPL
+MOV R1, R0
+MOV R1, @DPTR
+MOV R1, R2
+MOV R1, R3
+MOV R1, DPH
+MOV R1, DPL
+MOV R1, SPH
+MOV R1, SPL
+MOV R2, R0
+MOV R2, R1
+MOV R2, @DPTR
+MOV R2, R3
+MOV R2, DPH
+MOV R2, DPL
+MOV R2, SPH
+MOV R2, SPL
+MOV R3, R0
+MOV R3, R1
+MOV R3, R2
+MOV R3, @DPTR
+MOV R3, DPH
+MOV R3, DPL
+MOV R3, SPH
+MOV R3, SPL
+MOV DPH, R0
+MOV DPH, R1
+MOV DPH, R2
+MOV DPH, R3
+MOV DPH, @DPTR
+MOV DPH, DPL
+MOV DPH, SPH
+MOV DPH, SPL
+MOV DPL, R0
+MOV DPL, R1
+MOV DPL, R2
+MOV DPL, R3
+MOV DPL, DPH
+MOV DPL, @DPTR
+MOV DPL, SPH
+MOV DPL, SPL
+MOV SPH, R0
+MOV SPH, R1
+MOV SPH, R2
+MOV SPH, R3
+MOV SPH, DPH
+MOV SPH, DPL
+MOV SPH, @DPTR
+MOV SPH, SPL
+MOV SPL, R0
+MOV SPL, R1
+MOV SPL, R2
+MOV SPL, R3
+MOV SPL, DPH
+MOV SPL, DPL
+MOV SPL, SPH
+MOV SPL, @DPTR
+ANL A, R0
+ANL A, R1
+ANL A, R2
+ANL A, R3
+ANL A, DPH
+ANL A, DPL
+ANL A, #data8
+ANL A, @DPTR
+ORL A, R0
+ORL A, R1
+ORL A, R2
+ORL A, R3
+ORL A, DPH
+ORL A, DPL
+ORL A, #data8
+ORL A, @DPTR
+XRL A, R0
+XRL A, R1
+XRL A, R2
+XRL A, R3
+XRL A, DPH
+XRL A, DPL
+XRL A, #data8
+XRL A, @DPTR
+RL A
+RLC A
+RR A
+RRC A
+INC DPTR
+DEC DPTR
+INC A
+DEC A
+ADD A, R0
+ADD A, R1
+ADD A, R2
+ADD A, R3
+ADD A, DPH
+ADD A, DPL
+ADD A, #data8
+ADD A, @DPTR
+ADDC A, R0
+ADDC A, R1
+ADDC A, R2
+ADDC A, R3
+ADDC A, DPH
+ADDC A, DPL
+ADDC A, #data8
+ADDC A, @DPTR
+SUB A, R0
+SUB A, R1
+SUB A, R2
+SUB A, R3
+SUB A, DPH
+SUB A, DPL
+SUB A, #data8
+SUB A, @DPTR
+SUBB A, R0
+SUBB A, R1
+SUBB A, R2
+SUBB A, R3
+SUBB A, DPH
+SUBB A, DPL
+SUBB A, #data8
+SUBB A, @DPTR
+PJMP addr11
+PJMP addr11
+PJMP addr11
+PJMP addr11
+PJMP addr11
+PJMP addr11
+PJMP addr11
+PJMP addr11
+PCALL addr11
+PCALL addr11
+PCALL addr11
+PCALL addr11
+PCALL addr11
+PCALL addr11
+PCALL addr11
+PCALL addr11
+DJNZ R0, rel8
+DJNZ R1, rel8
+DJNZ R2, rel8
+DJNZ R3, rel8
+CJNE R0, #data8, rel8
+CJNE R1, #data8, rel8
+CJNE R2, #data8, rel8
+CJNE R3, #data8, rel8
+LJMP addr16
+LCALL addr16
+RET
+RETI
+SJMP rel8
+JMP @A+DPTR
+JMP @DPTR
+CJNE A, #data8, rel8
+JZ rel8
+JNZ rel8
+JC rel8
+JNC rel8
+JPO rel8
+JPE rel8
+JS rel8
+JNS rel8
+PUSH R0
+PUSH R1
+PUSH R2
+PUSH R3
+PUSH DPH
+PUSH DPL
+PUSH A
+PUSH FLAGS
+POP R0
+POP R1
+POP R2
+POP R3
+POP DPH
+POP DPL
+POP A
+POP FLAGS
+MUL R0, R1
+DIV R0, R1
+DA A
+reserved
+IN A, port_addr
+OUT port_addr, A
+INT vect8
+HLT
+
+org 0x0151
+rel8:
+addr11:
+addr16:
+NOP
Binary file tests/full.bin has changed
--- a/tests/test.asm	Thu Jan 30 17:09:55 2014 +0000
+++ b/tests/test.asm	Sat Feb 22 20:30:58 2014 +0000
@@ -1,7 +1,2 @@
-SET C
-CLR C
-SET BS
-CLR BS
-SET IE
-CLR IE
-HLT
+org 0x0010
+db 0x42 0x57 0x42 0x57 0x00 0x00 0x00
Binary file tests/test.bin has changed
--- a/utils/gen_language.ipynb	Thu Jan 30 17:09:55 2014 +0000
+++ b/utils/gen_language.ipynb	Sat Feb 22 20:30:58 2014 +0000
@@ -31,8 +31,7 @@
      ],
      "language": "python",
      "metadata": {},
-     "outputs": [],
-     "prompt_number": 1
+     "outputs": []
     },
     {
      "cell_type": "code",
@@ -62,11 +61,14 @@
       "                    width = width + consts[a]\n",
       "            valid_args.update({tuple(line[1]):[int(codes[i]), width]})\n",
       "            \n",
+      "            found_label = 0\n",
       "            for a in line[1]:\n",
-      "                found_label = 0\n",
       "                if a in labelable:\n",
       "                    found_label = 1\n",
       "                    args.append('label')\n",
+      "                elif a == '@addr16':\n",
+      "                    found_label = 1\n",
+      "                    args.append('@label')\n",
       "                else:\n",
       "                    args.append(a)\n",
       "            if found_label:\n",
@@ -74,12 +76,266 @@
       "            \n",
       "        i = i + 1\n",
       "    iset.update({mne:valid_args})\n",
-      "#pprint(iset, indent=5)\n"
+      "pprint(iset, indent=5)\n"
      ],
      "language": "python",
      "metadata": {},
-     "outputs": [],
-     "prompt_number": 2
+     "outputs": [
+      {
+       "output_type": "stream",
+       "stream": "stdout",
+       "text": [
+        "{    'add': {    ('a', '#data8'): [166, 2],\n",
+        "                 ('a', '@dptr'): [167, 1],\n",
+        "                 ('a', 'dph'): [164, 1],\n",
+        "                 ('a', 'dpl'): [165, 1],\n",
+        "                 ('a', 'r0'): [160, 1],\n",
+        "                 ('a', 'r1'): [161, 1],\n",
+        "                 ('a', 'r2'): [162, 1],\n",
+        "                 ('a', 'r3'): [163, 1]},\n",
+        "     'addc': {    ('a', '#data8'): [174, 2],\n",
+        "                  ('a', '@dptr'): [175, 1],\n",
+        "                  ('a', 'dph'): [172, 1],\n",
+        "                  ('a', 'dpl'): [173, 1],\n",
+        "                  ('a', 'r0'): [168, 1],\n",
+        "                  ('a', 'r1'): [169, 1],\n",
+        "                  ('a', 'r2'): [170, 1],\n",
+        "                  ('a', 'r3'): [171, 1]},\n",
+        "     'anl': {    ('a', '#data8'): [134, 2],\n",
+        "                 ('a', '@dptr'): [135, 1],\n",
+        "                 ('a', 'dph'): [132, 1],\n",
+        "                 ('a', 'dpl'): [133, 1],\n",
+        "                 ('a', 'r0'): [128, 1],\n",
+        "                 ('a', 'r1'): [129, 1],\n",
+        "                 ('a', 'r2'): [130, 1],\n",
+        "                 ('a', 'r3'): [131, 1]},\n",
+        "     'cjne': {    ('a', '#data8', 'label'): [223, 3],\n",
+        "                  ('a', '#data8', 'rel8'): [223, 3],\n",
+        "                  ('r0', '#data', 'label'): [212, 2],\n",
+        "                  ('r0', '#data', 'rel8'): [212, 2],\n",
+        "                  ('r1', '#data', 'label'): [213, 2],\n",
+        "                  ('r1', '#data', 'rel8'): [213, 2],\n",
+        "                  ('r2', '#data', 'label'): [214, 2],\n",
+        "                  ('r2', '#data', 'rel8'): [214, 2],\n",
+        "                  ('r3', '#data', 'label'): [215, 2],\n",
+        "                  ('r3', '#data', 'rel8'): [215, 2]},\n",
+        "     'clr': {    ('bs',): [11, 1], ('c',): [9, 1], ('ie',): [13, 1]},\n",
+        "     'cpl': {    ('a',): [15, 1], ('c',): [14, 1]},\n",
+        "     'da': {    ('a',): [250, 1]},\n",
+        "     'dec': {    ('a',): [159, 1], ('dptr',): [157, 1]},\n",
+        "     'div': {    ('r0', 'r1'): [249, 1]},\n",
+        "     'djnz': {    ('r0', 'label'): [208, 2],\n",
+        "                  ('r0', 'rel8'): [208, 2],\n",
+        "                  ('r1', 'label'): [209, 2],\n",
+        "                  ('r1', 'rel8'): [209, 2],\n",
+        "                  ('r2', 'label'): [210, 2],\n",
+        "                  ('r2', 'rel8'): [210, 2],\n",
+        "                  ('r3', 'label'): [211, 2],\n",
+        "                  ('r3', 'rel8'): [211, 2]},\n",
+        "     'hlt': {    ('',): [255, 1]},\n",
+        "     'in': {    ('a', 'port_addr'): [252, 2]},\n",
+        "     'inc': {    ('a',): [158, 1], ('dptr',): [156, 1]},\n",
+        "     'int': {    ('vect8',): [254, 2]},\n",
+        "     'jc': {    ('label',): [226, 2], ('rel8',): [226, 2]},\n",
+        "     'jmp': {    ('@a+dptr',): [221, 1], ('@dptr',): [222, 1]},\n",
+        "     'jnc': {    ('label',): [227, 2], ('rel8',): [227, 2]},\n",
+        "     'jns': {    ('label',): [231, 2], ('rel8',): [231, 2]},\n",
+        "     'jnz': {    ('label',): [225, 2], ('rel8',): [225, 2]},\n",
+        "     'jpe': {    ('label',): [229, 2], ('rel8',): [229, 2]},\n",
+        "     'jpo': {    ('label',): [228, 2], ('rel8',): [228, 2]},\n",
+        "     'js': {    ('label',): [230, 2], ('rel8',): [230, 2]},\n",
+        "     'jz': {    ('label',): [224, 2], ('rel8',): [224, 2]},\n",
+        "     'laf': {    ('',): [18, 1]},\n",
+        "     'lcall': {    ('addr16',): [217, 3], ('label',): [217, 3]},\n",
+        "     'ljmp': {    ('addr16',): [216, 3], ('label',): [216, 3]},\n",
+        "     'mov': {    ('@addr16', 'a'): [29, 3],\n",
+        "                 ('@dptr', 'a'): [31, 1],\n",
+        "                 ('@dptr', 'dph'): [36, 1],\n",
+        "                 ('@dptr', 'dpl'): [37, 1],\n",
+        "                 ('@dptr', 'r0'): [32, 1],\n",
+        "                 ('@dptr', 'r1'): [33, 1],\n",
+        "                 ('@dptr', 'r2'): [34, 1],\n",
+        "                 ('@dptr', 'r3'): [35, 1],\n",
+        "                 ('@dptr', 'sph'): [38, 1],\n",
+        "                 ('@dptr', 'spl'): [39, 1],\n",
+        "                 ('@label', 'a'): [29, 3],\n",
+        "                 ('a', '#data8'): [21, 2],\n",
+        "                 ('a', '@a+dptr'): [26, 1],\n",
+        "                 ('a', '@a+pc'): [27, 1],\n",
+        "                 ('a', '@addr16'): [28, 3],\n",
+        "                 ('a', '@dptr'): [30, 1],\n",
+        "                 ('a', '@label'): [28, 3],\n",
+        "                 ('a', 'addr16'): [24, 3],\n",
+        "                 ('a', 'dph'): [60, 1],\n",
+        "                 ('a', 'dpl'): [61, 1],\n",
+        "                 ('a', 'label'): [24, 3],\n",
+        "                 ('a', 'r0'): [56, 1],\n",
+        "                 ('a', 'r1'): [57, 1],\n",
+        "                 ('a', 'r2'): [58, 1],\n",
+        "                 ('a', 'r3'): [59, 1],\n",
+        "                 ('a', 'sph'): [62, 1],\n",
+        "                 ('a', 'spl'): [63, 1],\n",
+        "                 ('addr16', 'a'): [25, 3],\n",
+        "                 ('dph', '#data8'): [44, 2],\n",
+        "                 ('dph', '@dptr'): [100, 1],\n",
+        "                 ('dph', 'a'): [52, 1],\n",
+        "                 ('dph', 'dpl'): [101, 1],\n",
+        "                 ('dph', 'r0'): [96, 1],\n",
+        "                 ('dph', 'r1'): [97, 1],\n",
+        "                 ('dph', 'r2'): [98, 1],\n",
+        "                 ('dph', 'r3'): [99, 1],\n",
+        "                 ('dph', 'sph'): [102, 1],\n",
+        "                 ('dph', 'spl'): [103, 1],\n",
+        "                 ('dpl', '#data8'): [45, 2],\n",
+        "                 ('dpl', '@dptr'): [109, 1],\n",
+        "                 ('dpl', 'a'): [53, 1],\n",
+        "                 ('dpl', 'dph'): [108, 1],\n",
+        "                 ('dpl', 'r0'): [104, 1],\n",
+        "                 ('dpl', 'r1'): [105, 1],\n",
+        "                 ('dpl', 'r2'): [106, 1],\n",
+        "                 ('dpl', 'r3'): [107, 1],\n",
+        "                 ('dpl', 'sph'): [110, 1],\n",
+        "                 ('dpl', 'spl'): [111, 1],\n",
+        "                 ('dptr', '#data16'): [23, 3],\n",
+        "                 ('dptr', 'sp'): [19, 1],\n",
+        "                 ('label', 'a'): [25, 3],\n",
+        "                 ('r0', '#data8'): [40, 2],\n",
+        "                 ('r0', '@dptr'): [64, 1],\n",
+        "                 ('r0', 'a'): [48, 1],\n",
+        "                 ('r0', 'dph'): [68, 1],\n",
+        "                 ('r0', 'dpl'): [69, 1],\n",
+        "                 ('r0', 'r1'): [65, 1],\n",
+        "                 ('r0', 'r2'): [66, 1],\n",
+        "                 ('r0', 'r3'): [67, 1],\n",
+        "                 ('r0', 'sph'): [70, 1],\n",
+        "                 ('r0', 'spl'): [71, 1],\n",
+        "                 ('r1', '#data8'): [41, 2],\n",
+        "                 ('r1', '@dptr'): [73, 1],\n",
+        "                 ('r1', 'a'): [49, 1],\n",
+        "                 ('r1', 'dph'): [76, 1],\n",
+        "                 ('r1', 'dpl'): [77, 1],\n",
+        "                 ('r1', 'r0'): [72, 1],\n",
+        "                 ('r1', 'r2'): [74, 1],\n",
+        "                 ('r1', 'r3'): [75, 1],\n",
+        "                 ('r1', 'sph'): [78, 1],\n",
+        "                 ('r1', 'spl'): [79, 1],\n",
+        "                 ('r2', '#data8'): [42, 2],\n",
+        "                 ('r2', '@dptr'): [82, 1],\n",
+        "                 ('r2', 'a'): [50, 1],\n",
+        "                 ('r2', 'dph'): [84, 1],\n",
+        "                 ('r2', 'dpl'): [85, 1],\n",
+        "                 ('r2', 'r0'): [80, 1],\n",
+        "                 ('r2', 'r1'): [81, 1],\n",
+        "                 ('r2', 'r3'): [83, 1],\n",
+        "                 ('r2', 'sph'): [86, 1],\n",
+        "                 ('r2', 'spl'): [87, 1],\n",
+        "                 ('r3', '#data8'): [43, 2],\n",
+        "                 ('r3', '@dptr'): [91, 1],\n",
+        "                 ('r3', 'a'): [51, 1],\n",
+        "                 ('r3', 'dph'): [92, 1],\n",
+        "                 ('r3', 'dpl'): [93, 1],\n",
+        "                 ('r3', 'r0'): [88, 1],\n",
+        "                 ('r3', 'r1'): [89, 1],\n",
+        "                 ('r3', 'r2'): [90, 1],\n",
+        "                 ('r3', 'sph'): [94, 1],\n",
+        "                 ('r3', 'spl'): [95, 1],\n",
+        "                 ('sp', '#data16'): [22, 3],\n",
+        "                 ('sp', 'dptr'): [20, 1],\n",
+        "                 ('sph', '#data8'): [46, 2],\n",
+        "                 ('sph', '@dptr'): [118, 1],\n",
+        "                 ('sph', 'a'): [54, 1],\n",
+        "                 ('sph', 'dph'): [116, 1],\n",
+        "                 ('sph', 'dpl'): [117, 1],\n",
+        "                 ('sph', 'r0'): [112, 1],\n",
+        "                 ('sph', 'r1'): [113, 1],\n",
+        "                 ('sph', 'r2'): [114, 1],\n",
+        "                 ('sph', 'r3'): [115, 1],\n",
+        "                 ('sph', 'spl'): [119, 1],\n",
+        "                 ('spl', '#data8'): [47, 2],\n",
+        "                 ('spl', '@dptr'): [127, 1],\n",
+        "                 ('spl', 'a'): [55, 1],\n",
+        "                 ('spl', 'dph'): [124, 1],\n",
+        "                 ('spl', 'dpl'): [125, 1],\n",
+        "                 ('spl', 'r0'): [120, 1],\n",
+        "                 ('spl', 'r1'): [121, 1],\n",
+        "                 ('spl', 'r2'): [122, 1],\n",
+        "                 ('spl', 'r3'): [123, 1],\n",
+        "                 ('spl', 'sph'): [126, 1]},\n",
+        "     'mul': {    ('r0', 'r1'): [248, 1]},\n",
+        "     'nop': {    ('',): [0, 1]},\n",
+        "     'orl': {    ('a', '#data8'): [142, 2],\n",
+        "                 ('a', '@dptr'): [143, 1],\n",
+        "                 ('a', 'dph'): [140, 1],\n",
+        "                 ('a', 'dpl'): [141, 1],\n",
+        "                 ('a', 'r0'): [136, 1],\n",
+        "                 ('a', 'r1'): [137, 1],\n",
+        "                 ('a', 'r2'): [138, 1],\n",
+        "                 ('a', 'r3'): [139, 1]},\n",
+        "     'out': {    ('port_addr', 'a'): [253, 2]},\n",
+        "     'pcall': {    ('addr11',): [207, 2], ('label',): [207, 2]},\n",
+        "     'pjmp': {    ('addr11',): [199, 2], ('label',): [199, 2]},\n",
+        "     'pop': {    ('a',): [246, 1],\n",
+        "                 ('dph',): [244, 1],\n",
+        "                 ('dpl',): [245, 1],\n",
+        "                 ('flags',): [247, 1],\n",
+        "                 ('r0',): [240, 1],\n",
+        "                 ('r1',): [241, 1],\n",
+        "                 ('r2',): [242, 1],\n",
+        "                 ('r3',): [243, 1]},\n",
+        "     'push': {    ('a',): [238, 1],\n",
+        "                  ('dph',): [236, 1],\n",
+        "                  ('dpl',): [237, 1],\n",
+        "                  ('flags',): [239, 1],\n",
+        "                  ('r0',): [232, 1],\n",
+        "                  ('r1',): [233, 1],\n",
+        "                  ('r2',): [234, 1],\n",
+        "                  ('r3',): [235, 1]},\n",
+        "     'reserved': {    ('',): [251, 1]},\n",
+        "     'ret': {    ('',): [218, 1]},\n",
+        "     'reti': {    ('',): [219, 1]},\n",
+        "     'rl': {    ('a',): [152, 1]"
+       ]
+      },
+      {
+       "output_type": "stream",
+       "stream": "stdout",
+       "text": [
+        "},\n",
+        "     'rlc': {    ('a',): [153, 1]},\n",
+        "     'rr': {    ('a',): [154, 1]},\n",
+        "     'rrc': {    ('a',): [155, 1]},\n",
+        "     'set': {    ('bs',): [10, 1], ('c',): [8, 1], ('ie',): [12, 1]},\n",
+        "     'sfa': {    ('',): [17, 1]},\n",
+        "     'sjmp': {    ('label',): [220, 2], ('rel8',): [220, 2]},\n",
+        "     'sub': {    ('a', '#data8'): [182, 2],\n",
+        "                 ('a', '@dptr'): [183, 1],\n",
+        "                 ('a', 'dph'): [180, 1],\n",
+        "                 ('a', 'dpl'): [181, 1],\n",
+        "                 ('a', 'r0'): [176, 1],\n",
+        "                 ('a', 'r1'): [177, 1],\n",
+        "                 ('a', 'r2'): [178, 1],\n",
+        "                 ('a', 'r3'): [179, 1]},\n",
+        "     'subb': {    ('a', '#data8'): [190, 2],\n",
+        "                  ('a', '@dptr'): [191, 1],\n",
+        "                  ('a', 'dph'): [188, 1],\n",
+        "                  ('a', 'dpl'): [189, 1],\n",
+        "                  ('a', 'r0'): [184, 1],\n",
+        "                  ('a', 'r1'): [185, 1],\n",
+        "                  ('a', 'r2'): [186, 1],\n",
+        "                  ('a', 'r3'): [187, 1]},\n",
+        "     'xcsd': {    ('',): [16, 1]},\n",
+        "     'xrl': {    ('a', '#data8'): [150, 2],\n",
+        "                 ('a', '@dptr'): [151, 1],\n",
+        "                 ('a', 'dph'): [148, 1],\n",
+        "                 ('a', 'dpl'): [149, 1],\n",
+        "                 ('a', 'r0'): [144, 1],\n",
+        "                 ('a', 'r1'): [145, 1],\n",
+        "                 ('a', 'r2'): [146, 1],\n",
+        "                 ('a', 'r3'): [147, 1]}}\n"
+       ]
+      }
+     ],
+     "prompt_number": 11
     },
     {
      "cell_type": "code",
@@ -96,66 +352,7 @@
      ],
      "language": "python",
      "metadata": {},
-     "outputs": [
-      {
-       "output_type": "stream",
-       "stream": "stdout",
-       "text": [
-        "nop, reserved, reserved, reserved, reserved\n",
-        "reserved, reserved, reserved, set, clr\n",
-        "set, clr, set, clr, cpl\n",
-        "cpl, xcsd, sfa, laf, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, mov, mov\n",
-        "mov, mov, mov, anl, anl\n",
-        "anl, anl, anl, anl, anl\n",
-        "anl, orl, orl, orl, orl\n",
-        "orl, orl, orl, orl, xrl\n",
-        "xrl, xrl, xrl, xrl, xrl\n",
-        "xrl, xrl, rl, rlc, rr\n",
-        "rrc, inc, dec, inc, dec\n",
-        "add, add, add, add, add\n",
-        "add, add, add, addc, addc\n",
-        "addc, addc, addc, addc, addc\n",
-        "addc, sub, sub, sub, sub\n",
-        "sub, sub, sub, sub, subb\n",
-        "subb, subb, subb, subb, subb\n",
-        "subb, subb, pjmp, pjmp, pjmp\n",
-        "pjmp, pjmp, pjmp, pjmp, pjmp\n",
-        "pcall, pcall, pcall, pcall, pcall\n",
-        "pcall, pcall, pcall, djnz, djnz\n",
-        "djnz, djnz, cjne, cjne, cjne\n",
-        "cjne, ljmp, lcall, ret, reti\n",
-        "sjmp, jmp, jmp, cjne, jz\n",
-        "jnz, jc, jnc, jpo, jpe\n",
-        "js, jns, push, push, push\n",
-        "push, push, push, push, push\n",
-        "pop, pop, pop, pop, pop\n",
-        "pop, pop, pop, mul, div\n",
-        "da, reserved, in, out, int\n"
-       ]
-      }
-     ],
-     "prompt_number": 3
+     "outputs": []
     },
     {
      "cell_type": "code",
@@ -171,27 +368,15 @@
      ],
      "language": "python",
      "metadata": {},
-     "outputs": [],
-     "prompt_number": 2
+     "outputs": []
     },
     {
      "cell_type": "code",
      "collapsed": false,
-     "input": [
-      "float(255)/15\n"
-     ],
+     "input": [],
      "language": "python",
      "metadata": {},
-     "outputs": [
-      {
-       "output_type": "pyout",
-       "prompt_number": 13,
-       "text": [
-        "17.0"
-       ]
-      }
-     ],
-     "prompt_number": 13
+     "outputs": []
     },
     {
      "cell_type": "code",