Shop OBEX P1 Docs P2 Docs Learn Events
Multiple port serial driver — Parallax Forums

Multiple port serial driver

TimmooreTimmoore Posts: 1,031
edited 2008-07-02 16:38 in Propeller 1
This may be of interest if you run multiple serial ports. I have a version of fullduplexserial that supports multiple ports. The code supports 4 but I have only tested up to 3 so far. The package also contains my demo app. It runs debug port at 115200, a gps at 38400 and cmu3 camera at 116500 using 1 cog for the serial port. The package also contains modified gps object and cmucam object that using this serial port object. Those objects have also been modified to share a cog for their reading rather than having a cog each. The orginal version of this demo need 6 cogs - main, gps reader, camera reader and 3 serial ports. This version uses 3 cogs - main, gps/camera reader and 1 cog for all the serial ports.

Edit: Update the object to support CTS/RTS flow control

Edit:Fixed bug not accepting receive chars with 1 port enabled. Fixed bug with rts on ports 0,2,3

Tim

Post Edited (Timmoore) : 7/2/2008 3:18:40 AM GMT
«1

Comments

  • SpinHeadSpinHead Posts: 28
    edited 2008-06-13 07:23
    Awesome job! this made my night! would it be possible to modify it to support cts/rts on at least 1 port?
  • PraxisPraxis Posts: 333
    edited 2008-06-13 08:30
    Sweet!
  • TimmooreTimmoore Posts: 1,031
    edited 2008-06-13 16:56
    Spinhead, I will think about it. cts is pretty simple, rts is harder. Especially to do it and not slow it down. I needed 3 ports supporting 115200, I am not sure I can do this and do flow control

    Edit: I need to try it out but thinking about it I believe I can add flow control without affecting the non-flow control paths too much.
    With flow control disabled it will drop the max baudrate about 3% which means for 3 ports it should still support 115200 baud which is what I need.
    With flow control enabled its much slower probably around 25% slower, if you want 115200 you probably can only run 2 ports. So the question is what baudrate do you need your flow controlled port to run at?

    Post Edited (Timmoore) : 6/13/2008 9:09:36 PM GMT
  • SpinHeadSpinHead Posts: 28
    edited 2008-06-14 01:32
    1 nonflow needs to run @ 115200, 1 nonflow needs to run at 9600, and the flow control port needs to run @ 38400

    Thanks!
  • TimmooreTimmoore Posts: 1,031
    edited 2008-06-14 02:42
    ok. I have done the code changes. I will try and test it at the weekend. If the changes work the way I think, you can enable flow control on any or all the ports. I found another couple of optimizations in the orginal code so without flow control its no slower. It will get slower for each port with flow control, with 3 ports enabled and 1 flow control, I think it should manage 115200. It doesn't matter that only one is running at 115200. Depending on the number of ports, it limits the max baudrate but all enabled ports should be to hit that speed.
  • SpinHeadSpinHead Posts: 28
    edited 2008-06-14 14:45
    Awesome! Let me know how it goes, or if you need help testing it!
  • Jimmy W.Jimmy W. Posts: 112
    edited 2008-06-14 21:17
    Timmoore said...
    This may be of interest if you run multiple serial ports. I have a version of fullduplexserial that supports multiple ports.


    Wow, this is amazing Timmoore, I love you for this, I am going to have to do some redesigning to accommodate the fact I wont have to use 5 cogs on the prop just to run serial ports! If you have good luck with the CTS/RTS let me know, I had to put some logic before every sendstring to see if the CTS was ready before I did a sendstring and I just left RTS high and it seemed to work, just have to be super careful about long string.
  • TimmooreTimmoore Posts: 1,031
    edited 2008-06-16 01:03
    I have updated the package at the top of the thread. It should support flow control on any or all of the 4 ports. Not enabling flow control has no penalty. Enabling flowcontrol will reduce the max baud rate the ports can handle. I have tested CTS and it works. I haven't had a chance to test rts yet. I also optimized away the cost of supporting the additional ports, i.e. there is no baud rate penalty for the additonal seral ports if they are not enabled.
    Edit: CTS is an input, it will stop the driver transmitting. Normal is high and will·tx, low stops tx. mode can be used to invert the pin.
    RTS is an output, when the rx buffer gets to a threshold. Default threshold is 48 bytes (buffer is 64bytes). Pin is high when can receive, low when buffer > threshold. Again mode can invert. AddPort has a parameter to set threshold if needed (0 means use default threshold).

    Post Edited (Timmoore) : 6/16/2008 7:13:58 AM GMT
  • agodwinagodwin Posts: 72
    edited 2008-06-30 17:51
    I'm trying to use pcFullDuplexSerial4FC and am having some problems with receive. I'm very new to the propeller so am probably making some obvious newbie mistake.

    Transmit works fine, and receive works if I use FullDuplexSerial instead so I think my hardware is OK.
    But I don't ever get a character received.

    I've simplified my test code as far as possible : currently I have this (cut down from gpstest):




    con
    _clkmode = xtal1 + pll16x '
    _xinfreq = 5_000_000 '

    obj
    uarts : "pcFullDuplexSerial4FC" '1 COG for 4 serial ports

    var

    pub main | time
    waitcnt(clkfreq*3 + cnt)

    uarts.Init 'Restart serial ports to change baudrate
    uarts.AddPort(0,31,30,UARTS#PINNOTUSED,UARTS#PINNOTUSED,UARTS#DEFAULTTHRESHOLD, {
    } UARTS#NOMODE,UARTS#BAUD115200) 'Add debug port
    uarts.Start 'Start the ports

    uarts.str(0, string("Start "))

    time := cnt + clkfreq*2
    repeat
    if time < cnt
    time := cnt + clkfreq*2
    uarts.str(0, string("in "))
    uarts.dec(0, uarts.rx(0))
    uarts.newline(0)
  • TimmooreTimmoore Posts: 1,031
    edited 2008-06-30 18:08
    I will try this tonight. I dont normally receive from the debug port but from port 1 and 2 so there maybe a problem there.
  • agodwinagodwin Posts: 72
    edited 2008-07-01 08:09
    Thanks, Tim.

    I've now wired up another port (pins 0 & 1). If I call that port 1, it still doesn't receive.

    However, if I create a port 0 on pins 30 & 31, port 1 (pins 0 & 1) will then work but port 0 still won't receive.
    And I can swap those over (port 0 on 0&1, port 1 on 30,31) and port 1 still works.
    It seems that just the first port used doesn't receive.

    Hope this helps.

    -adrian

    Post Edited (agodwin) : 7/1/2008 9:44:17 AM GMT
  • TimmooreTimmoore Posts: 1,031
    edited 2008-07-01 16:10
    thanks, I got tied up hunting another debug.
  • TimmooreTimmoore Posts: 1,031
    edited 2008-07-02 03:18
    Yes, there was a bug, receive wouldn't work it there was 1 port enabled. I also found a bug with rts handling on some ports. I updated the gpstest archive with the new driver. @agodwin there is also a test program using your program sertest archive which works.
  • jazzedjazzed Posts: 11,803
    edited 2008-07-02 03:44
    This project looks awesome. I'm sending you a PM with questions; hope you don't mind.

    ▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔▔
  • agodwinagodwin Posts: 72
    edited 2008-07-02 08:57
    Thanks, Tim; that's fixed it.
    This is a really useful bit of code !
  • TimmooreTimmoore Posts: 1,031
    edited 2008-07-02 16:02
    great, question for parallax since this started from fulduplexserial whats the situation with putting it on parallax object exchange?
  • Mike GreenMike Green Posts: 23,101
    edited 2008-07-02 16:16
    There have already been variations of several drivers posted on the Object Exchange. You just have to follow the rules for posting and include the required license and copyright notice for the Object Exchange. For example, several versions of FemtoBasic include a modified FullDuplexSerial driver and there's one using a DAT section for buffers and other variables so it can be included in multiple objects without duplication, etc. Give credit for what you borrowed and take credit for your own creativity and work.
  • TimmooreTimmoore Posts: 1,031
    edited 2008-07-02 16:38
    Thanks, that makes it easy since I added a long description at the top of the file.
  • You wouldn't happen to have an older version without the flow control code in it, would you?

    I'm looking at possibly porting this to C, but I'm running tight on memory. Having a version without flow control support would save some space. I'm probably going to strip it to only contain either two, possibly three of the ports (haven't decided yet) which will also cut down on code space.

    I should probably have started with, has anyone ported this to Prop C yet?

    Jason
  • Cluso99Cluso99 Posts: 18,069
    There is a more recent 4-port serial driver IIRC.
  • More recent, yes, with more options. I want fewer, because the code will be smaller. :)
  • Duane DegnDuane Degn Posts: 10,588
    edited 2015-11-22 22:06
    JasonDorie wrote: »
    More recent, yes, with more options. I want fewer, because the code will be smaller.

    There are options with fewer features. I'll add links as I find them.

    Here's a related thread. I don't think it has any of the simplified drivers in it. I haven't found the thread I'm looking for yet.

  • I modified Tracy's version of the four port object to load from upper EEPROM. I don't think my version is a good one to use.

    ksltd posted his single port and four port serial drivers in this thread. These are the simplified versions I referred to earlier.
  • Thanks Duane - much appreciated. I'll grab these and have a look.
  • Tracy AllenTracy Allen Posts: 6,664
    edited 2015-12-09 17:09
    I'm attaching my version of the 4-port object that does not include the flow control. It's my go-to object these days, as I don't normally ever need the flow control. It would have a smaller footprint except that I added additional spin support that I usually need for my projects. Definitely removing ports will save space, but on the other hand, the object recycles some of its DAT space as data buffers after loading up the pasm COG.

    In this version I changed the pasm initialization code for the port rx and tx coroutine vectors and believe it is much more efficient at short-circuiting unused coroutines.

    revised version, please see 6 posts down.
  • Any of the funny business of overlaying DAT sections makes porting to C a little trickier (though it's still possible). I'll take a look at it - sounds like it's exactly what I'm looking for.
  • I am trying to send/recv full hex data $00-$ff as FDS and 4port FDS talk about.
    I can run sample programs and all work for text, but I don't seem to be able to send null $00.
    Is this a bug or just me?
    Thanks; GWKAUB
  • ElectrodudeElectrodude Posts: 1,657
    edited 2015-11-24 18:41
    What send method are your using? fds.str(stringptr) (and similarly, fds4.str(port, stringptr) can't send $00, since that means end-of-string, but fds.tx(txbyte) (and similarly, fds4.tx(port, txbyte)) can.
  • Tracy AllenTracy Allen Posts: 6,664
    edited 2015-11-24 21:41
    @gwkaub, If you're trying to send nulls embedded in a chuck of data, take a look (in fullDuplexSerial4pnf) at the methods,
    StrN(port,pointer,byteCount)
    or
    Packet(port, bytePointer, byteCount)
    For longer packets, the latter can be much faster than the StrN loop that repeats the method tx(port,byte). The Packet method, adapted from kltsd's serial object, uses bytemoves to get data into the serial buffer.
  • Just wanted to say thanks to everyone who pointed me at files. I've successfully ported Tracey Allen's object to C/C++. (the interface part, at least - the PASM bits are still in a Spin file) I've got two serial ports in use now. I actually have potential uses for all four.

    J

Sign In or Register to comment.