Shop OBEX P1 Docs P2 Docs Learn Events
Jump table across page boundries — Parallax Forums

Jump table across page boundries

toru173toru173 Posts: 17
edited 2006-05-13 16:35 in General Discussion
I'm looking at the SX28 as the basis of an interpreter, and I have read a few of the posts on these forums relating to this particular usage. I noted, however, that all suggestions result in fairly small instruction sets so that the "jump table" method can be used to interpret them without crossing page boundries. I am wondering if there is a quick and easy way to get around this problem? My goal is to interpret a fairly high-level language, with instructions such as "write character to screen"or something. Please take into account that I've never touched an SX in my life, but I have read a little about them ^_^

My thinking brought me to this;

(I refer to the 'secret' opcodes - specifically "pushPC" listed here: http://sxlist.com/techref/ubicom/secrets.htm)

The 12bit offset to the start of the code corrosponding to the "opcode" to be interpreted is stored in a list. You would then execute an IREAD relative to the opcode (0-255) and the page at which your list starts, a pushPC then a RETP (in that order)

My understanding is that the IREAD will store the destination address in the M and W registers, the pushPC will then put these registers on the stack, and then the RETP will pop them from the stack into the PC. Is this correct? Is there an easier way of doing this?

Thankyou in advance

Comments

  • Peter VerkaikPeter Verkaik Posts: 3,956
    edited 2006-05-13 09:25
    It would be easier to just create a jumptable that directly jumps to the
    appropiate code.
    For example:
    mov w,opcode
    add pc,w
    jmp code_opcode0
    jmp code_opcode1
    etc.
    All main entries must then be in the lower half of a single page.
    If one page is not enough (most likely) then just do for some opcodes
    code_opcode0:
    jmp @code_opcode0_entry
    to jump to another page. Return from each code with a retp

    You could also double the opcode at the start like this:
    mov w,opcode
    add w,opcode
    add pc,w
    jmp @code_opcode0
    jmp @code_opcode1
    etc.
    but I expect this takes more codespace.

    regards peter
  • toru173toru173 Posts: 17
    edited 2006-05-13 10:34
    Say I have 256 (the full byte) opcodes. This means that, for whatever method, I will need two pages to occupy the entire jump table. This means that unfortunatly those methods are out. I was hoping to get around this, but I suppose testing the highest bit and setting the page accordingly would work. Is there no other alternative?
  • Peter VerkaikPeter Verkaik Posts: 3,956
    edited 2006-05-13 10:44
    You can have a simple test at the start:
    org $200
    cjae opcode,#67,@jumptable2 ;example value = start opcode in next jump table
    mov w,opcode
    add pc,w
    ;jumptable1 for opcodes 0-66

    org $400
    jumptable2:
    mov w,opcode
    sub w,#67
    add pc,w
    ;jumptable2 for opcodes>=67

    You can extend this to more pages.
    But I don't think you will reach 256 opcodes as there is only
    2K codespace in a SX28. For 256 routines that would be 8 words per routine,
    not counting the jumptables.
    If you limit the opcodes to 127 then at most two jumptables are required.

    Edit: actually, with 127 opcodes
    you can use a single jumptable:
    ;w loaded with opcode
    org $200
    add w,opcode ;double opcode
    add pc,w
    jmp @code0 ;address $202
    jmp @code1

    The full lower half of the page can hold 127 jmp@



    regards peter

    Post Edited (Peter Verkaik) : 5/13/2006 10:59:03 AM GMT
  • Peter VerkaikPeter Verkaik Posts: 3,956
    edited 2006-05-13 12:38
  • toru173toru173 Posts: 17
    edited 2006-05-13 15:49
    Thankyou for those links, Peter. The second was what motivated me to join this forum and post this problem, but your smallc interpreter is very interesting. In that discussion you made the following comment:

    Other problem, the switch statement reads the address to jmp to
    using iread. It looks the only way to do this jump is the use of a
    secret instruction and reti

    This is similar to the method I had imagined, I think. Could you please show me what you were refering to?

    As to why I might need so many opcodes; I had intended to implement a subset of the JVM on the SX. I'm a big fan of the Lego RCX robotics and there has been a port of the JVM to the H8 at the centre of the robot (LeJOS - I think it stands for "Lego Java Operating System", but I believe it also means "far" in spanish) and the code availible is quite easy to understand. Even if I'm not able to squeeze the entire JVM into the memory availible (I am aiming for the stack manipulation operations and the JVM equivilent of the SX native instructions, at least), I would still have a very rich and well-documented language to program with.

    What you suggested in your previous post (starting "You can have a simple test at the start:") is what I had thought necessary. I would like to avoid this method though because it limits the amount of code movement availible to me. At the very least, thankyou for verifying that method for me ^_^

    I'd also like to thank you for your quick and knowledgable responses. You're helping me to learn more about this chip then the datasheet could have told me - for example, it took me a while to work out the meaning of the @ symbol in front of some of the addresses in your code, but now that I know of it I'm sure I will use it often. Thankyou!
  • Peter VerkaikPeter Verkaik Posts: 3,956
    edited 2006-05-13 16:35
    Talking about subset of JVM. This has been done by parallax using an SX48 and is known as Javelin.
    http://www.parallax.com/javelin/index.asp
    No way this is possible using an SX28 otherwise parallax may have done so.

    Smallc has alot smaller memory footprint than JVM, but then it also lacks
    some nice features of java. Smallc can be used with an SX28 as I showed in the first link
    I provided. Problem is that smallc as a language has no knowledge of ports, memory maps
    and all other sx features. That makes writing native compiled code (sx assembler)
    difficult, as there are many restrictions for the written code.

    The switch table as generated by the smallc compiler has the following layout:
    For each 'case' value there are 2 16bit entries: a code address (label) and compare value (case value).
    The last 2 16bit entries in this table are 0 ('default') and an address (default label).

    As the SX does not have a JMP M:W instruction, and there is no access to the call stack,
    the only way to jump to some label address indirectly, is by using secret sx instructions.
    However, for an interpreter, you can avoid this, because I showed in the bytecode interpreter thread,
    that all address references (labels) are within the generated table of tokens, that will represent
    your compiled code.

    I have attached my java class for the smallc interpreter as it shows how to interpret the
    smallc generated table. If you have specific question about this java program, please
    do so in the javelin forum.

    If you have specific questions about the smallc files I posted, please do so in the
    appropiate thread.



    regards peter
Sign In or Register to comment.