IMO, the ideal situation for educational use would be a compiler that compiles C to Spin bytecodes and that allows C programs to call Spin library methods directly, without having to translate them to C++ first and then back again to PASM.
Look here! -> David Betz SpinWrap program allows calling spin library methods directly without translating them. It provides a standard C or C++ interface to the spin interpreter. It only needs to be included in the build process. Clear functional example here. Why am I repeating myself?
I would like to see a C compiler that compiled to spin bytecodes also. I don't really care how fast it would run. The beauty of that solution is not having to include an interpreter in the C program (the bloat) or require a mailbox interface (the obfuscator).The problem is, such a compiler essentially needs to be written from scratch unless OpenSpin supported curlys.
David mentioned a "Student IDE" ... that is possible with the Learn library. Maybe that's a good test case for a QtQuick Android app.
I admire your perseverance, Dave. But your resulting "Spin bytecode" C programs will execute slower even than CMM (the slowest C currently implemented on the Propeller). And they will probably end up larger as well.
The threaded chess program is about the same size in both CMM and Spin at around 13K. However, you are correct that CMM is faster than Spin. It's about 3 to 4 times faster. The problem with Spin is that the interpreter had to be crammed into the 2K of cog RAM, and much of the time is spent in decoding byte-codes and setting up self-modifying code. The interpreter could probably run twice as fast if the cogs had 4K of memory. Another problem is that the Spin VM is stack-based rather than register-based. This results in a lot of hub RAM access.
With that said, there are some nice features of Spin, such as the relocatable nature of the object code. This allows binary blobs to be loaded anywhere in memory and relocated just by adjusting the 5 state variables in the header. The spinix OS is built around this feature. It's also convenient that the Spin interpreter is available from ROM, which saves 2K of hub RAM space.
Look here! -> David Betz SpinWrap program allows calling spin library methods directly without translating them.
My bad. My first impression of SpinWrap was that the Spin objects went through the spin2cpp process.
I would like to see a C compiler that compiled to spin bytecodes also.
I'm glad we can agree on something!
I thihnk Dave has it right with cspin: a preprocessor that compiles C to Spin source. That eliminates the issue of the bytecodes being undocumented. One possible issue is how deeply it parses the C code before generating the Spin source. IOW, does it catch all programmer errors, or can it generate bad Spin code and rely on the Spin compiler to catch those errors? In the latter case tracking back to the C source to generate an informative error message could be difficult. But I suspect that, since Dave wrote it, all the error checking is done in cspin.
I might try to incorporate cspin into the Propeller Tool via a Perl wrapper -- the same technique I used for the AutoDoc program. One issue would be the PropTool editor's syntax highlighting getting really weird with C source.
I might try to incorporate cspin into the Propeller Tool via a Perl wrapper -- the same technique I used for the AutoDoc program. One issue would be the PropTool editor's syntax highlighting getting really weird with C source.
One possible issue is how deeply it parses the C code before generating the Spin source. IOW, does it catch all programmer errors, or can it generate bad Spin code and rely on the Spin compiler to catch those errors? In the latter case tracking back to the C source to generate an informative error message could be difficult. But I suspect that, since Dave wrote it, all the error checking is done in cspin.
For the most part cspin just translates C syntax to Spin syntax, and it doesn't do extensive error checking. It does compile a list of variables and their attributes, so it does catch errors related to incorrect pointer dereferencing or invalid struct elements. At some point I want to parse statements so I can handle operator precedence correctly, and also generate floating-point function calls. This will require more extensive error checking.
Another problem is that the Spin VM is stack-based rather than register-based. This results in a lot of hub RAM access.
An CMM is register-based? I thought register-allocation became a lost art with the rise of stacks and stack frames. But it does make more sense in an architecture like the Prop's.
Avoiding the stack by using registers is one of the first things done when optimizing in most decent compilers (at least the C/C++ ones I've seen/worked with).
Memory is just too damn slow, even Cache is dozens of times slower than registers in modern architectures. As I recall, for recent Intel architectures, register access = 1 clock, L1 cache (32-128k) = 5-7 clocks, L2 cache (256-512k) = 20-40 clocks, L3 cache (1-8MB) = 80-120 clocks, DDR3 Memory = 200-500+ clocks. L1 and L2 are per core, L3 is shared. The numbers are probably off (but not by much), but I think you get the idea of the perf differences.
Can't help with the Spin part, however for a simpler C, why not look at David's Pico C?
Just came across it while trying to find a decent Forth comparison thread.
An CMM is register-based? I thought register-allocation became a lost art with the rise of stacks and stack frames. But it does make more sense in an architecture like the Prop's.
PropGCC uses a stack and registers. However, once a value is loaded into a register the optimizer will try to keep intermediate results in registers rather than writing them to the stack. In Spin, the statement "A := B + C" results in 9 rdxxxx/wrxxxx instructions. In optimized C there should just be 3 rdxxxx/wrxxxx instructions. If the variables were defined as register variables there would be zero rdxxxx/wrxxxx instructions.
Can't help functions Spin part, however for a simpler C, why not look at David's Pico C?
It's not clear how useful that would be. I added propeller hardware access functions which work, but including pasm code isn't possible without requiring an xmmc device > typical propeller 64KB eeprom size.
An CMM is register-based? I thought register-allocation became a lost art with the rise of stacks and stack frames. But it does make more sense in an architecture like the Prop's.
My problem is similar but from the other direction. I'm all C for teaching. After a few meetings of the basics, students browse the Parallax catalog and want to buy products (e.g. INA219) but sample code is only in SPIN. I think it would be good for sales to have a policy that every product has sample programs in all of PBASC, SPIN and C before offered for sale. (If not possible, like I2C in BS2, a txt file that explains that).
Doing all these additions sounds like a good intern project for the summer.
I've not tried David's wrapper, I will this afternoon. But it is a work-around to a problem that would not exist if code in all three languages were supplied.
Comments
Look here! -> David Betz SpinWrap program allows calling spin library methods directly without translating them. It provides a standard C or C++ interface to the spin interpreter. It only needs to be included in the build process. Clear functional example here. Why am I repeating myself?
I would like to see a C compiler that compiled to spin bytecodes also. I don't really care how fast it would run. The beauty of that solution is not having to include an interpreter in the C program (the bloat) or require a mailbox interface (the obfuscator).The problem is, such a compiler essentially needs to be written from scratch unless OpenSpin supported curlys.
David mentioned a "Student IDE" ... that is possible with the Learn library. Maybe that's a good test case for a QtQuick Android app.
With that said, there are some nice features of Spin, such as the relocatable nature of the object code. This allows binary blobs to be loaded anywhere in memory and relocated just by adjusting the 5 state variables in the header. The spinix OS is built around this feature. It's also convenient that the Spin interpreter is available from ROM, which saves 2K of hub RAM space.
I'm glad we can agree on something!
I thihnk Dave has it right with cspin: a preprocessor that compiles C to Spin source. That eliminates the issue of the bytecodes being undocumented. One possible issue is how deeply it parses the C code before generating the Spin source. IOW, does it catch all programmer errors, or can it generate bad Spin code and rely on the Spin compiler to catch those errors? In the latter case tracking back to the C source to generate an informative error message could be difficult. But I suspect that, since Dave wrote it, all the error checking is done in cspin.
I might try to incorporate cspin into the Propeller Tool via a Perl wrapper -- the same technique I used for the AutoDoc program. One issue would be the PropTool editor's syntax highlighting getting really weird with C source.
-Phil
Anything is possible with open source
-Phil
Memory is just too damn slow, even Cache is dozens of times slower than registers in modern architectures. As I recall, for recent Intel architectures, register access = 1 clock, L1 cache (32-128k) = 5-7 clocks, L2 cache (256-512k) = 20-40 clocks, L3 cache (1-8MB) = 80-120 clocks, DDR3 Memory = 200-500+ clocks. L1 and L2 are per core, L3 is shared. The numbers are probably off (but not by much), but I think you get the idea of the perf differences.
Just came across it while trying to find a decent Forth comparison thread.
It's not clear how useful that would be. I added propeller hardware access functions which work, but including pasm code isn't possible without requiring an xmmc device > typical propeller 64KB eeprom size.
Doing all these additions sounds like a good intern project for the summer.
I've not tried David's wrapper, I will this afternoon. But it is a work-around to a problem that would not exist if code in all three languages were supplied.