How to send a sequence of AT commands to a serial port in bash?
If you install the PPP package you can use the chat
program that comes with it. Or you can use kermit
. Or the cu
program that comes with uucp. But to do it with pure shell is trickier. You might be able to use the read and printf functions, with stdio redirected to the port.
some snippet:
stty -F /dev/ttyS0 38400 raw
chat -f script.txt < /dev/ttyS0 > /dev/ttyS0
Should get you started.
Writing to the serial port from the Linux command line
echo '\x12\x02'
will not be interpreted, and will literally write the string \x12\x02
(and append a newline) to the specified serial port. Instead use
echo -n ^R^B
which you can construct on the command line by typing CtrlVCtrlR and CtrlVCtrlB. Or it is easier to use an editor to type into a script file.
The stty
command should work, unless another program is interfering. A common culprit is gpsd
which looks for GPS devices being plugged in.
sending hex bytes to serial in bash
The problem is that read
interprets escape sequences by default, effectively removing your backslashes. Make your file contain e.g. \x01\x02\x03
and use read -r
:
while read -r line
do
echo -en "$line" > /dev/ttyUSB0
done < "$1"
Automating serial port communication on Linux
Kermit is a serial communication app like minicom and it has its own script language, and I used it for some automatic upload on embedded devices. However, it is quite limited and/or buggy, so I finally switched to using python and pyserial.
Whenever you deal with texte mode, like AT command set or speaking to a shell over a serial line, it is really powerful.
If I need to do binary transfer using some standard protocol, I usually use command line tools in non interactive mode, and spawn them from my python script.
Here is some part of the tools I built : waiting for some input, sending data through xmodem, sending a command to u-boot and starting a transfer using the kermit protocol. I use it for automatic flashing and testing of embedded devices.
class Parser :
def __init__(self, sport_name):
self.currentMsg = ''
if sport_name :
self.ser = serial.Serial(sport_name, 115200)
def WaitFor(self, s, timeOut=None):
self.ser.timeout = timeOut
self.currentMsg = ''
while self.currentMsg.endswith(s) != True :
# should add a try catch here
c=self.ser.read()
if c != '' :
self.currentMsg += c
sys.stdout.write(c)
else :
print 'timeout waiting for ' + s
return False
return True
def XmodemSend(self,fname):
if not self.WaitFor('C', 1) :
print 'RomBOOT did not launch xmodem transfer'
return
self.ser.flushInput()
self.ser.close()
call(["xmodem","-d",self.ser.port,"-T",fname])
self.ser.open()
def UbootLoad(self, fname):
self.ser.write('loadb 0x20000000\n')
if not self.WaitFor('bps...',1) :
print 'loadb command failed'
sys.exit()
self.ser.flushInput()
self.ser.close()
retcode=call(['kermit','-y','kermit_init','-s',fname])
if retcode != 0 :
print 'error sending' + fname
sys.exit()
self.ser.open()
self.UbootCmd('echo\n')
Bash, serial I/O and Arduino
Try using the tool stty:
stty -F /dev/my_serial_port <baud_rate> cs8 cread clocal
As always, read the manpage before applying the above. cread
allows you to receive data. You may want to omit clocal
if you are using flow control. If you aren't sure what the above settings are, ask, and I can write up a more complete answer.
Related Topics
Systemd with Multiple Execstart
Delete Files with String Found in File - Linux Cli
How to Do Division with Variables in a Linux Shell
How to Diff Directories Over Ssh
Does Os X Have an Equivalent to /Dev/Shm
Architecture of I386 Input File Is Incompatible with I386:X86-64
What's the Difference Between Event-Driven and Asynchronous? Between Epoll and Aio
Is It Safe to Delete the Journal File of Mongodb
How to Capture Raw Hid Input on Linux
Magic Numbers of the Linux Reboot() System Call
How to Delete First Two Lines and Last Four Lines from a Text File with Bash
Backup a Running Docker Container
How to Get My Golang Web Server to Run in the Background
Macros for Gcc/G++ to Differentiate Linux and MAC Osx