Serial Receiving from Arduino to Raspberry Pi with PySerial stops after a while

后端 未结 5 804
小蘑菇
小蘑菇 2021-01-04 19:09

I\'m working on a project in which I have to receive some 25 character data at a time in order to process it in Raspberry Pi. Here is the example code that generates some da

相关标签:
5条回答
  • 2021-01-04 19:27

    I used to get this a lot, and then a friend told me to prompt the arduino for data from python.

    Description below


    consider having the arduino only send data when prompted by your python program:

    prompt.py

    #!/usr/bin/python
    import serial, time
    ser = serial.Serial('/dev/ttyACM0',  115200, timeout = 0.1)
    
    #if you only want to send data to arduino (i.e. a signal to move a servo)
    def send( theinput ):
      ser.write( theinput )
      while True:
        try:
          time.sleep(0.01)
          break
        except:
          pass
      time.sleep(0.1)
    
    #if you would like to tell the arduino that you would like to receive data from the arduino
    def send_and_receive( theinput ):
      ser.write( theinput )
      while True:
        try:
          time.sleep(0.01)
          state = ser.readline()
          print state
          return state
        except:
          pass
      time.sleep(0.1)
    
    f = open('dataFile.txt','a')
    
    while 1 :
        arduino_sensor = send_and_receive('1')
        f.write(arduino_sensor)
        f.close()
        f = open('dataFile.txt','a')
    

    prompt.ino

    void setup () {   pinMode(13, OUTPUT);   Serial.begin(115200); } 
        void loop() {
    
      if (Serial.available())    {
    
         ch = Serial.read();
    
         if ( ch == '1' ) { 
           Serial.println(analogRead(A0)); // if '1' is received, then send back analog read A0
         } 
         else if (ch == '2') {    
           digitalWrite(13,HIGH); // if '2' is received, turn on the led attached to 13
         } 
         else if (ch == '3') {
           digitalWrite(13,LOW); // if '3' is received then turn off the led attached 13
         } else {
           delay(10);
         }
       }    
    }
    

    Also, I made a github repository that has some further examples for python-arduino communication:

    https://github.com/gskielian/Arduino-DataLogging/blob/master/PySerial/README.md

    0 讨论(0)
  • 2021-01-04 19:28

    Try sudo rasbpi-config, choose interface option, say 'no' to first message ("kernel login"), 'yes' to second message ("serial communication on"). I found if the first message is on it throws errors. Saying 'no' fixes it.

    0 讨论(0)
  • 2021-01-04 19:29

    I had the same problem and was breaking my head for a good time, try this

    Run

    ps -ef | grep tty
    

    If the output looks anything like

    root      2522     1  0 06:08 ?        00:00:00 /sbin/getty -L ttyAMA0 115200 vt100
    

    Then you need to disable getty from trying to send data to that port

    In order to use the Raspberry Pi’s serial port, we need to disable getty (the program that displays login screen) by find this line in file /etc/inittab

    T0:23:respawn:/sbin/getty -L ttyAMA0 115200 vt100
    

    And comment it out by adding # in front of it

    #T0:23:respawn:/sbin/getty -L ttyAMA0 115200 vt100)
    

    To prevents the Raspberry Pi from sending out data to the serial ports when it boots, go to file /boot/cmdline.txt and find the line and remove it

    console=ttyAMA0,115200 kgdboc=ttyAMA0,115200
    

    Reboot the Raspberry Pi

    Credit where credit is due: http://blog.oscarliang.net/raspberry-pi-and-arduino-connected-serial-gpio/ helped me figure out how to diable getty

    0 讨论(0)
  • 2021-01-04 19:36

    I had to struggle with this when reading gps data in raspberry pi. The output would stop after about 10seconds and report

     device reports readiness to read but returned no data (device disconnected?)
    

    The solutions given in almost all forums are for raspberry pi 2 with wheezy. I finally managed to get continuous gps streaming in my raspberry pi3 with jessie by doing the following:

    1. set enable_uart=1 and add dtoverlay=pi3-disable-bt in /boot/config.txt. then reboot
    2. I had to change my /boot/cmdline.txt to

      dwc_otg.lpm_enable=0 console=tty1 console=serial0,9600 root=/dev/mmcblk0p7 rootfstype=ext4 elevator=deadline fsck.repair=yes rootwait

      then reboot

    3. stop getty: sudo systemctl stop serial-getty@ttyAMA0.service

      to disable: sudo systemctl stop serial-getty@ttyAMA0.service

    You need to be careful with the /boot/cmdline.txt. Any mistake in the file may make your raspberry pi to not boot. It is better keep a backup of the file before editing. Also set the baud rate properly. In my case, it was 9600. Hope this helps!

    0 讨论(0)
  • 2021-01-04 19:43

    During your loop function in your Arduino code you never end an newline char \n, this is only a problem with ser.readline() because it reads until a \n character.

    During your setup function you correctly send a \n character which could explain the intial value being sent, but not the data.

    perhaps modifying your Arduino code like this:

    void loop(){
        for(i=0;i<25;i++){
            for(a=0;a<i;a++){
                if((a==9)||(a==19)||(a==24)) {
                  Serial.print('l');
                } else {
                    Serial.print('d');   
                }
            } /*end for loop a*/
            for(b=0;b<25-i;b++){
                Serial.print('l');
            } /*end for loop b*/
    
            Serial.print('\n'); // CODE EDITED HERE
            delay(2000);
        }    
    }
    

    And your python code like so...

    ser = None
    try:
        ser = serial.Serial('/dev/AMA0',9600,timeout=3)
        ser.open()
    
        while True:
            try:
                serial_data = ser.readline()
                print serial_data
            except:
                pass
    except:
        pass    
    finally:
        if ser:
            ser.close()
    
    0 讨论(0)
提交回复
热议问题