This just got me thinking... In addition to removing stuff from objects, maybe we can add stuff?
This may not make any sense, but what if you wanted to add a custom method to an existing object.
You could make a copy, call it something else, and add your stuff.
But, what if you could merge Spin2 files into a single object?
Maybe it'd go like this:
OBJ
ser : "fullduplexserial.spin2" : "MyCustomSerialMethods.spin2"
On the surface it looks like polymorphism, but just below the surface you could just call it an "overlay", as long as you don't have any collisions of method names, but overriding another method brings some messes with it, in the above syntax there is nothing to suggest inheritance and order.
Can there be a helper function(s) to build the mode bits? The return value of which then goes into the pinmode instruction or into a var?
Those 0011_0001_00000_0 bit strings are too long, and since the underscores aren't enforced, it's easy to get out of alignment. How about where there's an underscore in the mode bits, separate that out into individual vars in the helper function?
What's nice is that if ersmith's compiler notices it's all constants and literal values, the function call would get optimized out.
Can there be a helper function(s) to build the mode bits? The return value of which then goes into the pinmode instruction or into a var?
Those 0011_0001_00000_0 bit strings are too long, and since the underscores aren't enforced, it's easy to get out of alignment. How about where there's an underscore in the mode bits, separate that out into individual vars in the helper function?
What's nice is that if ersmith's compiler notices it's all constants and literal values, the function call would get optimized out.
IMHO The less there is to learn in the basic Spin2 language the better. So far, so good:)
But the P2 is also a whole new ball game... with a lot to learn.
I think the helper function you are describing belongs in "the tool."
Help->Smart_Pins->Configure->Mode->etc.->etc.
From which one possible result is a new text file with your realized configuration.
I've seen calls for another Propeller Manual... a short introduction and description of a very extensive help structure within the PropTool itself (and/or FlexGui) might be far better.
Books are great for long plane flights... not so good cluttering up the workspace.
> @pedward said:
> On the surface it looks like polymorphism, but just below the surface you could just call it an "overlay", as long as you don't have any collisions of method names, but overriding another method brings some messes with it, in the above syntax there is nothing to suggest inheritance and order.
Yes, I was thinking it'd be just as if one of them #included the other one in it.
Or, as if the compiler just concatenated the two files into one before compiling...
It could be that duplicate names or symbols are not allowed...
Can there be a helper function(s) to build the mode bits? The return value of which then goes into the pinmode instruction or into a var?
Those 0011_0001_00000_0 bit strings are too long, and since the underscores aren't enforced, it's easy to get out of alignment. How about where there's an underscore in the mode bits, separate that out into individual vars in the helper function?
If pin modes aren't going to be assigned "friendly names" in spin, I would hope that we can have friendly names placed in an include file. Having them in the "tool" would be nice too.
When I was last picking over the PIN modes for clocked serial out, I was going cross eyed trying to ensure what I typed in was correct. I needed to change the clock divisor for Rev B silicon and it took way too long to re-learn where it was. It's not intuitive at all, but I believe it could be for the most common modes.
I suggested to Chip that the special capabilities of pins be given friendly mnemonics. Hence the DACSETUP and PWMSETUP. I suggested also to have many of these peripheral capabilities be expressed in an object oriented interface.
So DAC.SETUP(pins, mode) where mode would have constants/enums for 75_OHM, and the like.
Pins would have something similar for common use cases.
That said, for anything uncommon, an interface to just set a bit mask for mode settings, would be the preferred interface.
The OBJECT.VERB format lends itself to being easily understood and is clean to write and read. Making Spin2 easy to translate from high level to assembly language shouldn't be a primary motivating factor, Parallax's bread and butter is education, making interfaces easy to understand and use is extremely important.
That is what drove the longer mnemonics we discussed; NOUNVERB was the embodiment I suggested because it makes the code completely readable without needing to refer to the manual. PINFLOAT and PINTOGGLE are very straightforward and communicate a lot of information quickly and simply.
The OBJECT.VERB notation is an extension of NOUNVERB in a friendly way that equally satisfies CS style guidelines as well as making it easy for beginners to grasp.
The downside of the OBJECT.VERB interface is that it requires more verbosity when programming. In the NOUNVERB model you just have DAC(pin, value), since you can only write to a DAC, the verb WRITE is superfluous. With an OBJECT.VERB syntax you would do:
DAC.WRITE(pin,value)
Which is just a little more verbose, but also conveys more information to unfamiliar readers.
@cgracey
do you think it is possible to have a command or special pub (eg HPUB) to execute outside (spin2-unaware) code?
something like
HPUB HubAddress(a,b,c,...):x,y
I mean:
- Spin2 will write to hubaddress+1 a, to hubaddress+2 b, .... and then jump to hubaddress
- from here hubexec code will be executed which should preserve all cog registers (spin environment)
- at the end the foreign code will write up to 2 results in two defined cog registers and jump to a third defined cog register which is the end of the HPUB and will pass the x and y results away, along the spin code
@cgracey
do you think it is possible to have a command or special pub (eg HPUB) to execute outside (spin2-unaware) code?
something like
HPUB HubAddress(a,b,c,...):x,y
I mean:
- Spin2 will write to hubaddress+1 a, to hubaddress+2 b, .... and then jump to hubaddress
- from here hubexec code will be executed which should preserve all cog registers (spin environment)
- at the end the foreign code will write up to 2 results in two defined cog registers and jump to a third defined cog register which is the end of the HPUB and will pass the x and y results away, along the spin code
I think you could construct an object to do that, using inline assembly. For example, if the return address is in ptrb and return values should be placed in pa and pb you could do something like:
PUB CallHub(hubaddress, a, b, c) : x,y
long[hubaddress+1] := a
long[hubaddress+2] := b
long[hubaddress+3] := c
asm ' I think Chip's syntax is different, I'm using fastspin syntax
calld ptrb, hubaddress
mov x, pa
mov y, pb
endasm
> @Cluso99 said:
> Chip,
> Is pnut available for trying out spin2 yet?
No. I need to document the language. Also, I'm working on the programmer and fast loader for it now. It's getting close.
@"Dave Hein" wrote a fast loader as part of his loadp2 program, which I'm maintaining (https://github.com/totalspectrum/loadp2). @evanh and @ozpropdev wrote an SPI flash programmer that's also part of the loadp2 package. All of that code is under the MIT license, so you can take whatever bits you'd like from it.
> @Cluso99 said:
> Chip,
> Is pnut available for trying out spin2 yet?
No. I need to document the language. Also, I'm working on the programmer and fast loader for it now. It's getting close.
@"Dave Hein" wrote a fast loader as part of his loadp2 program, which I'm maintaining (https://github.com/totalspectrum/loadp2). @evanh and @ozpropdev wrote an SPI flash programmer that's also part of the loadp2 package. All of that code is under the MIT license, so you can take whatever bits you'd like from it.
Thanks, Eric. I think I might have mine done, already. I'm looking at in on the scope now. It does everything as fast as can be done using RCFAST. Once I get it cleaned up, I'll hook it into PNut.exe and see what happens.
Chip, the fast loader that I added to loadp2 was based on the MainLoader.spin2 program that you included in the FPGA zip files. You removed it from the zip file somewhere between v21 and v30. I just modified it a bit so I could pass some parameters to it.
Chip, the fast loader that I added to loadp2 was based on the MainLoader.spin2 program that you included in the FPGA zip files. You removed it from the zip file somewhere between v21 and v30. I just modified it a bit so I could pass some parameters to it.
I had forgotten all about the MainLoader program. Yes, that was how things worked for a long time. I think I removed it from the FPGA files when we got the new ROM_Booter working which uses a text-only/terminal-friendly protocol.
Here's the current interpreter. This has been a lot of fun to work on and very challenging. The code that does the Spin2 calls and returns was really difficult to work out and optimize. It took me days to spool it up if I had been away from it too long. In time, we'll find ways to improve it, I think.
Three skips > 7 after label hub_p can be made 7 or less, saving two cycles for each. Code just before that doesn't need changing but I've done it anyway below for consistency:
'
' Setup hub variable
'
hub_im getnib ad,pa,#0 'a b a: setup long[vbase][0..15]
hub_ap rfvar ad '| | c d e f g h i j k l m n o p q r s t b: setup long[dbase][0..15]
hub_pp popa ad '| | | | | | | | | | | | | | | | | | | | u v w c: setup byte[pbase + rfvar]
' d: setup byte[vbase + rfvar]
shl ad,#2 'a b | | | | | | | | | | | | | | | | | | | | | e: setup byte[dbase + rfvar]
shl x,#1 '| | | | | | | | | | | l m n | | | | | | | v | f: setup byte[pbase + rfvar][pop index]
shl x,#2 '| | | | | | | | | | | | | | | | | r s t | | w g: setup byte[vbase + rfvar][pop index]
add ad,x '| | | | | f g h | | | l m n | | | r s t u v w h: setup byte[dbase + rfvar][pop index]
' i: setup word[pbase + rfvar]
add ad,vbase 'a | | d | | g | | j | | m | | p | | s | | | | j: setup word[vbase + rfvar]
add ad,dbase '| b | | e | | h | | k | | n | | q | | t | | | k: setup word[dbase + rfvar]
add ad,pbase '| | c | | f | | i | | l | | o | | r | | | | | l: setup word[pbase + rfvar][pop index]
' m: setup word[vbase + rfvar][pop index]
hub_p mov ad,x '| | | | | | | | | | | | | | | | | | | | | | | x y z n: setup word[dbase + rfvar][pop index]
popa x '| | | | | f g h | | | l m n | | | r s t u v w x y z o: setup long[pbase + rfvar]
' p: setup long[vbase + rfvar]
mov rd,rd_long 'a b | | | | | | | | | | | | o p q r s t | | w | | z q: setup long[dbase + rfvar]
mov rd,rd_byte '| | c d e f g h | | | | | | | | | | | | u | | x | | r: setup long[pbase + rfvar][pop index]
mov rd,rd_word '| | | | | | | | i j k l m n | | | | | | | v | | y | s: setup long[vbase + rfvar][pop index]
' t: setup long[dbase + rfvar][pop index]
mov wr,wr_long 'a b | | | | | | | | | | | | o p q r s t | | w | | z u: setup byte[pop base][pop index]
mov wr,wr_byte '| | c d e f g h | | | | | | | | | | | | u | | x | | v: setup word[pop base][pop index]
mov wr,wr_word '| | | | | | | | i j k l m n | | | | | | | v | | y | w: setup long[pop base][pop index]
' x: setup byte[pop address]
mov sz,#31 'a b | | | | | | | | | | | | o p q r s t | | w | | z y: setup word[pop address]
mov sz,#7 '| | c d e f g h | | | | | | | | | | | | u | | x | | z: setup long[pop address]
mov sz,#15 '| | | | | | | | i j k l m n | | | | | | | v | | y |
_ret_ setq2 #$160 'a b c d e f g h i j k l m n o p q r s t u v w x y z (next bytecode is variable operator)
'
There are other skips > 7 starting at label op_sqrt that might be avoidable. Using unique letters immediately after ' for each skipping option is an idea I have copied (without spaces, though, to reduce line length). It would be very good if assemblers could use these comments to generate skip patterns automatically.
However, starting at op_sqrt, there are some "x x " that appear to be alternatives to "m n ". Repeating the same latter might make auto-generation a bit tricky. What does "x x" mean?
Also, should
call #.scas 'SCAS x x | | | | | | g |
alti wr 'wr m n | | | | | | | |
be this?
call #\.scas 'SCAS x x | | | | | | g |
alti wr 'wr m n | | | | | | | |
I just changed the 'call #\.scas'. That would have been a sleeper.
I will get those hub_p patterns rearranged. I was stuck thinking it wasn't possible, for some reason, so I let the word-size setups suffer, thinking they were going to be the least-commonly used.
I let those SQRT/LOG/EXP patterns be long, because I figured they were not going to be super common and the CORDIC takes lots of cycles, anyway.
Those 'x' characters within 'm' and 'n' patterns mean 'substitute the letter pattern here (a..j). It's how we get variable assignments (x += 4), both isolated and push versions. The push versions leave the written value on the stack for further operations (see y, x := (y += 5) * 3).
Chip, etc
I was just pondering about writing a python program to pre-parse the spin2 bytecode tables. for example...
' Setup hub variable
'b=====================================================================================================================================
hub_im getnib ad,pa,#0 'a b a: setup long[vbase][0..15]
hub_ap rfvar ad '| | c d e f g h i j k l m n o p q r s t b: setup long[dbase][0..15]
hub_pp popa ad '| | | | | | | | | | | | | | | | | | | | u v w c: setup byte[pbase + rfvar]
' d: setup byte[vbase + rfvar]
shl x,#2 '| | | | | | | | | | | | | | | | | r s t | | w e: setup byte[dbase + rfvar]
shl x,#1 '| | | | | | | | | | | l m n | | | | | | | v | f: setup byte[pbase + rfvar][pop index]
add ad,x '| | | | | f g h | | | l m n | | | r s t u v w g: setup byte[vbase + rfvar][pop index]
shl ad,#2 'a b | | | | | | | | | | | | | | | | | | | | | h: setup byte[dbase + rfvar][pop index]
' i: setup word[pbase + rfvar]
add ad,pbase '| | c | | f | | i | | l | | o | | r | | | | | j: setup word[vbase + rfvar]
add ad,vbase 'a | | d | | g | | j | | m | | p | | s | | | | k: setup word[dbase + rfvar]
add ad,dbase '| b | | e | | h | | k | | n | | q | | t | | | l: setup word[pbase + rfvar][pop index]
' m: setup word[vbase + rfvar][pop index]
hub_p mov ad,x '| | | | | | | | | | | | | | | | | | | | | | | x y z n: setup word[dbase + rfvar][pop index]
popa x '| | | | | f g h | | | l m n | | | r s t u v w x y z o: setup long[pbase + rfvar]
' p: setup long[vbase + rfvar]
mov rd,rd_long 'a b | | | | | | | | | | | | o p q r s t | | w | | z q: setup long[dbase + rfvar]
mov wr,wr_long 'a b | | | | | | | | | | | | o p q r s t | | w | | z r: setup long[pbase + rfvar][pop index]
mov sz,#31 'a b | | | | | | | | | | | | o p q r s t | | w | | z s: setup long[vbase + rfvar][pop index]
' t: setup long[dbase + rfvar][pop index]
mov rd,rd_byte '| | c d e f g h | | | | | | | | | | | | u | | x | | u: setup byte[pop base][pop index]
mov wr,wr_byte '| | c d e f g h | | | | | | | | | | | | u | | x | | v: setup word[pop base][pop index]
mov sz,#7 '| | c d e f g h | | | | | | | | | | | | u | | x | | w: setup long[pop base][pop index]
' x: setup byte[pop address]
mov rd,rd_word '| | | | | | | | i j k l m n | | | | | | | v | | y | y: setup word[pop address]
mov wr,wr_word '| | | | | | | | i j k l m n | | | | | | | v | | y | z: setup long[pop address]
mov sz,#15 '| | | | | | | | i j k l m n | | | | | | | v | | y |
_ret_ setq2 #$160 'a b c d e f g h i j k l m n o p q r s t u v w x y z (next bytecode is variable operator)
'e=====================================================================================================================================
'
Note that I put a delimiter line before and after the set of instructions to make it easy for the program to encode the skip info.
I am thinking that the skip bitmap could be formulated and output back into the spin2 code as a CON section with the equates for the label appended with "_skip_a" where "a" is the alpha character used in the comments for the appropriate skip.
So, for example we would get a CON section with comments picked up from the instruction code thus...
and the spin2 code for the execf table would become...
bc_setup_var_0_15 long hub_im_skip_a 'Cx * setup long[vbase][0..15]
bc_setup_local_0_15 long hub_im_skip_b 'Dx * setup long[dbase][0..15]
bc_setup_byte_pbase long hub_ap_skip_c '53 * setup byte[pbase + rfvar]
.....
meaning after a change the python program would re-run and generate or replace the CON section with new values. The execf tables would remain unchanged.
I’ve started to parse the comment section. If the first “a” instruction always begins with the comment ‘a<space> and has 3 characters a:<space> then I can pick out each sequence easily I think.
Last August I did some bytecodes and I used a different commenting method. I thought it was a little easier but it still wasn’t easy. So I think a software solution is better as it’s less prone to errors which would be hard to debug.
Would it be reasonable to expect the comment sequence of a set of skip'd instructions to begin the comment with a 2-3 character sequence
eg 3 characters '~<space>
' Address/read/write variable
'
var_rd pusha x '~ a b d a: @var
_ret_ mov x,ad '~ a | | b: read long[dbase][0..15]
'~ c: write long[dbase][0..15] (isolated)
var_wr_im getnib ad,pa,#0 '~ b c | d: read var
shl ad,#2 '~ b c | e: write var (isolated)
add ad,dbase '~ b c | f: write var (push)
alti rd '~ | | d
_ret_ rdlong x,ad '~ b | d
var_wr alti wr '~ | | e f
wrlong x,ad '~ c | e f
_ret_ popa x '~ c | e |
_ret_ zerox x,sz '~ d f (ret for d, trim+ret for f)
'
Blank lines would be ignored
Any other lines in between wiithout the '~<space> sequence would be considered a break from the skip format, so the next '!<space> sequence would be a new skip sequence.
This would make it easy to find skip sequences in the source code.
una_iso mov w,x ' m a: !!
una_psh pusha x 'push | n b: !
alti rd 'rd m n c: - (neg)
op_notb test x wz 'rd,!! m n a d: ABS
op_sqrt qsqrt x,#0 'SQRT x x | h e: ENCOD
op_log qlog x 'LOG x x | | i f: DECOD
op_exp qexp x 'EXP x x | | | j g: ONES
muxz x,_FFFFFFFF '!! x x a | | | h: SQRT
op_not not x '! x x | b | | | i: LOG
op_neg neg x '- x x | | c | | | j: EXP
op_abs abs x 'ABS x x | | | d | | |
op_ncod encod x 'ENCOD x x | | | | e | | |
op_dcod decod x 'DECOD x x | | | | | f | | |
op_ones ones x 'ONES x x | | | | | | g | | |
getqx x ' x x | | | | | | | h i j
alti wr 'wr m n | | | | | | | | | |
ret 'wr,op m n a b c d e f g h i j m: ?= var (isolated)
_ret_ mov x,w 'iso m | n: ?= var (push)
_ret_ zerox x,sz 'push n x: use a..j
I haven't checked out the code but what is the purpose of the m and n? Are they masks?
By enforcing the use of '~<space> I can pick out the sequences beginning with a... but I'm unsure about the ones beginning with m, n etc (ie not a)
Comments
This may not make any sense, but what if you wanted to add a custom method to an existing object.
You could make a copy, call it something else, and add your stuff.
But, what if you could merge Spin2 files into a single object?
Maybe it'd go like this:
It'd be sorta like a child class...
Those 0011_0001_00000_0 bit strings are too long, and since the underscores aren't enforced, it's easy to get out of alignment. How about where there's an underscore in the mode bits, separate that out into individual vars in the helper function?
What's nice is that if ersmith's compiler notices it's all constants and literal values, the function call would get optimized out.
IMHO The less there is to learn in the basic Spin2 language the better. So far, so good:)
But the P2 is also a whole new ball game... with a lot to learn.
I think the helper function you are describing belongs in "the tool."
Help->Smart_Pins->Configure->Mode->etc.->etc.
From which one possible result is a new text file with your realized configuration.
I've seen calls for another Propeller Manual... a short introduction and description of a very extensive help structure within the PropTool itself (and/or FlexGui) might be far better.
Books are great for long plane flights... not so good cluttering up the workspace.
> On the surface it looks like polymorphism, but just below the surface you could just call it an "overlay", as long as you don't have any collisions of method names, but overriding another method brings some messes with it, in the above syntax there is nothing to suggest inheritance and order.
Yes, I was thinking it'd be just as if one of them #included the other one in it.
Or, as if the compiler just concatenated the two files into one before compiling...
It could be that duplicate names or symbols are not allowed...
If pin modes aren't going to be assigned "friendly names" in spin, I would hope that we can have friendly names placed in an include file. Having them in the "tool" would be nice too.
When I was last picking over the PIN modes for clocked serial out, I was going cross eyed trying to ensure what I typed in was correct. I needed to change the clock divisor for Rev B silicon and it took way too long to re-learn where it was. It's not intuitive at all, but I believe it could be for the most common modes.
Just my $.02
So DAC.SETUP(pins, mode) where mode would have constants/enums for 75_OHM, and the like.
Pins would have something similar for common use cases.
That said, for anything uncommon, an interface to just set a bit mask for mode settings, would be the preferred interface.
The OBJECT.VERB format lends itself to being easily understood and is clean to write and read. Making Spin2 easy to translate from high level to assembly language shouldn't be a primary motivating factor, Parallax's bread and butter is education, making interfaces easy to understand and use is extremely important.
That is what drove the longer mnemonics we discussed; NOUNVERB was the embodiment I suggested because it makes the code completely readable without needing to refer to the manual. PINFLOAT and PINTOGGLE are very straightforward and communicate a lot of information quickly and simply.
The OBJECT.VERB notation is an extension of NOUNVERB in a friendly way that equally satisfies CS style guidelines as well as making it easy for beginners to grasp.
The downside of the OBJECT.VERB interface is that it requires more verbosity when programming. In the NOUNVERB model you just have DAC(pin, value), since you can only write to a DAC, the verb WRITE is superfluous. With an OBJECT.VERB syntax you would do:
DAC.WRITE(pin,value)
Which is just a little more verbose, but also conveys more information to unfamiliar readers.
--Perry
do you think it is possible to have a command or special pub (eg HPUB) to execute outside (spin2-unaware) code?
something like I mean:
- Spin2 will write to hubaddress+1 a, to hubaddress+2 b, .... and then jump to hubaddress
- from here hubexec code will be executed which should preserve all cog registers (spin environment)
- at the end the foreign code will write up to 2 results in two defined cog registers and jump to a third defined cog register which is the end of the HPUB and will pass the x and y results away, along the spin code
I think you could construct an object to do that, using inline assembly. For example, if the return address is in ptrb and return values should be placed in pa and pb you could do something like:
Is pnut available for trying out spin2 yet?
> Chip,
> Is pnut available for trying out spin2 yet?
No. I need to document the language. Also, I'm working on the programmer and fast loader for it now. It's getting close.
BMASK is a unary operator which makes a bitmask whose MSB is the lower 5 bits of the argument. For example (BMASK 7) would result in $000000FF.
I kind of agree.
Might help if you have a bus that spans over INA and INB...
Maybe like this:
Yes, that could be useful. I have a few bytecodes and longs free.
We can't use PropPlug to program P2?
You can. The P2 Eval board has the USB built-in, though. If you make your own board without USB, you'll need a PropPlug.
@"Dave Hein" wrote a fast loader as part of his loadp2 program, which I'm maintaining (https://github.com/totalspectrum/loadp2). @evanh and @ozpropdev wrote an SPI flash programmer that's also part of the loadp2 package. All of that code is under the MIT license, so you can take whatever bits you'd like from it.
The fast loader is https://github.com/totalspectrum/loadp2/blob/master/MainLoader1.spin2, and the SPI flash programmer is at https://github.com/totalspectrum/loadp2/blob/master/board/P2ES_flashloader.spin2.
Thanks, Eric. I think I might have mine done, already. I'm looking at in on the scope now. It does everything as fast as can be done using RCFAST. Once I get it cleaned up, I'll hook it into PNut.exe and see what happens.
I had forgotten all about the MainLoader program. Yes, that was how things worked for a long time. I think I removed it from the FPGA files when we got the new ROM_Booter working which uses a text-only/terminal-friendly protocol.
Three skips > 7 after label hub_p can be made 7 or less, saving two cycles for each. Code just before that doesn't need changing but I've done it anyway below for consistency:
There are other skips > 7 starting at label op_sqrt that might be avoidable. Using unique letters immediately after ' for each skipping option is an idea I have copied (without spaces, though, to reduce line length). It would be very good if assemblers could use these comments to generate skip patterns automatically.
However, starting at op_sqrt, there are some "x x " that appear to be alternatives to "m n ". Repeating the same latter might make auto-generation a bit tricky. What does "x x" mean?
Also, should
be this?
I just changed the 'call #\.scas'. That would have been a sleeper.
I will get those hub_p patterns rearranged. I was stuck thinking it wasn't possible, for some reason, so I let the word-size setups suffer, thinking they were going to be the least-commonly used.
I let those SQRT/LOG/EXP patterns be long, because I figured they were not going to be super common and the CORDIC takes lots of cycles, anyway.
Those 'x' characters within 'm' and 'n' patterns mean 'substitute the letter pattern here (a..j). It's how we get variable assignments (x += 4), both isolated and push versions. The push versions leave the written value on the stack for further operations (see y, x := (y += 5) * 3).
I was just pondering about writing a python program to pre-parse the spin2 bytecode tables. for example... results in a table as follows...
Note that I put a delimiter line before and after the set of instructions to make it easy for the program to encode the skip info.
I am thinking that the skip bitmap could be formulated and output back into the spin2 code as a CON section with the equates for the label appended with "_skip_a" where "a" is the alpha character used in the comments for the appropriate skip.
So, for example we would get a CON section with comments picked up from the instruction code thus... and the spin2 code for the execf table would become... meaning after a change the python program would re-run and generate or replace the CON section with new values. The execf tables would remain unchanged.
Last August I did some bytecodes and I used a different commenting method. I thought it was a little easier but it still wasn’t easy. So I think a software solution is better as it’s less prone to errors which would be hard to debug.
Might get some time tomorrow.
Would it be reasonable to expect the comment sequence of a set of skip'd instructions to begin the comment with a 2-3 character sequence
eg 3 characters '~<space> Blank lines would be ignored
Any other lines in between wiithout the '~<space> sequence would be considered a break from the skip format, so the next '!<space> sequence would be a new skip sequence.
This would make it easy to find skip sequences in the source code.
Your thoughts?
I've noticed these don't fit the mould I haven't checked out the code but what is the purpose of the m and n? Are they masks?
By enforcing the use of '~<space> I can pick out the sequences beginning with a... but I'm unsure about the ones beginning with m, n etc (ie not a)