Shop OBEX P1 Docs P2 Docs Learn Events
Simpleide simpletools problem? — Parallax Forums

Simpleide simpletools problem?

Up until recently I have been using libfdserial and libsimpletext without any problems. I am using a program that that uploads data via serial to my Raspberry Pi. On the SimpleIDE side the program runs as expected, but on the Raspberry Pi side,using Python, I have to use decode() on the incoming data. This is where the problem lies, ..."can't decode byte 0xea in position 0"... Not sure what is causing this problem? Any help will be appreciated.

Thanks
Ray

Comments

  • RsadeikaRsadeika Posts: 3,837

    Doing some more investigation, using the P2 and implementing jm_fullduplexserial.spin2, the problem with the Python decode() went away. I am guessing that the Simpleide C version of FullDuplexSerial function has something that the decode() can not deal with. I wonder what would be the best way to get around this would be. Since Simpleide has gone quiet, as far as updating is concerned, I am not holding my breath.

    If FlexC was able to do some WiFi, like handling and creating a WEB page, I would probably change over to FlexC, but I am not holding my breath on this one either. Everything seems to be so scattered and on usable.

    Ray

  • iseriesiseries Posts: 1,492

    Since I don't know what the program on P1 is doing it's hard to determine what is going on.

    I looked through the code in fdserial and there is nothing in there that prevents it from sending 0xea.
    The P2 does not work like the P1 so the code to send data is nothing like the P1.

    To test this out I wrote this program:

    /**
    * @brief Simple serial test program
    * loop serial data back to terminal
    */
    
    #include "simpletools.h" 
    #include "propeller.h"
    #include "fdserial.h"
    
    
    int i;
    fdserial *f;
    
    
    int main()
    {
      f = fdserial_open(17, 16, FDSERIAL_MODE_NONE, 9600);
    
      for (i=0;i<256;i++)
        fdserial_txChar(f, i);
    
      fdserial_close(f);
    
      while (1)
      {
        high(0);
        pause(1000);
        low(0);
        pause(1000);
      }    
    }
    

    On the receiving side I used XCTL to capture the serial data:

    You can see all the data came through with no issues from P1 to my computer.

    Sending binary data through serial is a bad idea.

    Also, you don't need a full duplex driver to send data as the data can only be transmitted at the rate you are sending it at. You need a full duplex driver to receive data if the program will be off doing something else when the data arrives.

    Mike

  • RsadeikaRsadeika Posts: 3,837

    Below is the Simpleide program, code is kind of messy, but you can get an idea of what is going on. This program is also working a WEB page, when I look at the C program part, I try to think of how I can simplify it. I added a part where I am sending data to the P2, to see if the work around is working.

    Ray

    /*
      sol_sta_1.c
    
    */
    #include "simpletools.h"
    #include "simpletext.h"
    #include "fdserial.h"
    #include "adcDCpropab.h"
    #include "wifi.h"
    
    
    serial *p2_1;
    serial *rpi4;
    
    
    /** Variables **/
    volatile float vw, vx, vy, vz;
    /* WiFi */
    int event, id, handle;
    int getFromPageId;
    char cmdStr[64];
    char *path;
    
    /* Subs */
    void rpi4_comm();
    void perifs();
    
    void menu();
    
    int main()
    {
      // Add startup code here.
      rpi4 = fdserial_open(2, 3, 0, 115200);
    
      cog_run(rpi4_comm,128);
      //rpi4 = fdserial_open(2, 3, 0, 115200);
      pause(150);
      cog_run(perifs,128);
      pause(150);
    
      char inBuff[40];
    
      wifi_start(31, 30, 115200, WX_ALL_COM);
      pause(50);
      getFromPageId = wifi_listen(HTTP, "/tpfm*");
    
    
      while(1)
      {
        // Add main loop code here.
        wifi_poll(&event, &id, &handle);
        if(event =='G')
        {
          if(id == getFromPageId)
          {
            memset(cmdStr, 0, sizeof(cmdStr));
            sprint(cmdStr, "PATH:%d\r", handle);
            path = wifi_command(cmdStr);
    
            if(strstr(path,"/Solar1") !=0)
            {
              wifi_print(GET, handle, "%.2f",vw);
            }
            else if(strstr(path,"/batarray") !=0)
            {
              wifi_print(GET, handle, "%.2f",vx);
            }                    
            else if(strstr(path,"/batfld") !=0)
            {
              wifi_print(GET, handle, "%.2f",vy);
            }       
          }              
        }
    
        else if(event == 'P')
        {
    
        }         
    
      }  
    } 
    
    /******************************************/
    
    /** Cores(COGs) **/
    
    /** Comms with RPi4 **/
    /*
      This works with a program on the RPi 4.
    */
    void rpi4_comm()
    {
      char inBuff[40];
      //rpi4 = fdserial_open(2, 3, 0, 115200);
      p2_1 = fdserial_open(0,1,0,115200);
    
      while(1)
      {
       /* writeStr(rpi4,"> ");  
        readStr(rpi4,inBuff,40);
        if(!strcmp(inBuff,"help")) menu();
        else if(!strcmp(inBuff,"solar array"))
        {
          writeFloatPrecision(rpi4,vw,4,2);
          writeStr(rpi4," Volts\n");
        }
        else if(!strcmp(inBuff,"battery array"))
        {
          writeFloatPrecision(rpi4,vx,4,2);
          writeStr(rpi4," Volts\n");
        }
        else if(!strcmp(inBuff,"flooded battery"))
        {
          writeFloatPrecision(rpi4,vy,4,2);
          writeStr(rpi4," Volts\n");
        }     
        else
        {
          writeStr(rpi4,"??\n");
        } */
    
        /* Stream data to RPi4*/
        /* Solar panel array */
       /* writeChar(rpi4,'S');
        writeChar(rpi4,'1');
        writeChar(rpi4,',');
        writeFloatPrecision(rpi4,vw,4,2);
        writeStr(rpi4,"\n");
    
        /* Battery array */
       /* writeChar(rpi4,'B');
        writeChar(rpi4,'1');    
        writeChar(rpi4,',');
        writeFloatPrecision(rpi4,vx,4,2);
        writeStr(rpi4,"\n"); */
    
        /* Flooded Battery */
       /* writeChar(rpi4,'B');
        writeChar(rpi4,'2');    
        writeChar(rpi4,',');
        writeFloatPrecision(rpi4,vy,4,2);
        writeStr(rpi4,"\n"); */
    
        /* Battery array voltage is less than 12.4 V. */   
        //if( vx < 12.4  )
        // {
        //    writeChar(rpi4,'0');
        //    writeStr(rpi4,"\n");
        //    pause(150);
        //    //writeFloatPrecision(rpi4,vx,4,2);
        //    writeDec(rpi4,vx);
        //    writeStr(rpi4,"\n");
        // }
         /* Battery array voltage is greater than 13.7 V */
        // if( vx > 14.4 )
        // {
         //   writeChar(rpi4,'3');
        //    writeStr(rpi4,"\n");
         //   pause(150);
            //writeFloatPrecision(rpi4,vx,4,2);
         //   writeDec(rpi4,vx);
         //   writeStr(rpi4,"\n");
         //}
         //writeChar(rpi4,0);
         //writeStr(rpi4,"\n");
    
         //writeDec(rpi4,13);     
    
         /* Flooded battery voltage is less than 12.0V. */ 
         //if( vy < 12.0 )
         //{
         //   writeChar(rpi4,'1');
         //   writeStr(rpi4,"\n");
         //   pause(150);
            //writeFloatPrecision(rpi4,vy,4,2);
         //   writeDec(rpi4,vy);
         //   writeStr(rpi4,"\n"); 
         //}
         /* Flooded battery voltage is greater than 13.7 V*/
         //if( vy > 13.7 )
         //{
           //writeStr(p2_1,"%de\n",vx);
           writeFloatPrecision(p2_1,vx,4,2);
           //writeDec(p2_1,vx);
           writeStr(p2_1,"\n"); 
           //writeStr(rpi4,"\n");
         //fdserial_txChar(rpi4,0);
         //fdserial_txChar(rpi4,10);
         //fdserial_txChar(rpi4,13);
    
         //  pause(150);
           //writeFloatPrecision(rpi4,vy,4,2);
         //  writeDec(rpi4,vy);
         //  writeStr(rpi4,"\n"); 
        // } 
    
          /* Solar array is greater than 17.0V. */
         // if( vw >= 19.0 )
         // {
         //    writeChar(rpi4,'2');
          //   writeStr(rpi4,"\n");
         //    pause(150);
             //writeFloatPrecision(rpi4,vw,4,2);
         //    writeDec(rpi4,vw);
         //    writeStr(rpi4,"\n"); 
         // }   
    
          //writeChar(rpi4,'1');
          //writeStr(rpi4,"\n");                
        pause(2000);
      }    
    }
    
    /***************/
    void perifs()
    {
      float v0, v1, v2, v3;
      adc_init(21, 20, 19, 18);
      pause(50);
    
      while(1)
      {
        /* Calculate the AD value for the battery array. */
          v0 = adc_volts(0);
          pause(150);
          vx = (v0*5.1058);
          //vx = (v0);
          //print("%.2f",vx);
    
          /*Calculate the AD value for flooded battery. */
          v1 = adc_volts(1);
          pause(150);
          vy = (v1*4.9570);
          //vy = (v1);
          //vyc=vy;
    
          /* Calculate the AD value for solar array*/
          v2 = adc_volts(2);
          pause(150);
          vw = (v2*5.2040);
          //vw = v2;
        //pause(500);
    
      }    
    }
    
    /***************/
    
    /** Subroutines **/
    void menu()
    {
      writeStr(rpi4,"\n          System Menu\n");
      writeStr(rpi4,"help - Show the System Menu.\n");
      writeStr(rpi4,"solar array - Solar array Volts.\n");
      writeStr(rpi4,"battery array - Battery array Volts.\n");
      writeStr(rpi4,"flooded battery - Flooded battery Volts.\n"); 
    }  
    
    /***************/
    
  • RsadeikaRsadeika Posts: 3,837

    Below is the Python program that I am uploading the data to. It will get a lot more complicated than what it looks like right now.

    Ray

    # sol_sta42.py
    #
    #
    #
    import asyncio
    from kasa import SmartPlug
    
    import time
    import datetime
    import serial
    
    port = "/dev/ttyS0"
    baud = 115200
    ser = serial.Serial(port,baud)
    
    print("solsta42.py program")
    ser.close()
    time.sleep(.250)
    ser.open()
    
    ingtext=0
    
    def get_time():
       global now
       now = datetime.datetime.now()
    
    
    async def main():
       p = SmartPlug("192.168.35.129")
       await p.update()
       print(p.alias)
    
       while True:
          gtext = ser.readline()
          ingtext = gtext.decode().strip("\n")  # Get data from P2
          #print(ingtext)
    
          if ingtext <= "12.50":
             await p.turn_on()
          if ingtext >= "14.50":
             await p.turn_off()
    
    
    
    
    if __name__ == "__main__":
        asyncio.run(main())
    
    
  • iseriesiseries Posts: 1,492

    Some time ago I tried to do serial to my RPi and had issues where sometimes random characters where being received.

    I see that you are using a Wifi module and wondering if it might be simpler to send the serial data through the Wifi module over your network to the RPi.

    MIke

  • RsadeikaRsadeika Posts: 3,837

    I was also thinking along those lines at some point, but I could not figure out how to do it. I am not that well versed in javascript and Sockets. When I looked into doing javascript tasks, that really boggled my brain. Plus, I am not sure about the WiFi module and how big of a program it could hold. The other thing that I am now thinking about is, is there a limitation with the Simpleide WiFi function as it pertains to using javascript.

    The other problem that started to occur, with the WiFi module is that something is changing the IP address of the WiFi module. Not sure if it is the TP-Link router or something else. I tried to see if I could lock in the IP address via the WiFi module setup, but I did not see how it could be done.

    Ray

  • RsadeikaRsadeika Posts: 3,837

    Below is the html program that I am using with the WiFi module. Even this is getting to be a complicated mess.

    Ray

    <!-- sol_sta1.html -->
    <!DOCTYPE HTML>
    
    <html>
        <head>
            <style>
                a{
                    background-color:#637aad;
                    color:white;
                    font-size:23px;
                    margin:5px;
                    width:100px;
                    height:55px;
                    cursor:pointer;
                    padding-top:4px;
                    padding-bottom:4px;
                }
                a:hover{background-color:white;color:navy;
            </style>
        </head>
        <body bgcolor=3b5898>
            <font face="Arial" size=3 color="cyan">
                <div align="center">
                    <h1> Home Station One</h1>
                </div>
    
            <h2> Outside Units </h2>
            <h> Solar Panel Array </h>
            <br>
            <br>
            <a onclick="getFromMcu('Solar1')">Main Array</a>
            <br>
            <p id = "SAValue">Waiting: </p>
    
    
            <h2> Inside Units </h2>
    
            <h> Batteries </h>
            <br>
            <br>
            <h> Battery Array </h>
            <br>
            <br>
            <a onclick="getFromMcu('batarray')">Battery Array</a>
            <br>
            <p id = "BAValue">Waiting: </p>
            <br>
            <h> Flooded Battery </h>
            <br>
            <br>
            <a onclick="getFromMcu('batfld')">Fld Battery</a>
            <br>
            <p id = "BFValue">Waiting: </p>
            <br>
            </div>
    
            </font>
        </body>
    
    <script>
    var getPathExt;
    
    function useMcuReply(response)
    {
        if(getPathExt == 'Solar1')
        {
        var val = document.getElementById("SAValue");
        val.innerHTML = "Value: " + response;
        }
        else if(getPathExt == 'batarray')
        {
        var val = document.getElementById("BAValue");
        val.innerHTML = "Value: " + response;
        }
        else if(getPathExt == 'batfld')
        {
        var val = document.getElementById("BFValue");
        val.innerHTML = "Value: " + response;
        }
    
    }
    
    function getFromMcu(pathExt)
    {
        getPathExt = pathExt;
        httpGet("/tpfm/" + pathExt, useMcuReply);
    }
    
    function httpGet(path, callback)
    {
        var req = new XMLHttpRequest();
        req.open("GET", path, true);
        req.onreadystatechange = function()
        {
            if(req.readyState == 4)
                if(req.status == 200)
                    callback(req.responseText);
                else
                    callback("Wating...");
        }
        req.send(null);
    }
    function httpPost(path, param)
    {
        var req = new XMLHttpRequest();
        req.open("POST", path, true);
        req.setRequestHeader("Content-type",
        "application/x-www-form-urlencoded");
        req.send(param);
    }
    
    </script>
    </html>
    
    
  • iseriesiseries Posts: 1,492

    Did you try and run Putty on RPi to see what the data looks like coming from the P1?

    Mike

  • RsadeikaRsadeika Posts: 3,837

    Yes I ran Putty and serial port terminal and what I got was not what I was sending. Just got some weird characters. Now I am wondering if it is Python on the rpi that is the culprit. I do not have any way of putting a win 10 machine in place of the rpi. This is starting to get complicated just to find the fault.

    Ray

  • iseriesiseries Posts: 1,492

    Well, I broke out my Raspberry Pi 3 and hooked up a few wires to the serial interface and ran this program:

    /**
    * @brief Simple serial test program
    * loop serial data back to terminal
    */
    
    #include "simpletools.h" 
    #include "propeller.h"
    #include "fdserial.h"
    
    
    int i;
    fdserial *f;
    
    
    int main()
    {
      f = fdserial_open(15, 14, FDSERIAL_MODE_NONE, 115200);
    
      for (i=0;i<256;i++)
        fdserial_txChar(f, i);
    
      fdserial_close(f);
    
      while (1)
      {
        high(0);
        pause(1000);
        low(0);
        pause(1000);
      }    
    }
    

    On the Pi side I used putty since that what I know and after setting the baud rate to 115200 got the following screen shot:

    Serial seems to work just fine.

    Also a about a year ago I wrote this program using Visual Studio:

    #include <stdio.h>
    #include <stdlib.h>
    
    #include "wiringPi.h"
    #include "wiringSerial.h"
    
    int sr;
    
    
    int main(int argc, char const *argv[])
    {
        int c;
    
        sr = serialOpen("/dev/ttyS0", 115200);
        if (sr < 0)
        {
            printf("Serial Port not Open\n");
            return -1;
        }
    
        wiringPiSetup();
    
        while (1)
        {
            c = serialGetchar(sr);
            if (c >= 0)
            {
                serialPutchar(sr, c);
                printf("%c", c);
            }
            else
            {
                fflush(stdout);
                delay(1);
            }
        }
    
        serialPuts(sr, "The quick red fox jumped over the lazy brown dog\n");
    
        serialClose(sr);
    
        return 0;
    }
    

    That also worked as well.

    Mike

  • RsadeikaRsadeika Posts: 3,837

    Thanks Mike for looking into some of this stuff. I created a work around for the time being.

    The Activity WX board is gathering some data and maintaining the WEB page. It is also uploading some data to the P2 Edge. This is using C.

    The P2 Edge is uploading the data to the rpi 4. This is using FlexBasic.

    The rpi 4 is developing the data that it has received. This is using Python.

    So, is it possible that somewhere I will introduce some bugs. I am still thinking about involving the three micro.bit boards that I have, into this system. Not sure how that will be done. This is using using microPython. Still thinking about having a private network, that is not available to the internet. So, how do I simplify all of this.

    Ray

  • iseriesiseries Posts: 1,492

    Maybe you should turn things around.

    From the RPi 4 you can make a connection to the WiFi board using telent and just send commands to the P1 which would then return the answers.

    No serial would be needed to do that.

    The RPi 4 should be able to do a web page or start a webserver that can process the requests.

    This would be easy to test from the RPi4 using putty at first and then build an app from that.

    Mike

Sign In or Register to comment.