Shop OBEX P1 Docs P2 Docs Learn Events
Catalina 2.6 - a FREE C compiler for the Propeller - The Final Frontier! - Page 15 — Parallax Forums

Catalina 2.6 - a FREE C compiler for the Propeller - The Final Frontier!

1121315171820

Comments

  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-11 03:02
    Ok, latest version attached.

    Hopefully it is the latest version (I think vb.net overwrote the previous one) and hopefully when you run setup it will overwrite the previous one.

    Default is com1 and kyedos needs to be 38400 baud.

    There are a couple of new dlls and hopefully the setup will register them correctly
  • RossHRossH Posts: 5,581
    edited 2010-11-11 03:50
    Hi Dr_Acula,

    I get the attached error mesage on startup.

    Ross.
  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-11 04:00
    Ok, try this one.

    The commonest reason for that error coming up is the prop tool is open (or something else using com1).

    But it might be possible you don't have COM1. eg if you are using USB to serial port adaptors (my real com port is COM1 and the USB one registers as COM3).

    So if that is the problem, try starting this program, and if that error comes up, then go into the Settings and change the com port, and it should reload with the new port.

    Once this is working I'll port over some simple code that reads an INI file so you can save the settings.
    1024 x 768 - 66K
  • Nick MuellerNick Mueller Posts: 815
    edited 2010-11-11 09:24
    OK Ross, I'm completely lost now! 8-/

    What I need is very simple and crude (to save space):
    * a RS232 driver that can read and write. I do have my own one with c-headers that works and I have to use that one because of the stop-bit-bug in Parallax's code. Mine also supports timeout that is essential for my application.
    * a extremely primitive printf that only supports decimals and maybe hex.

    In ICC, when you linked stdio, putchar was missing. You just had to write your own code that made the connection between stdio and output (=my RS232). Just one line of code and done. I don't need a keyboard, files, etc.


    Where do I have to look at to get something working with my stuff that preferably uses (almost) nothing of the libs you supplied (except a crude printf with a putchar supplied by me).


    Thanks,
    Nick
  • RossHRossH Posts: 5,581
    edited 2010-11-11 14:36
    Hi Nick,

    You can do the same with Catalina.

    Catalina's current serial I/O capability is provided by the PC HMI. It allows you to do serial reads and writes using the normal stdio functions such as putc(), getc(), scantf() and printf(). If this functionality is not sufficent for your needs (e.g. it does not immplement timeouts) then you have a couple of options:
    1. The driver level for this functionality is provided by the files Catalina_PC_Text.Spin and Catalina_PC_Keyboard.spin in the target directory. You could simply modify these to suit your needs - this might be the simplest option.
    2. The functions putc() and getc() are the lowest level functions in the C library, and Catalina provides implementations of them which you can replace with your own (note that in most implementations of the C library, putchar(c) is simply a macro for putc(c, stdout)).
    Using either method you will get full stdio support. If you don't want full stdio support (e.g. you need to save space) then Catalina also provides a simpler set of HMI functions that you can use directly - these are described on pages 23 - 27 of the Catalina Reference Manual, and include a simplified version of printf() (called t_printf()) that would probably meet your needs. However, this would require that you use the first method (i.e. change the HMI drivers).

    As I said, the first method is probably easier, and may be more suitable for your needs - but if you choose the second method, here are some more details you will need to know:

    The current versions of putc() and getc() are in the files catalina_getc.c and catalina_putc.c in Catalina\source\lib\catalina_io (if you look at them, you will see that they themselves just use the underlying HMI functions k_wait() and t_char() - which are the low-level functions provided by all the various Catalina HMI options).

    You can replace these with your own versions. You can then either rebuild the whole library, or just recompile your new versions and then put the compiled versions in the appropriate library (note that you will need to use the same file names). For example:
    cd Catalina\source\lib\catalina_io
    [I]
    <<... edit catalina_putc.c and catalina_getc.c appropriately ...>>[/I]
    
    catalina -S catalina_putc.c catalina_getc.c
    
    [I]<<... this will generate catalina_putc.s and catalina_getc.s ...>> [/I]
    
    copy /y catalina_getc.s ..\..\..\lib\libc
    copy /y catalina_putc.s ..\..\..\lib\libc
    
    You can use this method to replace the files in libc or libci, but not in libcx (libcx uses a slighty different mechanism since it has to manage file access as well).

    Ross.
  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-11 14:36
    Ross has now got a list of things to do that is a mile long, but I think he was going to take a look at serial driver code this weekend.

    There is a very nifty dual RS232 driver in the CP/M code that has been proven to be stable over the last 6 months. I am not entirely sure about timeouts - the code works differently in that it has a large buffer, and you can call a routine to see if there are any bytes in the buffer. If there is a byte (or more), then you call another routine to read it.

    I think that works quicker that solutions using a timeout.

    We are at the sharp end of development here, so I suspect if something is not available, one or more of us has to write it! The good news though is that many things are already written but just need to be tweaked a bit.

    @ Ross, did the latest vb code work? If not, I might move the serial part of vb.net from startup to only running when you do a download. At least then you can get into the program and most things will work.

    re some of the options in the last post, these should be easy to add to the Settings part of the IDE.
  • Nick MuellerNick Mueller Posts: 815
    edited 2010-11-11 15:54
    I am not entirely sure about timeouts - the code works differently in that it has a large buffer, and you can call a routine to see if there are any bytes in the buffer.

    Dracula, there is not that much difference. I too check the buffer if it has something to read. If not, it keeps trying for x milliseconds and then gives up. In the Modbus-protocol in RTU-mode, that's the signal for end-of-message.
    My driver can have an buffer of different sizes and the ASM is changed to remove the hardcoded size by Parallax. Furthermore, I have to handle RTS in a timing-critical way to properly drive the RS485. My code has driven a mill (3 tons!) for hundreds of hours*) without hickup. Now, I have designed new Modbus-interfaces to add to the current one.

    @Ross:
    That sounds very promising! I think I'll achieve more than just the boring "Hello world!" :)

    Do you have provisions to pass a set of #defines to every compile via the command-line?


    *) alone the test-code that bombarded the interface with permutations of valid and invalid commands run for 24 hours.

    Nick
  • Nick MuellerNick Mueller Posts: 815
    edited 2010-11-11 17:44
    <<... edit catalina_putc.c and catalina_getc.c appropriately ...>>
    You can use this method to replace the files in libc or libci, ...

    Does that work:?
    I completely delete getc and putc from libc or libci and provide my own putc in the main file (or somewhere else). The linker should be happy with that.

    I didn't try that (couldn't) because:
    I modified Catalina_PC_Text and Catalina_PC_Kbd but then I realized that I really don't want to do that.
    1.) risk of overwrite with an update
    2.) other files reference these two files and need to be changed too (because I do have to provide additional parameters)

    In my eyes, that's a huge maintenance-risk. At least for me, and I don't want to take that. The changes I have to make have to be as isolated as possible.

    I need a way to provide my own say Catalina_BufferedSerial.spin and convince Catalina to compile/link/use that and not the Catalina_PC_xxx files.


    Yes I know, I suck ...

    Nick
  • RossHRossH Posts: 5,581
    edited 2010-11-11 17:46
    Dr_Acula wrote: »
    @ Ross, did the latest vb code work? If not, I might move the serial part of vb.net from startup to only running when you do a download. At least then you can get into the program and most things will work.

    Hi Dr_Acula,

    Can't try your latest code till I get home! I'll let you know later today.

    Ross.
  • RossHRossH Posts: 5,581
    edited 2010-11-11 17:48
    Do you have provisions to pass a set of #defines to every compile via the command-line?
    Nick

    Yes - see page 60 in the Catalina Reference Manual.

    Ross.
  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-11 18:04
    Darn work gets in the way of propeller time!

    Re "I need a way to provide my own say Catalina_BufferedSerial.spin and convince Catalina to compile/link/use that and not the Catalina_PC_xxx files."

    That is one of the things on Ross' ever increasing list of things we keep asking him to do!

    Specifically, I think he was going to write up some more detailed notes on how the registry works, so it will be easier for others to write their own drivers.

    Any code that does interface with catalina will need to be quite different to standard spin objects, in that there is little, if any, supporting spin code. It needs to be almost pure pasm, that can be loaded into a cog and set running. But it is the interface between this pasm code and catalina that is currently a black art that only Ross understands.

    I've even pondered taking it another level and, say, putting the video buffer a little higher in hub ram, so it frees up the bottom 2 -3k of hub ram. Then you could load in new cog code on the fly from within catalina. You could start with a generic serial driver, then your code could load a new driver. But to do that you need to know how the registry works, and not only how to register a cog, but also how to unregister a cog as well.

    Currently, I have no idea how the registry works (even having read through some code) and I'm looking forward to learning more about it.

    I agree that modifying keyboard etc code is not a great solution (though I'm just as guilty as anyone of doing that - hardly any of my code uses objects straight out of the box, which kind of negates the concept of objects as something you just plug in and use).

    There are ways around this - eg one of the CP/M emulations used the IDE to read in the entire source file for CP/M and rewrite sections of the code before resaving and recompiling. It was a solution that worked but it is messy.

    To me, a cleaner solution would be to have the standard driver code, but with a series of menu choices in an IDE (or command switches in a command line compiler) so you could choose variants. An example might be from the homemade dracblade board thread where there is a need for a keyboard driver with keys set up for a Belgian keyboard. Given there might be many combinations and permuations as more driver code is added to the C library, one would need to think about the neatest way to do this.

    I'd like to have a go writing my own driver code for something (eg a new serial object) as I think it could be useful to document the process. I don't quite feel I have the skills to do that now but hopefully soon.
  • RossHRossH Posts: 5,581
    edited 2010-11-11 18:24
    Does that work:?
    I completely delete getc and putc from libc or libci and provide my own putc in the main file (or somewhere else). The linker should be happy with that.

    I didn't try that (couldn't) because:
    I modified Catalina_PC_Text and Catalina_PC_Kbd but then I realized that I really don't want to do that.
    1.) risk of overwrite with an update
    2.) other files reference these two files and need to be changed too (because I do have to provide additional parameters)

    In my eyes, that's a huge maintenance-risk. At least for me, and I don't want to take that. The changes I have to make have to be as isolated as possible.

    I need a way to provide my own say Catalina_BufferedSerial.spin and convince Catalina to compile/link/use that and not the Catalina_PC_xxx files.


    Yes I know, I suck ...

    Nick

    Hi Nick,

    Yes, you could also simply delete putc() and getc() completely and rebuild the library, then include these in your own code as required. This would essentially duplicate the way ICC does it. Note that you may need to modify some of the build scripts or makefiles (to remove any references to catalina_putc and catalina_getc).

    Adding your own serial plugin is another option. To load that plugin at run time you need to create a new target. Here's how to do it for an LMM program (XMM is very similar):
    • The existing targets are in Catalina\target\input - the simplest is the main LMM target, called lmm_default_input.spin. Copy this to a new target file in the same directory called lmm_nick_input.spin.
    • In your modified target file (which is just a normal SPIN program) you then load and initialize your plugin. If you want to be able to specify whether or not your plugin should be loaded at compile time, surround it with #ifdef NICK ... #endif (where NICK is going to be the command-line symbol we will use for your plugin). The simplest one already there is probably the CLOCK plugin. Search for all instances of CLOCK and duplicate what it does (using NICK instead of CLOCK, obviously).
    • In the directory Catalina\target there will be a file called catalina_default.s - you need to copy this to catalina_nick.s - this file allows you to include your own LMM PASM routines as part of the target (you probably won't need this capability, but the file has to exist).
    Now compile your program with a command like the following:
    catalina -t nick -D NICK -lc hello_world.c
    
    The -t nick tells Catalina to use your new target, and the -D NICK tells that target to include your plugin.

    The good thing about creating your own plugins (and targets that use them) is that you won't lose your work even if you copy a new release of Catalina over the existing release.

    Now what could be easier? :lol:

    Ross.
  • RossHRossH Posts: 5,581
    edited 2010-11-11 19:28
    @All,

    Going through the process of adding a new Catalina target for Nick (see post above) made me realize that I could reduce the learning curve to almost zero simply by adding a new standard plugin target that does nothing except load a dummy plugin (which in a fit of originality I will probably call PLUGIN) - which in turn does nothing except accept a command sent via the registry (which I will no doubt wrap up in a C function called call_plugin() or something equally imaginative :)).

    It's easy enough to do, and would also satisfy the promise I made to document the use of the registry a bit better. I will include this in the next release.

    Ross.
  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-11 20:10
    That sounds an interesting idea.

    Ok, how do I pass a value to a dummy plugin, and how do I get a value back?

    Thinking about this more, I think you only ever need one value. eg for a serial port driver, pass the value which points to a list of values, which in the existing code is a few longs and then the buffer. So if you know your driver has 5 longs then 64 bytes, all you need is the start of that list.

    I like the idea of a dummy plugin!

    Hmm - what if there are two or more dummy plugins, can we do that?
  • RossHRossH Posts: 5,581
    edited 2010-11-11 20:31
    Dr_Acula wrote: »
    That sounds an interesting idea.

    Ok, how do I pass a value to a dummy plugin, and how do I get a value back?

    Thinking about this more, I think you only ever need one value. eg for a serial port driver, pass the value which points to a list of values, which in the existing code is a few longs and then the buffer. So if you know your driver has 5 longs then 64 bytes, all you need is the start of that list.

    I like the idea of a dummy plugin!

    Hmm - what if there are two or more dummy plugins, can we do that?

    I will include an example C function that invokes the underlying registry services, specifying the dummy plugin as the target. The dummy plugin will accept the request, but do nothing with it except return a dummy status.

    The registry is optimized to speed up the two commonest forms of communications - the first is a request with a single parameter of up to 24 bits (this is also known as a "short" request), the second is a request with a full 32 bit parameter - which may itself be a pointer to a block containing addiitonal parameter data (this is known as a "long" request).

    As for adding two or more plugins to a target - once you have seen how to do one, doing more than one is actually very trivial. What complicates the existing targets (till they are almost unreadable) is just how many platforms they support, and how many incompatible ways there are to combine the various plugins and libraries for those platforms! Catalina tries quite hard to protect you from the most obvious problems (e.g. linking with the floating point libraries that expect the floating point plugins to be loaded, then forgetting to load the plugins. Or linking with the extended library but forgetting to load the SD Card plugin. Or trying to load a video driver on CPU #2 of the TriBladeProp. Etc etc).

    Ross.
  • Nick MuellerNick Mueller Posts: 815
    edited 2010-11-12 02:10
    Now what could be easier?

    At least, that's the cleanest way to do it.
    The changes are as local as possible and done by adding my new files. And not by changing foreign supplied files.


    Once more, thanks a lot!
    Nick
  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-12 02:50
    Yes, already I can see clever things you could do with a generic plugin. Consider a keyboard plugin - you could do that with a short request (24 bit) - one byte to ask "have you got anything" and if positive, another byte contains the ascii value.

    At a very simple level, serial ports could work the same way. Pass a few bits that say which serial port (00,01 etc), a bit to send or receive, and it returns a bit to say true or false a value is present and another byte with the value. Easily possible in 24 bits.

    VT100 code - well that is just a series of bytes and the cog code sorts out what the escape sequences mean (pullmoll has written one in pasm).

    The LCD driver code is a bit more complex as it needs to share latches with the memory so it needs to halt memory access while outputting bytes. But cluso's code can be modified to do this with a 24 bit value.

    I'm looking forward to this!

    On another topic, I modified the IDE so it only opens the serial port for a download, then closes it again afterwards. So at least you can get into the program and try things out, even if there is a problem with the serial port. New IDE attached.
  • PaxiPaxi Posts: 10
    edited 2010-11-12 16:23
    Hi, again. First thanks for the link with I/O Pin Definition.
    I managed to move on with the driver and the program works so far and reads the bitstream from every button pressed. I did some documentation (mostly for myself) and will add a .doc file with everything explained in detail if the drivers are finished, since I´m doing this for a project. But most of you probably don´t need much documentation to understand the above code (unless it was quite difficult to me..). Btw it´s a bit hard to read it in the
    segment because of the comments etc., so better copy it to some kind of text editor with highlighting if you are interested in it.
    [code]
    #include <stdio.h>
    #include <catalina_cog.h>
    
    
    void main()
    {	unsigned i;
    	unsigned reg;
    	unsigned savereg;
    	unsigned LOW = 0;
    	unsigned CLKPIN_MASK = 0x8;                                  			//P3 on HYDRA 00000100 = 8 = 0x8
    	unsigned LATCHPIN_MASK = 0x10; 								 			//P4 on HYDRA 00001000 = 16 = 0x10
    	unsigned DATAPIN_MASK = 0x20;								 			//P5 on HYDRA 00010000 = 32 = 0x20
    	
    	
    	/*
    		Setting I/O
    	*/
    	_dira(CLKPIN_MASK | LATCHPIN_MASK | DATAPIN_MASK, CLKPIN_MASK | LATCHPIN_MASK);    
    	/*
    		00000100 | 00001000 | 00010000 = 00011100 => Pins 3,4,5 are affected
    		&
    		00000100 | 00001000 = 00001100 & 00011100 => 000011000 => Pins 3,4 == 1 (OUTPUT) Pin 5 == 0 (INPUT) other Pins not affected
    	*/
    	
    	/*
    		Setting OUTPUT to LOW/HIGH
    	*/	
    	_outa(LATCHPIN_MASK, LOW); 
    	/*
    		00010000 & 0000000 = 0000000 => P5 is LOW (0) now
    	*/
    	
    	while(1)  {
    		_outa(LATCHPIN_MASK, LATCHPIN_MASK);
    		
    		//Set LATCH HIGH
    		_waitcnt(_cnt() + 500);
    		
    		//Wait till Counter reaches _cnt() + 500
    		//reg = (_ina() & DATAPIN_MASK) ? 0 : 1;
    		
    		if(DATAPIN_MASK & _ina() ) {
    			reg = 0;
    			printf("if %x\n", reg);
    			}
    		else 
    		{
    		reg = 1;
    		printf("else %x\n", reg);
    		}
    		//printf("out %x\n", reg);
    		_waitcnt(_cnt() + 500);
    		//Reads first bit inside _ina(), show 0 or 1
    		_outa(LATCHPIN_MASK, LOW);
    		//set LATCH LOW ("clear")
    		
    		for(i = 0; i<8; i++) {
    		
    			/*reads the 7 bits left vom CLK(PULSE) Line
    			set CLK HIGH first
    			wait
    			shift bits into reg (i tried this one, not sure how it works exactly with shifting i+1 and not 1 only)
    			set CLK LOW again
    			wait*/
    		
    		
    			_outa(CLKPIN_MASK, CLKPIN_MASK);
    			
    			_waitcnt(_cnt() + 500);
    			//reg |= (_ina() & DATAPIN_MASK ? 0 : 1) << (i+1);
    			
    			if(DATAPIN_MASK & _ina()) {
    				savereg = reg;
    				reg = 0 << (i+1);
    				reg = savereg | reg;
    			}else {
    				
    				savereg = reg;
    				reg = 1 << (i+1);
    				reg = savereg | reg;
    				}
    			_outa(CLKPIN_MASK, LOW);
    			_waitcnt(_cnt() + 500);
    		}
    		switch(reg)
    		{
    		case 0x1:	
    			printf("KEY A IS PRESSED\n");
    			break;
    		case 0x2:
    			printf("KEY B IS PRESSED\n");
    			break;
    		case 0x4:
    			printf("KEY SELECT IS PRESSED\n");
    			break;
    		case 0x8:
    			printf("KEY START IS PRESSED\n");
    			break;
    		case 0x10:
    			printf("KEY UP IS PRESSED\n");
    			break;
    		case 0x20:
    			printf("KEY DOWN IS PRESSED\n");
    			break;
    		case 0x40:
    			printf("KEY LEFT IS PRESSED\n");
    			break;
    		case 0x80:
    			printf("KEY RIGHT IS PRESSED\n");
    			break;
    		default:
    			printf("NO KEY PRESSED\n");
    			break;
    		
    		
    		
    	}
    	//printf("%x\n", reg);
           _waitcnt(_cnt() + 1000000);
    		
    				
    	}
    	
    	/*
    			
    	  A = 0x1 = 00000001 = 1
    	  B = 0x2 = 00000010 = 2
    	  SELECT = 0x4 = 00000100 = 4
    	  START =  0x8 = 00001000 = 8
    	  UP = 0x10 = 00010000 = 16
    	  DOWN = 0x20 = 00100000 = 32
    	  LEFT = 0x40 = 01000000 = 64
    	  RIGHT = 0x80 = 10000000 = 128
    
    	
    	*/
    
    
    
    
    }
    
    
    

    Well the code above works but there is another problem I encountered respectively i have some questions left.
    My goal is to use this driver with a game I´m programming afterwards.
    My first question is:
    I haven´t tried it so far since i haven´t started programming the game yet. But would it be possible to upload the driver as it is on cpu 1 and upload the game on cpu2 and use the driver for the game without doing any kind of interprocess communication myself? I know every cog has their own registers but I´m not sure if it proably works anyway.
    Second question:
    I first want to use the driver in the same C File as my game and therefore i can´t run the driver in the loop. So i guess i have to use some kind of interrupt controller. The games runs in the loop and if the signal 0x1 comes from P5 f.e the corresponding Interrupt Service Routine is executed and returns to the game again afterwards. Thats the theory but how could I realise this?
    I found the function int _waitpeq(unsigned mask, unsigned result, int a_or_b); in the doc but I don´t know how to implement it in the way i need it. It would be very nice if you could give me one example for an Interrupt Request and the corresponding Service Routine according to my code.
    Probably it is also possible to split the code in some functions and use a .h file to include it but since the driver has to run all the time and check for incoming signals in the loop I wasn´t sure about how to realise that either :confused:

    Thanks in advance again

    Regards Paxi
  • RossHRossH Posts: 5,581
    edited 2010-11-12 16:46
    Dr_Acula wrote: »
    On another topic, I modified the IDE so it only opens the serial port for a download, then closes it again afterwards. So at least you can get into the program and try things out, even if there is a problem with the serial port. New IDE attached.

    Hi Dr_Acula,

    I can compile programs ok, but I can't download them even when I set the COM port correctly - I just get an "Error opening serial port message". But if I take the binary and download it manually using Payload to the same com port, it works ok.

    Also, I can only seem to open and compile files from C:\Program Files\Catalina\demos - is the path hardcoded?

    Ross.
  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-12 16:53
    Ross will hopefully be online soon.

    I'm looking forward to the generic plugin and in anticipation of this I re-read the catalina manual.

    I found this comment "Plugins are a very versatile solution since they can interact with the Catalina C program at run time - but they can be complex to develop"

    Agreed, especially with code like the dracblade where any additional latch driver code must be integrated with the ram driver code. (That is the most complex of things on the wish list, so possibly leave it till last).

    But underneath that, on page 44, is this "Load a compiled PASM program into a cog"

    This goes on to talk about a program called "test_spinc.c" which I found in the folder "c:\program files\catalina\demos\spinc"

    There is this text "Catalina provides a _coginit() function that works in a very similar manner to the corresponding SPIN or PASM coginit operations - i.e. it is used to load a binary PASM program into a cog for execution."

    and that I think is exactly what I would like to do.

    With and SD card, it is easy to have multiple binary images of compile cog programs that you could load in and out on the fly.

    The part that I am interested in is how to pass parameters. 24bits will be just fine.

    The spinc program has this
    /*
     * This is an example of how to format data to be passed tothe cog program 
     * (via the usual PAR parameter). Note this is an example only - the flash_led 
     * cog program does not actually expect any data.
     */ 
    unsigned long data[] = { 1, 2, 3 };
    

    So what I would be interested in is a tiny demo program, where you pass three values like above, the cog program adds one to each value, and then returns them.

    If you could do that, then you can grow a program from there.

    But I'm not entirely clear how coginit works. In the example, it appears the code is converted into a .h file, and then is included in the compilation. So I don't think that allows loading/running cogs from within a C program on the fly.

    In the manual is also "Writing an LMM PASM function that can be called directly from C"

    which may also be useful, though not directly to me at the moment as I am more interested in real pasm running at full speed.

    So the next question - can catalina load and unload cogs from within C? The steps as I would see it would be to have a precompiled binary file sitting on an sd card, and the ability to move this into a certain location in hub ram in order to execute the instruction that moves it into the cog. And then a 24 or 32 bit interface.

    If catalina can do this, then a demo program to add one to a value (? and to set a flag somewhere in the 24 bits to say it is done) would be very useful.

    But if this cannot be done, then it will still be very useful to load in cog programs on startup and set them running forever. The description in the plugin section has a bet both ways by saying "...but they can be complex to develop" and then saying "Most standard Parallax drivers can be easily converted into plugins."

    I hope it is the latter!
  • RossHRossH Posts: 5,581
    edited 2010-11-12 17:01
    Paxi wrote: »
    My goal is to use this driver with a game I´m programming afterwards.
    My first question is:
    I haven´t tried it so far since i haven´t started programming the game yet. But would it be possible to upload the driver as it is on cpu 1 and upload the game on cpu2 and use the driver for the game without doing any kind of interprocess communication myself? I know every cog has their own registers but I´m not sure if it proably works anyway.
    Second question:
    I first want to use the driver in the same C File as my game and therefore i can´t run the driver in the loop. So i guess i have to use some kind of interrupt controller. The games runs in the loop and if the signal 0x1 comes from P5 f.e the corresponding Interrupt Service Routine is executed and returns to the game again afterwards. Thats the theory but how could I realise this?
    I found the function int _waitpeq(unsigned mask, unsigned result, int a_or_b); in the doc but I don´t know how to implement it in the way i need it. It would be very nice if you could give me one example for an Interrupt Request and the corresponding Service Routine according to my code.
    Probably it is also possible to split the code in some functions and use a .h file to include it but since the driver has to run all the time and check for incoming signals in the loop I wasn´t sure about how to realise that either :confused:

    Hi Paxi,

    I haven't looked at your code yet (but I will when I get time!). However, to answer your other questions ...

    Yes, you can run this program as a function on another cog - for examples on how to do this, look in the Catalina\demos\multicog directory. A more sophisticated and easier to use multi-cog/multi-thread library will be included in the next release, but the techniques demonstrated in that directory will work for what you need to do, and will still be supported in the next release.

    Every cog has their own registers (and local variables), but all cogs can share global variables - just be careful about access these from multiple cogs - use a lock if you need to ensure only one cog is accessing the global variables at once (only usually necessary for writes). Also (as you will see in the "multicog" examples) some library code is not currently "cog-safe" - such as the HMI calls - and will need to be protected this way.

    In general, on the Prop you don't use interrupts, not should you try and simulate them - if the driver is running in another cog it simply does it's thing and puts its results in a global variable - in the other cogs you simply "poll" this variable - polling is a real "no no" when you are on a single cpu architecture, but not on the Propeller - it is one of the advantages of the Prop architecture that you never need to mess about with interrupts.

    To summarize - rewrite your driver as a function, and simply start it on another cog. Write the results to one or more global variables and read these in your main function.

    See the "dining philosophers" example in the multicog directory for a fully worked example.

    Ross.
  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-12 17:03
    RossH, yes the directories are hard coded but that can be changed if you want.

    Re the serial port, I've only got it working for COM1. Are you using COM1 or another port?
  • RossHRossH Posts: 5,581
    edited 2010-11-12 17:09
    Hi Dr_Acula,

    I had hoped to post an example "dummy" plugin and target that loads it later today.

    Yes, Catalina can load and unload plugins on the fly. It could load the binaries from SD cards if you wrote all the necessary file management code (open the file, read the binary contents into a hub memory buffer etc).

    Yes, you can pass parameters to such plugins on startup (therafter you normally communicate via the registry - although many plugins also communicate via one or more Hub RAM buffers whose address is passed to them as a startup parameter).

    I will try and incorporate all this into one fully worked example ... if I get time!

    Ross.
  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-12 17:27
    Many thanks. Meanwhile, I'm deep inside the serial port code - I have always used it on com1 but I think it needs to be a lot more flexible and be able to work on any com port. So I'm adding that code at the moment.

    Addit: Ok, got some code. The serial port drivers are not easy to deal with - they default to COM1 and if you happen to be using a USB to serial device they won't work.

    I think this code is the right one. It has been tested on com1 which is my real serial port, and on com3 which is my usb serial port.

    To test, try Settings/Available Ports and that should produce a list of ports. Then try testing one with Settings/Test Com Port. Then try changing to a different port number with Settings/Com Port. Hopefully if that works it will download correctly.

    If not then more debugging is required!
  • RossHRossH Posts: 5,581
    edited 2010-11-13 21:16
    Dr_Acula wrote: »
    Many thanks. Meanwhile, I'm deep inside the serial port code - I have always used it on com1 but I think it needs to be a lot more flexible and be able to work on any com port. So I'm adding that code at the moment.

    Addit: Ok, got some code. The serial port drivers are not easy to deal with - they default to COM1 and if you happen to be using a USB to serial device they won't work.

    I think this code is the right one. It has been tested on com1 which is my real serial port, and on com3 which is my usb serial port.

    To test, try Settings/Available Ports and that should produce a list of ports. Then try testing one with Settings/Test Com Port. Then try changing to a different port number with Settings/Com Port. Hopefully if that works it will download correctly.

    If not then more debugging is required!

    Ok - some progress. I got it to download correctly, and got a "file OK (some corrected) errors"

    But then I get a whole heap of rubbish on the screen. The last thing I see is an attempt to execute "hello.bin" (which is the file I compiled and downloaded) but the file is not found.

    Am I missing a step?

    Ross.
  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-14 01:41
    I'd be hoping for no errors on a xmodem download, but at least you have the serial port working.

    The 'hidden' code after a download is
    LineOfText = "Spin Catlyst2.bin" + vbCr ' run the serial version of catalyst

    and then a 5 second delay and then

    LineOfText = UCase(filename_noextension) + vbCr ' and run the program

    Do you have catlyst2.bin on the sd card? (It is simply catlalyst compiled to talk to the serial port rather than the vga, which is why nothing appears on the screen)
  • RossHRossH Posts: 5,581
    edited 2010-11-14 14:13
    Dr_Acula wrote: »

    Do you have catlyst2.bin on the sd card? (It is simply catlalyst compiled to talk to the serial port rather than the vga, which is why nothing appears on the screen)

    Hi Dr_Acula,

    That would explain it. I was out last night - I'll try this out tonight.

    Ross.
  • RossHRossH Posts: 5,581
    edited 2010-11-15 01:43
    RossH wrote: »
    Hi Dr_Acula,

    That would explain it. I was out last night - I'll try this out tonight.

    Ross.

    Success! Program compiled, downloaded and run!

    One thing - I noticed that even if I select COM2, the program continues to try to use COM1 (and I get the usual exception thrown) unless I also do "Test Com Port". After that it seems to works ok.

    Ross.

    P.S. If you used "payload" as your download program instead of xmodem, you won't need to have either KyeDos or Catalyst installed.
  • Dr_AculaDr_Acula Posts: 5,484
    edited 2010-11-15 02:12
    Great news.

    Well, if it needs a test of the com ports to kick start things, then I could just put that in the startup code and it could happen in the background.

    I'll need to add an INI so you can save the settings.

    Can you explain more about how payload works? How would the download work for instance? Does it save to the sd card? Would I need to write some different driver code in vb.net, and if so, what does the protocol look like? And can you change the baud rate (for some reason I can't seem to get anything to work at 115200, either usb to serial adaptors or real serial. It is a mystery as I understand the proptool downloads at 115200. I've pondered a startup routine that tries comms at different rates then picks the fastest one, a bit like fax machine protocols).
  • RossHRossH Posts: 5,581
    edited 2010-11-15 02:30
    Dr_Acula wrote: »
    Great news.

    Can you explain more about how payload works? How would the download work for instance? Would I need to write some different driver code in vb.net, and if so, what does the protocol look like? And can you change the baud rate (for some reason I can't seem to get anything to work at 115200, either usb to serial adaptors or real serial. It is a mystery as I understand the proptool downloads at 115200. I've pondered a startup routine that tries comms at different rates then picks the fastest one, a bit like fax machine protocols).

    You don't need to know the innards of payload - just use it! Use a "system" function call (or whatever the vb.net equivalent is to just execute a command line). E.g. after you compile "hello.c" into "hello.binary", just execute payload hello. For normal binaries, payload simulates the Propeller downloader, so it should work on any platform. You can set the baud rate and com port if you want (e.g. use a command like payload -b 38400 -p 2 hello) but payload normally sorts all this out for you automatically.

    The only complication is that if your program is an XMM program (instead of an LMM program) you have to first download XMM loader (which is in the utilities folder by default, or you can copy it elsewherer) - but you can do this all in one payload command, such as payload ..\utilities\XMM hello.

    Ross.
Sign In or Register to comment.