Jumbled out put of RFID Tags

681 views Asked by At

I am working on a project, in which I have to interface multiple RFID Readers (I'm Using EM 18, With Serial out) with Raspberry Pi. I'm using an USB to TTL Converter to connect EM 18 to Raspberry Pi. I've connected two RFID Readers using USB to TTL Adapter. This is my code for one station

Code

import serial, time
while True:
    try:
        print 'station one Is Ready!! Please Show your Card'
                card_dataa = serial.Serial('/dev/ttyUSB0', 9600).read(12)
        print card_dataa
        continue
    except serial.SerialException:
        print 'Station 1 is Down'
    break

My Issues are

  1. I would like to get the readings from both the RFID Readers in the same program simultaneously.

  2. I've two Programs with the above code, station1.py and station2.py.

Station1.py is for USB0 and Station2.py is for USB1. I am executing the programs in different Terminal simultaneously.

For example station1.py in terminal 1 and station2.py in terminal 2. The program executes fine, but the readings are jumbled. For example, 6E0009D2CC79 and 4E0070792760 are the tag id's that i'm using for testing. if I'm executing only one program i'm getting the reading properly, but if I'm executing both programs simultaneously in two terminals I'm getting the tag Id's jumbled.

  1. I want to combine both the readings in the same program.

Thanks in Advance

2

There are 2 answers

3
George Profenza On BEST ANSWER

I'd recommend create a new Serial object once and reading multiple times, as needed:

import serial, time

try:
    station1 = serial.Serial('/dev/ttyUSB0', 9600)
    print 'station one Is Ready!! Please Show your Card'
except serial.SerialException:
        print 'Station 1 is Down'

while True:
    card_dataa = station1.read(12)
    print card_dataa

Optionally you can set a timeout of 0:

import serial, time

try:
    station1 = serial.Serial('/dev/ttyUSB0', 9600,timeout=0)
    print 'station one Is Ready!! Please Show your Card'
except serial.SerialException:
        print 'Station 1 is Down'

while True:
    card_dataa = station1.read(12)
    if len(card_dataa) > 0: print card_dataa

You should also easily be able to open 2 serial connections in the same program:

import serial, time

station1 = None
station2 = None

try:
    station1 = serial.Serial('/dev/ttyUSB0', 9600,timeout=0)
    print 'station 1 Is Ready!! Please Show your Card'
except Exception,e:
        print 'Station 1 is Down',e

try:
    station2 = serial.Serial('/dev/ttyUSB1', 9600,timeout=0)
    print 'station 2 Is Ready!! Please Show your Card'
except Exception,e:
        print 'Station 2 is Down',e


while True:
    if station1 != None:
        card_dataa1 = station1.read(12)
        if len(card_dataa1) > 0:    print card_dataa1
    if station2 != None:
        card_dataa2 = station2.read(12)
        if len(card_dataa2) > 0:    print card_dataa2

This means the 2nd reader would wait for the 1st reader to finish before printing, which is why fingaz recommended threading.

Here's a basic commented proof of concept for threading:

import threading,time,serial

#subclass threading.Thread
class RFIDSerialThread(threading.Thread):
    SLEEP_TIME = 0.001 #setup sleep time (update speed)
    #constructor with 3 parameters: serial port, baud and a label for this reader so it's easy to spot
    def __init__(self,port,baud,name): 
        threading.Thread.__init__(self) #initialize this instance as a thread
        self.isAlive = False #keep track if the thread needs to run(is setup and able to go) or not
        self.name = name     #potentially handy for debugging
        self.data = ""       #a placeholder for the data read via serial
        self.station = None  #the serial object property/variable
        try:
            self.station = serial.Serial(port,baud,timeout=0) #attempt to initialize serial
            self.isAlive = True #and flag the thread as running
        except Exception,e: 
            print name + " is Down",e #in case of errors print the message, including the station/serial port

    def run(self): #this gets executed when the thread is started
        while self.isAlive:
            if self.station != None:    self.data = self.station.read(12) #read serial data
            time.sleep(RFIDSerialThread.SLEEP_TIME)

if __name__ == '__main__':
    #initialize the two readers
    station1 = RFIDSerialThread('/dev/ttyUSB0',9600,"station #1")
    station2 = RFIDSerialThread('/dev/ttyUSB1',9600,"station #2")
    #start the threads
    station1.start()
    station2.start()

    while True:#continously print the data (if any)
        if len(station1.data) > 0:  print station1.name,station1.data
        if len(station2.data) > 0:  print station2.name,station2.data

Note that I haven't attached actual hardware to test, so this may not work as is, but should provide enough info to progress.

I would also suggest trying to physically distance the readers. Depending on the readers and their capabilities they may be interfering witch each other which might result in faulty data. In case you still have issues with jumbled data, I'd try to figure out where the problem is by taking some assumptions out.(e.g. is the issue a hardware (readers interfering, broken reader, loose USB connector, etc.) or software(serial port not properly initialized/flushed/etc.), taking one thing out at a time)

3
fingaz On

To have a concurrent flow, you can use the threading module. Here's a link to the documentation:

https://docs.python.org/2/library/threading.html