PDA

View Full Version : Running Native Code with ImageCraft C



jazzed
04-22-2008, 11:41 AM
Being able to run native pasm in ImageCraft C should allow us to get existing asm drivers up in short order.

Below is one way to run native pasm on a cog in ImageCraft C. Don't know if there is another way. Something more elegant would be desirable.·ImageCraft will be adding a parameter variable to cognew_native so we can communicate with the pasm.

Creating the pasm array will require dumping the .binary file, removing the header, and formatting as a C array then stuffing it into a file to be included in·a cog loader .c module. Hopefully someone can write a utility that does the conversion.·Being able to·preserve code in it's existing form by adding a cookie like·0xbabeface in the asm would be useful. This would be in lieu of hacking out spin methods, etc.



/**
* @file native.c
* Demonstrates running native propeller opcodes defined as an array from C.
*/
#include <propeller.h>

//undef USE_NATIVE to use LMM toggleBit function in a cog
#define USE_NATIVE

#ifdef USE_NATIVE
long longArr[] = {
0xa0ffecff, // mov dira, #$ff
0x6cffe8ff, // loop xor outa, #$ff
0x5c7c0001 // jmp #loop
};
#else
long toggleStack[10];
void toggleBit(void) {
asm("mov dira, #$ff");
while(1) {
asm("xor outa, #$ff");
}
}
#endif

void main(void) {
#ifdef USE_NATIVE
_coginit_native(4, (void*)&longArr);
#else
cognew(toggleBit, toggleStack);
#endif
while(1); // don't let program terminate
}


·Added missing toggleStack in·undef USE_NATIVE case·4-22.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
jazzed·... about·living in·http://en.wikipedia.org/wiki/Silicon_Valley (http://en.wikipedia.org/wiki/Silicon_Valley)

Traffic is slow at times, but Parallax orders·always get here fast 8)

Post Edited (jazzed) : 4/22/2008 4:11:20 PM GMT

ImageCraft
04-22-2008, 01:55 PM
Wow, thanks! You are really "jazzed" about this, aren't you? (ha ha) Thanks! The Propeller community is just awesome. This is one reason why I decided we will publish the source code to the LMM kernel, because if we don't, it just means that it will take someone to swap coffee break time with disassembling time http://forums.parallax.com/images/smilies/smile.gif

First of all, at the production release, you can add an assembly .s file to your project that contains pure COG code and you can launch that. So you don't have to do it the hard way.

Second, if you want to do this before the facility is available, google for things like bin2hex and you should find some utility out there.

Ym2413a
04-22-2008, 06:03 PM
I wonder if there is a way in insert a block of ASM code in ImageCraft C. :)

So instead of:



asm("mov dira, #$01");
asm("mov dira, #$02");
asm("mov dira, #$03");




You could do something sort of like:



#ASM
mov dira, #$01
mov dira, #$02
mov dira, #$03
#END ASM




I guess this is more of a shortcut if anything, but it could help when writting large blocks of ASM code into your C programs.
Thanks everyone!

--Andrew Arsenault.

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
Share the knowledge: propeller.wikispaces.com (http://propeller.wikispaces.com)
Lets make some music: www.andrewarsenault.com/hss (http://www.andrewarsenault.com/hss)

jazzed
04-23-2008, 12:30 AM
Andrew,
It's not what you want exactly, but something like this appears to work:



void toggleBit(void)
{
int time;
int per = 16*12;
asm("\n\
mov dira, #$ff \n\
mov %time, cnt \n\
add %time, %per \n\
");
while(1) {
asm(" \
xor outa, #$ff \n\
waitcnt %time, %per \n\
");
}
}


▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
jazzed·... about·living in·http://en.wikipedia.org/wiki/Silicon_Valley (http://en.wikipedia.org/wiki/Silicon_Valley)

Traffic is slow at times, but Parallax orders·always get here fast 8)

Rayman
04-23-2008, 01:22 AM
This would be very nice! Is this a way to get the VGA driver working?

Harrison.
04-23-2008, 01:45 AM
I used this method and now have a vga signal! I'm still implementing the rest of the functions (print, newline, etc) so that it will actually be useful.

I did have to use an intermediate cog so I could access the coginit instruction directly (so I could pass a par to the new cog). This is a bit messy, but it seems to work well enough for now.

Harrison

jazzed
04-23-2008, 03:02 AM
Harrison. said...
I used this method and now have a vga signal!
...
Yee ha! http://forums.parallax.com/images/smilies/roll.gif·:)

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
jazzed·... about·living in·http://en.wikipedia.org/wiki/Silicon_Valley (http://en.wikipedia.org/wiki/Silicon_Valley)

Traffic is slow at times, but Parallax orders·always get here fast 8)

ImageCraft
04-23-2008, 03:41 AM
Harrison. said...
I used this method and now have a vga signal! I'm still implementing the rest of the functions (print, newline, etc) so that it will actually be useful.

I did have to use an intermediate cog so I could access the coginit instruction directly (so I could pass a par to the new cog). This is a bit messy, but it seems to work well enough for now.

Harrison


Probably no need to use another cog just as a middle-person, you can add your own function:

// function prototype, add to the file that references the function
int my_cognew_native(void (*func)(int), int par);


Add a .s file to the project file list, and write something like:
.area text(rom, rel)
_my_cognew_native::
shr R0,#2
shl R0,#4 ; get function address into the right place
shr R1,#2 ; get par into the the right place
shl R1,#18
or R0,R1
COGINIT R0 WR WC WZ
IF_C neg R0,#1
@FRET

not tested, but something like it should work....

Ariba
04-23-2008, 05:51 AM
Here is a tested code with a function to start a new assembly cog:



#include "Propeller.h"

int cognew_asm(void* addr, int* param);

int asmcode[] = {
0x08BC19F0, //rdlong R1,par
0xA0FC1601, //mov R0,#1
0x2CBC160C, //shl R0,R1
0xA0BFEC0B, //mov dira,R0
0xA0FC1A01, //mov R2,#1
0x2CFC1A18, //shl R2,#24
0xA0BC19F1, //mov R1,cnt
0x80BC180D, //add R1,R2
0x6CBFE80B, //blink: xor outa,R0
0xF8BC180D, //waitcnt R1,R2
0x5C7C0008 //jmp #blink
};

void main()
{
int ledpin = 16;
cognew_asm(&asmcode, &ledpin);
}

int cognew_asm(void* addr, int* param)
{
asm("mov R4,%param");
asm("andn R4,#3");
asm("shl R4,#14");
asm("or R4,%addr");
asm("shl R4,#2");
asm("or R4,#8");
asm("coginit R4 wr wc");
asm("if_c neg R4,#1");
asm("mov R0,R4");
}




Just change the ledpin variable to use other Pins.

I also tried it with a .s file and the assembly source in the coments above. But the jmp #blink does not jump to the right location, because an ORG 0 is not possible. Then I tried jmp #8, but this produce a jmp #0 in the binary, and I tried jmp #blink-asmentry (with an asmentry label at begin), but that is not accepted by the Compiler.
I think we need first a detailed description of the ICC Prop Assembler and it's possibilities.

The code for starting a new cog is a bit different from what ImageCraft has suggested in the previous post, but I have done it before I have read that.

Andy

EDIT: The code above seams not do work with more then 1 cog, I don't know why !

Post Edited (Ariba) : 4/23/2008 2:19:41 AM GMT

jazzed
04-28-2008, 01:57 PM
Anyone having luck with the VGA driver?

▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
jazzed·... about·living in·http://en.wikipedia.org/wiki/Silicon_Valley (http://en.wikipedia.org/wiki/Silicon_Valley)

Traffic is slow at times, but Parallax orders·always get here fast 8)