CeeBee
Posts: 14
Joined: Thu Nov 03, 2016 6:56 am

Rpi UART to Arduino.

Sun Nov 13, 2016 1:32 am

Hey all.

The RPi is too slow for my application using USB camera, so I made the effort to learn linux and python to use the Picamera interface.

To understand the rest of this post please see the project here:

http://ceebeeoddsandsods.blogspot.com/2 ... 0-cam.html

Image
Image

which is a reduced version of this, still works exactly the same though
Image

The Arduino and RPi wiring diagram there works fine in IoT using pins 8/10 (uart) to make the connection to the arduino.

Under Linux/python I can also access the board perfectly using /dev/ttyAMC0 (regular USB serial) so serial install is OK.

video of it running and output on regular USB https://www.youtube.com/watch?v=-OucCgswJco

Have disabled the boot using the port in raspi-confi and added enable_uart =1 in config.txt, also double checked its not still listed in ccmdline.txt. No issues there.

My TRY:EXCEPT code for opening serial reports no errors (testing on USB it accurately determines if the usb connection is there or not.. it also reports no errors using UART...

but.. using USB i can send and receive characters no problem, as soon as i hit send on the UART it crashes the app. (terminal spin, no errors reported.



What am I missing?
Last edited by CeeBee on Mon Nov 14, 2016 11:53 pm, edited 1 time in total.

User avatar
joan
Posts: 14887
Joined: Thu Jul 05, 2012 5:09 pm
Location: UK

Re: Rpi UART to Arduino.

Sun Nov 13, 2016 10:01 am

Can't help with your problem.

I was wondering if the Arduino was needed. Is it doing anything the Pi couldn't do?

tito-t
Posts: 298
Joined: Thu Jan 07, 2016 5:14 pm

Re: Rpi UART to Arduino.

Sun Nov 13, 2016 10:50 am

I once had a similar issue in a C/C++ program but I could resolve this by help from a different (German) forum, using a proprietary communication program which is more safe in case of transmission failures.

The Pi was not able to do it alone as I have 6 pwm motors at L298 H-Bridges (3 pins each) feat. rotary encoders (+2 pins each) = overall 30 pins additionally to digtal sensor pins, i2c, UART.
I first tried it with an MCP23017 by i2c, then tried an Arduino Due (3.3V, pin layout like the MEGA, no level shifters) which worked finally by UART (also providing analog ports).

So if you need a C-coded program I might be able to give you the link.
- Tim

dgordon42
Posts: 788
Joined: Tue Aug 13, 2013 6:55 pm
Location: Dublin, Ireland

Re: Rpi UART to Arduino.

Sun Nov 13, 2016 12:44 pm

CeeBee wrote:Have disabled the boot using the port in raspi-confi and added enable_uart =1 in config.txt, also double checked its not still listed in ccmdline.txt. No issues there.
'raspi-config' may be your problem.

I assume from your Fritzing drawing that you are using a Pi 3, although this should work for all models.

First, on a Pi 3, check '/dev' for the presence of both the 'ttyS0' and 'serial0' entries. You should see something like this:

Code: Select all

flash@RaspberryThree ~ $ ls -lh /dev/serial0
lrwxrwxrwx 1 root root 5 Nov 13 11:59 /dev/serial0 -> ttyS0
flash@RaspberryThree ~ $ ls -lh /dev/ttyS0
crw-rw---- 1 root dialout 4, 64 Nov 13 11:59 /dev/ttyS0
flash@RaspberryThree ~ $
On models previous to the Pi 3, you should have:

Code: Select all

pi@raspberrypi ~ $ ls -lh /dev/serial0
lrwxrwxrwx 1 root root 5 Nov 13 12:01 /dev/serial0 -> ttyAMA0
pi@raspberrypi ~ $ ls -lh /dev/ttyAMA0
crw-rw---- 1 root dialout 4, 64 Nov 13 12:01 /dev/ttyAMA0
flash@RaspberryThree ~ $
If these entries are not present in '/dev', The Pi's serial port may not work.

Disabling the boot messages in 'raspi-config' (in what I believe to be a bug) kills the whole port. When this happens, the above entries disappear from '/dev'.
If you find the 'serial0' or the 'ttyS0' or the 'ttyAMA0' entries missing from '/dev', then go back to 'raspi-config' and enable the serial port boot messages, and reboot your Pi.

Now, 'raspi-config' will add the line "enable_uart=1" again to your '/boot/config.txt' file. Check for this with the command:

Code: Select all

grep uart /boot/config.txt
If it returns more than one line of "enable_uart=1", or any other line in the file with a "uart" command (such as "uart=1"), open '/boot/cmdline.txt' in a text editor, and hunt down and delete these extra lines. '/boot/config.txt' should have a single "enable_uart=1" entry for serial port operations.

'raspi-config' will also have added the phrase "console=serial0, 115200" to the file '/boot/cmdline.txt'. Open this file in a text editor, and remove the phrase. Note that '/boot/cmdline.txt' must only contain 1 line, do not split the line when editing, or try to add comments.
Reboot your Pi, and check the '/dev' Directory for the 'serial0' entry. It should now be there, and your serial port should work.

You should refer to the serial port in code as "/dev/serial0". This will allow your code to run in all models of Pi running Raspbian Jessie dated later than about May 2016.

Hope this helps,
Dave.

CeeBee
Posts: 14
Joined: Thu Nov 03, 2016 6:56 am

Re: Rpi UART to Arduino.

Sun Nov 13, 2016 1:19 pm

dgordon42 wrote:
CeeBee wrote:Have disabled the boot using the port in raspi-confi and added enable_uart =1 in config.txt, also double checked its not still listed in ccmdline.txt. No issues there.
'raspi-config' may be your problem.

I assume from your Fritzing drawing that you are using a Pi 3, although this should work for all models.

First, on a Pi 3, check '/dev' for the presence of both the 'ttyS0' and 'serial0' entries. You should see something like this:

Code: Select all

flash@RaspberryThree ~ $ ls -lh /dev/serial0
lrwxrwxrwx 1 root root 5 Nov 13 11:59 /dev/serial0 -> ttyS0
flash@RaspberryThree ~ $ ls -lh /dev/ttyS0
crw-rw---- 1 root dialout 4, 64 Nov 13 11:59 /dev/ttyS0
flash@RaspberryThree ~ $
On models previous to the Pi 3, you should have:

Code: Select all

pi@raspberrypi ~ $ ls -lh /dev/serial0
lrwxrwxrwx 1 root root 5 Nov 13 12:01 /dev/serial0 -> ttyAMA0
pi@raspberrypi ~ $ ls -lh /dev/ttyAMA0
crw-rw---- 1 root dialout 4, 64 Nov 13 12:01 /dev/ttyAMA0
flash@RaspberryThree ~ $
If these entries are not present in '/dev', The Pi's serial port may not work.

Disabling the boot messages in 'raspi-config' (in what I believe to be a bug) kills the whole port. When this happens, the above entries disappear from '/dev'.
If you find the 'serial0' or the 'ttyS0' or the 'ttyAMA0' entries missing from '/dev', then go back to 'raspi-config' and enable the serial port boot messages, and reboot your Pi.

Now, 'raspi-config' will add the line "enable_uart=1" again to your '/boot/config.txt' file. Check for this with the command:

Code: Select all

grep uart /boot/config.txt
If it returns more than one line of "enable_uart=1", or any other line in the file with a "uart" command (such as "uart=1"), open '/boot/cmdline.txt' in a text editor, and hunt down and delete these extra lines. '/boot/config.txt' should have a single "enable_uart=1" entry for serial port operations.

'raspi-config' will also have added the phrase "console=serial0, 115200" to the file '/boot/cmdline.txt'. Open this file in a text editor, and remove the phrase. Note that '/boot/cmdline.txt' must only contain 1 line, do not split the line when editing, or try to add comments.
Reboot your Pi, and check the '/dev' Directory for the 'serial0' entry. It should now be there, and your serial port should work.

You should refer to the serial port in code as "/dev/serial0". This will allow your code to run in all models of Pi running Raspbian Jessie dated later than about May 2016.

Hope this helps,
Dave.
Afraid it didn't work :(

Both of those were missing. I did as you suggested:
enabled com in raspi config
enable_uart=1 was already in my config.txt
rebooted

serial0 showed up, tested with it, it accepted connection but no communication occurred..

I then reread your post properly and also removed the console=serial1etcetc from cmdline.txt
(also in cmdline.txt is a line console=tty1 should that stay or go?)

rebooted, then ttyS0 showed up but serial0 disapeared.

tested in ttyS0 and again AMA0.. nada.. AMA0 refused my connection, and ttyS0 said its connected, but no actual communication happened...

this is what it looks like over regular USB (just finishing up the coding now)
https://www.youtube.com/watch?v=xrmniI8BLVc

CeeBee
Posts: 14
Joined: Thu Nov 03, 2016 6:56 am

Re: Rpi UART to Arduino.

Sun Nov 13, 2016 1:46 pm

joan wrote:Can't help with your problem.

I was wondering if the Arduino was needed. Is it doing anything the Pi couldn't do?
I tried doing time critical stuff related to triggering external camera from RPI GPIO and if linux kicks in doing anything at all it freezes up.

also its a PITA to build a bunch of voltage dividers to make the 3.3v rpi work in a 5v world.

CeeBee
Posts: 14
Joined: Thu Nov 03, 2016 6:56 am

Re: Rpi UART to Arduino.

Sun Nov 13, 2016 1:49 pm

tito-t wrote:I once had a similar issue in a C/C++ program but I could resolve this by help from a different (German) forum, using a proprietary communication program which is more safe in case of transmission failures.

The Pi was not able to do it alone as I have 6 pwm motors at L298 H-Bridges (3 pins each) feat. rotary encoders (+2 pins each) = overall 30 pins additionally to digtal sensor pins, i2c, UART.
I first tried it with an MCP23017 by i2c, then tried an Arduino Due (3.3V, pin layout like the MEGA, no level shifters) which worked finally by UART (also providing analog ports).

So if you need a C-coded program I might be able to give you the link.
Thank you for the offer, but I've crammed android coding, arduino, c# in UWP and forms, as well as python in the last 2 months, im not up to learning new code right now ;)

dgordon42
Posts: 788
Joined: Tue Aug 13, 2013 6:55 pm
Location: Dublin, Ireland

Re: Rpi UART to Arduino.

Sun Nov 13, 2016 3:10 pm

Can you confirm that you are using a Pi 3B?
Can you check the output of:

Code: Select all

uname -a
For '/dev/serial0' to work, the date should be later than about May 2016. By the way, that's serialZero, not serialOh!
CeeBee wrote:also in cmdline.txt is a line console=tty1 should that stay or go?
It should stay, your '/boot/cmdline.txt' should look like this:

Code: Select all

dwc_otg.lpm_enable=0 console=tty1 root=/dev/mmcblk0p2 rootfstype=ext4 elevator=deadline fsck.repair=yes rootwait
'mmcblk0' will have a different 'p' number if you use NOBBS.
CeeBee wrote:tested in ttyS0 and again AMA0.. nada.. AMA0 refused my connection, and ttyS0 said its connected, but no actual communication happened...
'/dev/ttyAMA0' will refuse a connection in a default Pi 3 as it's reserved for Bluetooth, so that part is normal.
You can check the serial port pins by doing a loopback test. Disconnect the Arduino from the Pi, and connect the serial port pins (physical pins 8 & 10) together, and run this code:

Code: Select all

#!/usr/bin/env python3
# Will also work on Python2.
# Serial port testing

from __future__ import print_function
import serial

test_string = "Testing 1 2 3 4".encode('utf-8')
# test_string = b"Testing 1 2 3 4" ### Will also work

port_list = ["/dev/serial0", "/dev/ttyS0"]

for port in port_list:

    try:
        serialPort = serial.Serial(port, 115200, timeout = 2)
        print("Opened port", port, "for testing:")
        bytes_sent = serialPort.write(test_string)
        print ("Sent", bytes_sent, "bytes")
        loopback = serialPort.read(bytes_sent)
        if loopback == test_string:
            print ("Received", len(loopback), "valid bytes, Serial port", port, "working \n")
        else:
            print ("Received incorrect data", loopback, "over Serial port", port, "loopback\n")
        serialPort.close()
    except IOError:
        print ("Failed at", port, "\n")
Good luck,
Dave.

CeeBee
Posts: 14
Joined: Thu Nov 03, 2016 6:56 am

Re: Rpi UART to Arduino.

Sun Nov 13, 2016 11:43 pm

dgordon42 wrote:Can you confirm that you are using a Pi 3B?
Can you check the output of:

Code: Select all

uname -a
For '/dev/serial0' to work, the date should be later than about May 2016. By the way, that's serialZero, not serialOh!
CeeBee wrote:also in cmdline.txt is a line console=tty1 should that stay or go?
It should stay, your '/boot/cmdline.txt' should look like this:

Code: Select all

dwc_otg.lpm_enable=0 console=tty1 root=/dev/mmcblk0p2 rootfstype=ext4 elevator=deadline fsck.repair=yes rootwait
'mmcblk0' will have a different 'p' number if you use NOBBS.
CeeBee wrote:tested in ttyS0 and again AMA0.. nada.. AMA0 refused my connection, and ttyS0 said its connected, but no actual communication happened...
'/dev/ttyAMA0' will refuse a connection in a default Pi 3 as it's reserved for Bluetooth, so that part is normal.
You can check the serial port pins by doing a loopback test. Disconnect the Arduino from the Pi, and connect the serial port pins (physical pins 8 & 10) together, and run this code:

Code: Select all

#!/usr/bin/env python3
# Will also work on Python2.
# Serial port testing

from __future__ import print_function
import serial

test_string = "Testing 1 2 3 4".encode('utf-8')
# test_string = b"Testing 1 2 3 4" ### Will also work

port_list = ["/dev/serial0", "/dev/ttyS0"]

for port in port_list:

    try:
        serialPort = serial.Serial(port, 115200, timeout = 2)
        print("Opened port", port, "for testing:")
        bytes_sent = serialPort.write(test_string)
        print ("Sent", bytes_sent, "bytes")
        loopback = serialPort.read(bytes_sent)
        if loopback == test_string:
            print ("Received", len(loopback), "valid bytes, Serial port", port, "working \n")
        else:
            print ("Received incorrect data", loopback, "over Serial port", port, "loopback\n")
        serialPort.close()
    except IOError:
        print ("Failed at", port, "\n")
Good luck,
Dave.
Hi Dave

Output from uname is
4.4.21-v7+ #911 SMP

my cmdline.txt is identical other than mmcblk0p7 (instead of 2) but at the end has this additionally
quiet splash plymouth.ignore-serial-consoles
which i removed, pasting here so i can copy it back.. just in case... ;)

on reboot still no serial0 from ls /dev/tty*. i have tty~tty63, ttyAMA0, ttyS0, ttyprintk

your code supplied reports 15 bytes received from both ports.

My code didint baulk at connecting to the nonexisting serial0 but as before no actual communication happened.
to check if my cable is OK i booted up mt other RPi to IoT to test the cable, its functioning.

changed my code to include the utf8, still nothing.

At this point I'm flummoxed.. maybe UART doesnt like 57600?

CeeBee
Posts: 14
Joined: Thu Nov 03, 2016 6:56 am

Re: Rpi UART to Arduino.

Sun Nov 13, 2016 11:56 pm

update

changed arduino code to connect at both 9600 and 115200, changed python code to suit. nada at either speed, it connected but no characters are sent or received.

when i run your code with my arduino plugged it it does not report a fail, but reports incorrect characters received back.

my code defs hereunder , noting this works perfectly over USB.. stumped.

Code: Select all

#get the serial port
try:
    ser = serial.Serial('/dev/serial0', 115200)
except:
    print "Com not connected, try unplug and replug the Arduino"
    print "then restart the application."
    pass

Code: Select all

def SerialWrite(value, value2):
    print value
    try:
        ser.write(value.encode('utf-8'))
    except:
        e = sys.exc_info() [0]
        print ("Error" % e)
    time.sleep(value2)
snippet from the main code that does the write

Code: Select all

#Main Target Code
    Count = 0
    while Count < ImageLoop:
        Count = Count + 1
        FileWrite = FileName+"0"+str(Count)+".jpg"
        Motion = str(int(Count*StepsPerPhoto))
        camera.capture(FileWrite)
        SerialWrite("0000"+Motion,2) # 2 is delay to wait for motion to complete
        #debug, remove later
       print FileWrite,Motion
       TriggerExternalCamera(2) #delay 2 for the Canon to shutter, note 0.5 is held high on trigger pin too
    SerialWrite("00000",5)

my arduino has following snippets (noting this works perfectly on either uart or usb on the IoT install)
(mega2560 code)

Code: Select all

  Serial1.begin(115200);
  Serial.begin(115200);

Code: Select all

if (Serial1.available() > 0 ) {
    ReadRPI = Serial1.readString();
    //code follows that breaks string up into chunks
    // report back via same port what we read
    // in iot used to check command arrived safely
    Serial1.print(Light1+Light2+Light3+Light4+AValue);
    ReadRPI = "";
  }
  if (Serial.available() > 0 ) {
    ReadRPI = Serial.readString();
     //code follows that breaks string up into chunks
    // report back via same port what we read
    // in iot used to check command arrived safely
    Serial.print(Light1+Light2+Light3+Light4+AValue);
  }

dgordon42
Posts: 788
Joined: Tue Aug 13, 2013 6:55 pm
Location: Dublin, Ireland

Re: Rpi UART to Arduino.

Mon Nov 14, 2016 2:17 pm

CeeBee wrote:Output from uname is
4.4.21-v7+ #911 SMP
All good, your running Raspbian Jessie from about September 2016.
CeeBee wrote:my cmdline.txt is identical other than mmcblk0p7 (instead of 2) but at the end has this additionally
quiet splash plymouth.ignore-serial-consoles
which i removed, pasting here so i can copy it back.. just in case... ;)
'mmcblk0p7' is normal if you installed Raspbian from NOOBS, or bought an SD card with Raspbian on it. As long as your Pi boots, it's fine. 'quite splash', as far as I know is to do with the PIXEL splash screen on start-up. 'plymouth.ignore-serial-consoles' also has to do with the splash screen, but I've not seen it before. It's not on any of my Pi's, so maybe best to leave it out until you get things working.
My Pi's are running headless, so I don't have much use for a splash screen.
CeeBee wrote:on reboot still no serial0 from ls /dev/tty*. i have tty~tty63, ttyAMA0, ttyS0, ttyprintk
The 'ls /dev/tty*' will only show devices in the '/dev' directory that start with the three letters "tty", that's why you are not seeing the 'serial0' entry.
CeeBee wrote:your code supplied reports 15 bytes received from both ports.
This is good, your Pi has passed a loopback test so your hardware is working properly, it also means that '/dev/serial0' exists!
It also means that you have got past the 'raspi-config' bug which removes the serial port entries in Linux.
CeeBee wrote:changed my code to include the utf8, still nothing.
This is necessary if you are working in Python3, Python2 will work without this step, but it does no harm to leave it in, as far as I know.
CeeBee wrote:changed arduino code to connect at both 9600 and 115200, changed python code to suit. nada at either speed, it connected but no characters are sent or received.
I would recommend that you set 9600 baud on all devices for troubleshooting, once you get things working you can wind up the speed.
CeeBee wrote:when i run your code with my arduino plugged it it does not report a fail, but reports incorrect characters received back.
The actual error message is important here, if the code returns:

Code: Select all

Received incorrect data over Serial port /dev/serial0
it means that NO data was received on the serial port within the 2 second time out period, but if it returns something like:

Code: Select all

Received incorrect data sheiv50375kk over Serial port /dev/serial0
it means that 12 corrupted bytes of data was received, instead of the expected 15 byte test string.

I plan on hooking up an Arduino to my Pi later on today to test your code snippets, I'll report on this later today.

Dave.

CeeBee
Posts: 14
Joined: Thu Nov 03, 2016 6:56 am

Re: Rpi UART to Arduino.

Mon Nov 14, 2016 2:56 pm

Thanks Dave. Appreciated.

dgordon42
Posts: 788
Joined: Tue Aug 13, 2013 6:55 pm
Location: Dublin, Ireland

Re: Rpi UART to Arduino.

Mon Nov 14, 2016 8:07 pm

Here is a short Arduino script to return received bytes on the serial port. If you connect the serial port on the Pi to the serial port on the Arduino as per your Fritzing drawing above, load this script onto the Mega, and run the Python loopback program above on your Pi, you should get 'Serial port working' messages like this:

Code: Select all

Opened port /dev/serial0 for testing:
Sent 15 bytes
Received 15 valid bytes, Serial port /dev/serial0 working

Opened port /dev/ttyS0 for testing:
Sent 15 bytes
Received 15 valid bytes, Serial port /dev/ttyS0 working
The Arduino code:

Code: Select all

/* return_serial.ino
 *  Script to read a byte from the serial port,
 *  and send it back out on the serial port.
 *  This script will only run on an Arduino Mega
 *  using serial pins 18 & 19, or an Arduino 
 *  Leonardo using serial pins 0 & 1.
 */

void setup() {
  Serial1.begin(9600);
}

void loop() {
  if (Serial1.available()> 0) {
    int data = Serial1.read();
    Serial1.write(data);
  }
}
I'm going to try your code now on my Arduino.

Good Luck,
Dave.

tito-t
Posts: 298
Joined: Thu Jan 07, 2016 5:14 pm

Re: Rpi UART to Arduino.

Mon Nov 14, 2016 8:28 pm

for the void loop() I would suggest instead:

Code: Select all

void loop() {
  if( Serial1.available() ) {
     // delay(10); // allows more serial data to be received together
     while( Serial1.available() ) {
        int data = Serial1.read();
     }
     Serial1.write(data);
  }
}
- Tim

CeeBee
Posts: 14
Joined: Thu Nov 03, 2016 6:56 am

Re: Rpi UART to Arduino.

Mon Nov 14, 2016 11:30 pm

Hi Tim, Thanks for the suggestion. Code is definitely neater. Im new to programming so every tip is a winner.

However if you follow thread above. The code works fine running via uart or usb in IoT on the Pi. It runs fine on USB from PC or my UP Board.

It runs fine on USB on the RPi running Jessie. What it doesn't do is run on UART on Jessie. At all.

The client code allows nearly 6 seconds for the transaction. 2 for IO transaction, then additional 4 for motion to complete and the camera trigger to fire, IO Measured, it requires in actuality a little less than 0.1 second to transmit 6 characters ( measured by camera trigger on pin on Arduino which sends back the timing from code received to trigger fired in my debug version).



Doing my head in.
Last edited by CeeBee on Mon Nov 14, 2016 11:45 pm, edited 1 time in total.

CeeBee
Posts: 14
Joined: Thu Nov 03, 2016 6:56 am

Re: Rpi UART to Arduino.

Mon Nov 14, 2016 11:41 pm

@Dave.

outside possibility (pending result of your tests with my code)

Can it be possible that because uart was intended for console comms that in one of the library's its hardcoded to a specific handshake(or even speed)? which will pass a loopback back test as both ends are on the Rpi talking through the same library?

Another possibilty is the routines themselves.. I can say that from the IoT code sending a writeln (plus carriage return) failed and it had to be a write for it to complete. Im not sure how the serial coms in jessie work, but i think my code is sending command sans a carriage return already.

at this point I'm considering soldering wiring from the USB port inwards to mount my nano neatly internally and giving up on this UART thing.

Silly that such a simple thing should be so hard....

CeeBee
Posts: 14
Joined: Thu Nov 03, 2016 6:56 am

Re: Rpi UART to Arduino.

Sat Dec 03, 2016 5:46 am

was never able to resolve the UART issue (not for lack of trying, going to assume linux/rpi for that os broken) so I rebuilt to dump the Arduino completely.

Build components now are:

RPi 1.2ghz v3B
AfterMarket Camera Any will do, as long as it has adjustable focus
ULN2003 Stepper 64steps*64:1 gear = 4096 steps @ 13kg torque. (includes driver board)

and some wires and one led worth a few cents.

Total build cost USD$51.60 ($64.50 - 20% discount if you buy for a total over 150USD on lazada)


The official touchscreen touchscreen useless, just get regular 7in LCD (~S20) and a BT mouse.

Runs damn fine off only one 5V USB power supply (PC or plug 1A min)

Downside.. all the code to control the stepper motion and position control had to be written from scratch, no useful stepper libraries like AccelStepper really exist in python/rpi.. that bit was unpleasant, cost me some drinking time last night.. but its done.

https://www.youtube.com/watch?v=rhOirZrU_10

Return to “Beginners”