Skip to content

Magnetic-Fox/MSR605X

Folders and files

NameName
Last commit message
Last commit date

Latest commit

 

History

113 Commits
 
 
 
 
 
 

Repository files navigation

MSR605X Utility

Python library with additional text user interface to be used as a standalone solution.

Table of Contents

Introduction
How it was started?
Dependencies (what is needed to run this code?)
Device permissions
Interpreter
Quick reference for MSR605X class
Break procedure
Quick reference for Interactive class
Known issues
Devices used for testing
Disclaimer
License

Introduction

This project aims to be the easiest possible, but fail-safe Python solution for HID-type MSR605X magstripe reader/writer device,which might be used as a library or as a standalone program with typical text user interface.

Maybe the code isn't the cleanest, but I wanted to make it a one-file solution for ease of use. That's why I decided to write such a detailed readme file, which might be considered a documentation.

How it was started?

Last time I (finally!) moved to the Linux Mint system (which I really love). However, I couldn't make official MSRX program run properly under Wine (which was a bit shocking as Wine is a very good solution and MSRX seems to be one of the easiest piece of software to run) and the other MSR-related projects found on the internet just weren't working for me for strange reasons (assertion errors, etc.). I then decided to start something really simple to be able to read and write ISO cards (at least). I thought it would probably never work, but when the first operations succeeded, I wanted to go further - that's how MSR605X class was written. And when it was ready to use I started writing Interactive class to provide basic text user interface support.

Dependencies (what is needed to run this code?)

The only additional library that is needed to run this code is hid library, which on Linux Mint can be found in APT under the name python3-hid (where it is described as "cython3 interface to hidapi").
The sys library (which You can find in imports at the top of this code) is here only for user input/output support (interpreter).

Device permissions

In order to use this solution, You have to have rights to read and write to the USB device. This is a bit tricky under Linux as You have to carefully find Your device and then create a udev rule file. Otherwise You'll have to run this code as a root (e.g. use sudo), which I do not recommend as it is not a good idea, especially for a long time (and not safe at all).

Here is an example of my 99-hid.rules file placed in the /etc/udev/rules.d/ directory:

SUBSYSTEM=="usb", ATTRS{idVendor}=="0801", ATTRS{idProduct}=="0003", MODE="0666"
KERNEL=="hidraw*", ATTRS{idVendor}=="0801", ATTRS{idProduct}=="0003", MODE="0666"

I know, it is not the safest option to use 0666 mode, but others simply didn't work for me (even with OWNER and GROUP set). Fortunately, I'm the only user of my computer. ;)

Note

You can use any valid name for the file. I've used 99-hid.rules, but probably 99-msr.rules would be good too.

After creating such file, if You don't want to restart Your system, to make this rules work, type in the terminal those two commands:

sudo udevadm control --reload-rules
sudo udevadm trigger

Now, if everything finished properly, MSR605X should be available to use without root permissions.

Interpreter

How to use it?

That's pretty simple - You can use it just like any other console tool. Just pass any commands and arguments You need. The only difference is that this tool interprets all passed arguments as a task list, which means that You can, for example, ask for five reads executed one after another or even change used device at the runtime.

Warning

If Your arguments are wrong, program just won't run and will display help screen.

Quick reference for interpreter commands

Interpreter configuration commands

Command Arguments Description
-p none data only output (pipe mode)

Note

Using pipe mode removes any unnecessary output from the commands leaving only data to be returned, terminated by the next line character \n.

Read/write operations

Command Arguments Description
-r none Read card in ISO mode
-rb none Read card in RAW mode
-w track1String [track2String [track3String]] Write card in ISO mode
-wb track1HexStr [track2HexStr [track3HexStr]] Write card in RAW mode *
-c none Copy card in ISO mode
-cb none Copy card in RAW mode *
-e trackNumber [trackNumber [trackNumber]] Erase card tracks

Legend:
* - command sets 8 bits per character mode

Important

Reading card in the pipe mode might return one or even three empty strings if card contains empty tracks.
On read error \x15 character (NAK) is returned.
Every track string is terminated by the next line character (\n).

Warning

RAW mode write accepts data only in XX XX XX ... format, where single XX represents hexadecimal value for a byte to be written.

Data setting commands

Command Arguments Description
-bc track1BPC track2BPC track3BPC Set bits per character interpretation for tracks (possible values: 5-8)
-bi track1BPI [track2BPI [track3BPI]] Set bits per inch for tracks (possible values: nothing, 75, 210)
-z track1and3LZ track2LZ Sets leading zeroes for track 1 & 3 and 2 (possible values: 0-255)

Coercivity setting commands

Command Arguments Description
-h none Sets high coercivity mode
-l none Sets low coercivity mode

LED control commands

Command Arguments Description
-i0 none Turns off all LEDs
-i1 none Turns on green LED and turns off yellow and red LEDs
-i2 none Turns on green and yellow LEDs and turns off red LED
-i3 none Turns on red LED and turns off green and yellow LEDs
-i4 none Turns on all LEDs

Device control commands

Command Arguments Description
-vid vendorID Sets Vendor ID part of the device address (possible values: 0x0000 - 0xFFFF)
-pid productID Sets Product ID part of the device address (possible values: 0x0000 - 0xFFFF)
-rid reportID Sets Report ID to use to communicate with the device (possible values: 0x00 - 0xFF)
-sr none Resets the device (soft)
-hr none Resets the device (hard)

Settings and device information gathering commands

Command Arguments Description
-gc none Gets coercivity setting
-zs none Gets leading zeroes setting
-m none Gets device model
-f none Gets firmware version

Important

When pipe mode is used, commands outputs are much shorter.
-gc command returns just H or L.
-zs command returns numbers only - each value in the separate line.
-m and -f commands return values only without any decoration.

Device test commands

Command Arguments Description
-tc none Makes a communication test
-ts none Makes a sensor test (probably unsupported)
-tr none Makes a RAM test (probably unsupported)

Questions to answer

How to write only third track of a card?

Just pass two empty strings at the beginning and then string for the third track:
./msr605x.py -w "" "" "2026=04=07"

How to set bits per inch for second track only?

Like in the example above, pass empty string to the first track:
./msr605x.py -bi "" 210

Caution

You must not provide empty string as a last argument as this is interpreted as error!
BAD EXAMPLE: ./msr605x.py -bi "" 210 ""

How to erase only one or two tracks?

This command is interpreted a bit another - You have to pass numbers indicating which tracks have to be erased, for example:
./msr605x.py -e 3
OR
./msr605x.py -e 3 2
OR
./msr605x.py -e 2 1 3

Important

Order of the numbers is not important, just do not duplicate them as this is interpreted as error.
BAD EXAMPLE: ./msr605x.py -e 2 1 2

How to set leading zeroes or bits per character for one track only?

This is not supported, because MSR605X provides no command for such usage (or at least MSR605 as I do not have documentation for MSR605X).
The only way it can be used is to provide all two parameters for leading zeroes and all three parameters for bits per character setting.

Example of leading zeroes setting:
./msr605x.py -z 61 22

Example of bits per character setting:
./msr605x.py -bc 7 5 5

RAM and sensor tests gives ERROR as a result - what's wrong?

These commands are probably unsupported by MSR605X. I programmed them as they are mentioned in "MSR605 Programmer's Manual", because maybe there are MSR605X-like magstripe devices that support those commands (let me know if they work if You have device other than mine).

I'm setting VID, PID and RID properly, but program doesn't run - what's wrong?

You've probably set the device address and report ID to be used for communication but haven't used any device commands to do actual communication. As this has no sense it is treated as a parameter error.

Tip

If You want to make a communication test of a chosen device, add -tc at the end of Your command.
For example: ./msr605x.py -vid 0x0801 -pid 0x0003 -tc

I want to stress-test your code!

Please type such command:
./msr605x.py -l -h -m -f -i0 -i1 -i2 -i3 -i4 -i1 -tc -zs -gc -ts -tr -bc 7 5 5 -bi 210 75 210 -z 61 22 -sr -hr

Note

Sensor and RAM tests would probably return errors (they are probably unsupported by MSR605X).

Quick reference for MSR605X class

Constants

Default values (VID + PID for MSR605X and additionals)

Name Value Description
DEFAULT_VID 0x0801 default Vendor ID for MSR605X
DEFAULT_PID 0x0003 default Product ID for MSR605X
DEFAULT_RID 0xFF byte-like; default, working Report ID for MSR605X
DEFAULT_TIMEOUT 100 default, short timeout for readData method in milliseconds
DEFAULT_CONTINUOUS_TIMEOUT 1000 default, continuous timeout for continuous read in readData method in milliseconds

ISO 7811 constants

Name Value Description
ISO1_ALPHABET {SPACE}#$()-./0123456789ABCDEFGHIJKLMNOPQRSTUVWXYZ[\]^ ISO 7811, track 1 alphabet; % and ? excluded as they can't be used for data (start and end sentinel)
ISO2_ALPHABET 0123456789= ISO 7811, track 2 alphabet; ; and ? excluded as they can't be used for data (start and end sentinel)
ISO3_ALPHABET 0123456789= ISO 7811, track 3 alphabet; ; and ? excluded as they can't be used for data (start and end sentinel)
ISO1_MAXSIZE 76 ISO 7811, maximum data length for track 1
ISO2_MAXSIZE 37 ISO 7811, maximum data length for track 2
ISO3_MAXSIZE 104 ISO 7811, maximum data length for track 3

Typical constants

Name Value Description
ESC 0x1B byte-like; escape character code
FS 0x1C byte-like; file separator character code

Response constants

Name Value Description
NO_DATA ESC + no data response code
BAD_DATA ESC * data read error response code
CMD_OK ESC 0 command successful code
CMD_FAIL ESC A command fail code
COMM_OK ESC y communication OK code
SB_RW_OK 0x30 status byte - read/write OK
SB_RW_ERROR 0x31 status byte - read/write error
SB_CMD_ERROR 0x32 status byte - command error
SB_CMD_INVALID 0x34 status byte - invalid command
SB_SWIPE_ERROR 0x39 status byte - card swipe error
HICO_SET ESC h Hi-Co set response
LOCO_SET ESC l Lo-Co set response

Data sequence, track and ISO constants

Name Value Description
START_SEQUENCE ESC s data sequence start
END_SEQUENCE_W ? FS data sequence end - for writing
END_SEQUENCE ? FS ESC data sequence end - helper for reading
ISO1_DATA_START ESC 0x01 ISO Track 1 - start sequence
ISO2_DATA_START ESC 0x02 ISO Track 2 - start sequence
ISO3_DATA_START ESC 0x03 ISO Track 3 - start sequence
START_SENTINEL_1 % ISO 7811, track 1 - start sentinel
START_SENTINEL_2_3 ; ISO 7811, track 2 and 3 - start sentinel
END_SENTINEL ? ISO 7811, all tracks - end sentinel
ISO_TRACK1 1 set track 1 constant - for OR-like operations (0b00000001)
ISO_TRACK2 2 set track 2 constant - for OR-like operations (0b00000010)
ISO_TRACK3 4 set track 3 constant - for OR-like operations (0b00000100)
ISO_TRACK1_210BPI 0xA1 track 1 - 210bpi setting byte
ISO_TRACK1_75BPI 0xA0 track 1 - 75bpi setting byte
ISO_TRACK2_210BPI 0xD2 track 2 - 210bpi setting byte
ISO_TRACK2_75BPI 0x4B track 2 - 75bpi setting byte
ISO_TRACK3_210BPI 0xC1 track 3 - 210bpi setting byte
ISO_TRACK3_75BPI 0xC0 track 3 - 75bpi setting byte

Command constants

Name Value Description
CMD_RESET ESC a reset command
CMD_READ ESC r ISO read command
CMD_WRITE ESC w ISO write command
CMD_COMM_TEST ESC e communication test command
CMD_ALL_LED_OFF ESC 0x81 all LEDs off command
CMD_ALL_LED_ON ESC 0x82 all LEDs on command
CMD_GREEN_LED_ON ESC 0x83 green LED on command
CMD_YELLOW_LED_ON ESC 0x84 yellow LED on command
CMD_RED_LED_ON ESC 0x85 red LED on command
CMD_LEAD_ZERO_SET ESC z leading zeroes setting command
CMD_LEAD_ZERO_CHECK ESC l leading zeroes gathering command
CMD_ERASE_CARD ESC c card erase command
CMD_BPI_SELECT ESC b BPI setting command
CMD_READ_RAW ESC m RAW read command
CMD_WRITE_RAW ESC n RAW write command
CMD_GET_MODEL ESC t device model gathering command
CMD_GET_FW_VERSION ESC v device firmware version gathering command
CMD_BPC_SET ESC o BPC setting command
CMD_SET_HICO ESC x Hi-Co setting command
CMD_SET_LOCO ESC y Lo-Co setting command
CMD_GET_COERCIVITY ESC d coercivity setting gathering command
FORCE_CMD_MODE 0x00 0xC2 force command start sequence

Probably not supported commands in MSR605X

Name Value Description
CMD_SENSOR_TEST ESC 0x86 sensor test command
CMD_RAM_TEST ESC 0x87 RAM test command

Methods

Technical methods

Name Parameters Description
__init__ vendorID, productID, reportID, timeout, continuousTimeout, breakProcedure constructor, used to initialize class on object creation (2x 0x0000 - 0xFFFF, 0x00 - 0xFF, 2x int, function or None)
__del__ none destructor, used to close device if forgotten

Internal helper methods

Name Parameters Description
toLSB msbByte byte from MSB to LSB converter (0 - 255)
bytesToLSB msbBytes byte string from MSB to LSB converter method (byte-like object)
dataSplit data, size full data to data chunks splitter method (byte-like object, int)
dataFill data, size data chunk to fixed size filler (filling with zeroes) (byte-like object, int)
dataFramesPrepare data data frames to be sent to the HID device preparation method
writeData data data to device writer method (byte-like object)
hardWriteData data data to device writer method (hard mode - working only with hard reset command; byte-like object)
readData continuousTimeout data read from device method (with or without continuous timeout; continuous timeout works like a loop with next iterations occurring after short timeout, e.g. 1 second; int)
exportISOData none export all tracks ISO data from response from device
exportRAWData none export all tracks RAW data from response from device
prepareISOData track1, track2, track3 ISO tracks data to data block converter (strings)
prepareRAWData track1, track2, track3 RAW tracks data to raw data block converter (with automated byte data to LSB byte data; byte-like objects)
isValid alphabet, int, string string validator method (alphabet string, maximum data length as int, user string)

Initialization methods

Name Parameters Description
setDevice vendorID, productID simple vendor ID and product ID setter method (2x 0x0000 - 0xFFFF)
setReportID reportID simple report ID setter method (0x00 - 0xFF)
setTimeout timeout simple timeout setter method (int)
setContinuousTimeout continuousTimeout simple continuous timeout setter method (int)
setBreakProcedure breakProcedure continuous read break procedure address setter method (procedure; read about break procedure below)
open none device open method
close none device close method

Actual device command control methods

Name Parameters Description
hardReset none hard reset method
reset none soft reset method
read none ISO card read method
write iso1, iso2, iso3 ISO card write method (single or even all tracks; strings)
communicationTest none device communication test method
allLedOff none all LEDs off method
allLedOn none all LEDs on method
greenLedOn none green LED on method
yellowLedOn none yellow LED on method (which in fact turns on GREEN and yellow LEDs)
redLedOn none red LED on method (which in fact turns OFF green and yellow LEDs)
sensorTest none sensor test method (PROBABLY UNSUPPORTED COMMAND IN MSR605X)
ramTest none RAM test method (PROBABLY UNSUPPORTED COMMAND IN MSR605X)
setLeadingZero leadZeroTrack1and3, leadZeroTrack2 leading zeroes for track 1 & 3 and track 2 setter method (2x 0 - 255)
checkLeadingZero none leading zeroes gathering method
eraseCard track1, track2, track3 card erase method (single or even all tracks; 3x True/False)
selectBPI settingByte bytes per inch setter method (byte-like object)
readRawData none RAW card read method
writeRawData track1, track2, track3 RAW card write method (byte-like objects)
getDeviceModel none device model gathering method
getFirmwareVersion none firmware version gathering method
setBPC track1, track2, track3 bits per character setter method (3x 5 - 8)
setHiCo none high coercivity card setter method
setLoCo none low coercivity card setter method
getCoercivitySetting none coercivity setting gathering method

Break procedure

A break procedure is a simple piece of code which can decide if readData method has to continue its operation or if it has to stop right now. It might be useful in situations, where external procedure might want to stop waiting for user to swipe the card.

It can be as easy as (let's say 10 stored in someInformation variable means that we have to stop):

def breakProcedure:
	global someInformation
	return someInformation == 10

Quick reference for Interactive class

Methods

Technical methods

Name Parameters Description
__init__ vendorID, productID, reportID simple constructor to initialize Interactive object (2x 0x0000 - 0xFFFF, 0x00 - 0xFF)
__del__ none simple destructor to close device (if forgotten)

Device control methods

Name Parameters Description
setVendorID vendorID vendor ID setter method (executes newDeviceSetting method automatically; 0x0000 - 0xFFFF)
setProductID productID product ID setter method (executes newDeviceSetting method automatically; 0x0000 - 0xFFFF)
setReportID reportID report ID setter method (0x00 - 0xFF)
open none device opening method
close none device closing method

Internal helper methods

Name Parameters Description
newDeviceSetting state device address changing state manipulation method (True/False)
toHex byte byte to 2-digit hex value converter method (0 - 255)
bytesToHex byteString byte string to 2-digit hex value converter method (byte-like object)
hexStringToBytes inputString 2-digit hex values string to byte object converter method (string formatted like 46 55 52 52 59 ...)
isDataOnlySelected taskList is silent mode selection present on the task list checker method (e.g. output from the argumentExtractor method)
isOnlyDeviceSettingsOnList taskList is only device address and report ID settings on the task list checker method

Interpreter methods

Name Parameters Description
getIntFromString string string of most popular types to integer converter method (e.g. 0xFF, 0b1010 or 0o777)
checkTaskList taskList task list validator method (e.g. output from the argumentExtractor method)
argumentExtractor data string array to task list converter method (e.g. sys.argv)

Text User Interface methods

Name Parameters Description
headerDisplay none program header display method
displayHelp none program help display method
ISOdataPrintOut status, data1, data2, data3 ISO read data print out method
RAWdataPrintOut status, data1, data2, data3 RAW read data print out method
interpreter none main interpreter method

MSR605X command wrappers for Text User Interface

Name Parameters Description
readISO none ISO card read wrapper method
writeISO track1, track2, track3 ISO card write wrapper method (strings)
copyISO none ISO card copy wrapper method
readRAW none RAW card read wrapper method
writeRAW track1, track2, track3 RAW card write wrapper method (hexStrings; 8-bit mode only for now)
copyRAW none RAW card copy wrapper method (8-bit mode only for now)
setBPC track1, track2, track3 bits per character setter wrapper method (5 - 8)
setBPI track1, track2, track3 bits per inch setter wrapper method (3x None, 75 or 210)
setHiCo none Hi-Co mode setter wrapper method
setLoCo none Lo-Co mode setter wrapper method
setLeadingZeroes leadZeroTrack1and3, leadZeroTrack2 leading zeroes setter wrapper method (2x 0 - 255)
eraseCard track1, track2, track3 card erase wrapper method (3x True/False)
deviceModel none device model gathering wrapper method
firmwareVersion none device firmware version gathering wrapper method
allLEDOff none all LEDs off wrapper method
greenLED none green LED on wrapper method
greenAndYellowLED none green and yellow LEDs on (yellowLedOn wrapper) method
redLED none red LED on wrapper method
allLEDOn none all LEDs on wrapper method
communicationTest none communication test wrapper method
getLeadingZeroes none leading zeroes setting gathering wrapper method
getCoercivity none coercivity setting wrapper method
sensorTest none sensor test wrapper method (OPERATION PROBABLY UNSUPPORTED IN MSR605X)
RAMTest none RAM test wrapper method (OPERATION PROBABLY UNSUPPORTED IN MSR605X)
softReset none soft reset wrapper method
hardReset none hard reset wrapper method

Known issues

Card write or erase ends with error

You're probably using Hi-Co card and just connected the MSR605X to the USB port.

Please note, that MSR605X loves to start in Lo-Co mode. You can check it by getting coercivity setting straight after connecting the device to the computer.
Any write operation (card erase and copy included) will obviously fail in such setup (Hi-Co card writing in the Lo-Co mode), so You have to switch to Hi-Co before writing to such card.

Tip

You don't have to manually set Hi-Co or Lo-Co mode and then run this script again to write or erase card.
It is possible to do both in a single run.

See this example: ./msr605x.py -h -w "TEST" "123" "456"

Why turning on the yellow LED turns on green too?

That's the way manufacturer created this device. Yellow LED on command in fact turns on green and yellow and turns off the red one.

So, the same situation with red LED?

Yup, unfortunately. This command actually turns off green and yellow LED and turns on the red one.

Sensor and RAM tests return errors

Those tests are mentioned in the MSR605 Programmer's Manual, but seems unsupported in the MSR605X (always return FAIL). It is unlikely that my device has problems with memory or sensors as everything works properly. However I decided to leave those tests in case they would work for somebody.

Devices used for testing

I only have one MSR605X device, which announces itself to the system as DEFTUN MSR Reader in FS Mode / MagTek Magstripe Insert Reader (0801:0003). It is possible that there are other devices marked as compatible with MSR605X that won't work with this solution. If You can test it - please, tell me if anything works or not.

Disclaimer

I've made much effort to provide here working codes with hope they'll be useful and free from any bugs. However I can't guarantee anything.

The software is provided here "AS IS" and I take no responsibility for anything.
You're using it on Your own risk!

License

Free. Please use this code with respect to the author (me).

Bartłomiej "Magnetic-Fox" Węgrzyn,
April 14, 2026

About

Python library to utilize MSR605X magnetic stripe card reader/writer with additional text user interface to use as a standalone utility

Topics

Resources

Stars

Watchers

Forks

Releases

No releases published

Packages

 
 
 

Contributors

Languages