Skip to content

Instantly share code, notes, and snippets.

@camalot
Forked from ShakataGaNai/hid-prox-weigand.ino
Last active September 6, 2017 03:31
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save camalot/8398315191bb783ad1f49bbce3364ca6 to your computer and use it in GitHub Desktop.
Save camalot/8398315191bb783ad1f49bbce3364ca6 to your computer and use it in GitHub Desktop.
/*
* HID RFID Reader Wiegand Interface for Arduino Uno
* Originally by Daniel Smith, 2012.01.30 -- http://www.pagemac.com/projects/rfid/arduino_wiegand
*
* Updated 2016-11-23 by Jon "ShakataGaNai" Davis.
* See https://obviate.io/?p=7470 for more details & instructions
*/
#define MAX_BITS 100 // max number of bits
#define WEIGAND_WAIT_TIME 3000 // time to wait for another weigand pulse.
unsigned char databits[MAX_BITS]; // stores all of the data bits
unsigned char bitCount; // number of bits currently captured
unsigned char flagDone; // goes low when data is currently being captured
unsigned int weigand_counter; // countdown until we assume there are no more bits
unsigned long facilityCode=0; // decoded facility code
unsigned long cardCode=0; // decoded card code
int LED_GREEN = 11;
int LED_RED = 12;
int BEEP_BEEP = 10;
// interrupt that happens when INTO goes low (0 bit)
void ISR_INT0() {
//Serial.print("0"); // uncomment this line to display raw binary
bitCount++;
flagDone = 0;
weigand_counter = WEIGAND_WAIT_TIME;
}
// interrupt that happens when INT1 goes low (1 bit)
void ISR_INT1() {
//Serial.print("1"); // uncomment this line to display raw binary
databits[bitCount] = 1;
bitCount++;
flagDone = 0;
weigand_counter = WEIGAND_WAIT_TIME;
}
void setup() {
pinMode(LED_RED, OUTPUT);
pinMode(LED_GREEN, OUTPUT);
pinMode(BEEP_BEEP, OUTPUT);
digitalWrite(LED_RED, HIGH); // High = Off
digitalWrite(BEEP_BEEP, HIGH); // High = off
digitalWrite(LED_GREEN, LOW); // Low = On
pinMode(2, INPUT); // DATA0 (INT0)
pinMode(3, INPUT); // DATA1 (INT1)
Serial.begin(9600);
Serial.println("RFID Readers");
// binds the ISR functions to the falling edge of INTO and INT1
attachInterrupt(0, ISR_INT0, FALLING);
attachInterrupt(1, ISR_INT1, FALLING);
weigand_counter = WEIGAND_WAIT_TIME;
}
void loop()
{
// This waits to make sure that there have been no more data pulses before processing data
if (!flagDone) {
if (--weigand_counter == 0)
flagDone = 1;
}
// if we have bits and we the weigand counter went out
if (bitCount > 0 && flagDone) {
unsigned char i;
Serial.print("Read ");
Serial.print(bitCount);
Serial.print(" bits. ");
if (bitCount == 35) {
// 35 bit HID Corporate 1000 format
// facility code = bits 2 to 14
for (i=2; i<14; i++) {
facilityCode <<=1;
facilityCode |= databits[i];
}
// card code = bits 15 to 34
for (i=14; i<34; i++) {
cardCode <<=1;
cardCode |= databits[i];
}
printBits();
}
else if (bitCount == 26) {
// standard 26 bit format
// facility code = bits 2 to 9
for (i=1; i<9; i++) {
facilityCode <<=1;
facilityCode |= databits[i];
}
// card code = bits 10 to 23
for (i=9; i<25; i++) {
cardCode <<=1;
cardCode |= databits[i];
}
printBits();
} else if ( bitCount == 37 ) { // Wiegand 37bit
// https://www.ooaccess.com/kb/37-bit-fc/
// facility code = bits 1 to 16
for(i = 1; i < 17; ++i ) {
facilityCode <<=1;
facilityCode |= databits[i];
}
// card code = bits 17 to 35
for (i = 17; i < 36; ++i) {
cardCode <<=1;
cardCode |= databits[i];
}
printBits();
} else {
// you can add other formats if you want!
// Serial.println("Unable to decode.");
}
// cleanup and get ready for the next card
bitCount = 0;
facilityCode = 0;
cardCode = 0;
for (i=0; i<MAX_BITS; i++)
{
databits[i] = 0;
}
}
}
void printBits() {
Serial.print("FC = ");
Serial.print(facilityCode);
Serial.print(", CC = ");
Serial.println(cardCode);
// Now lets play with some LED's for fun:
digitalWrite(LED_RED, LOW); // Red
if(cardCode == 12345){
// If this one "bad" card, turn off green
// so it's just red. Otherwise you get orange-ish
digitalWrite(LED_GREEN, HIGH);
}
delay(500);
digitalWrite(LED_RED, HIGH); // Red Off
digitalWrite(LED_GREEN, LOW); // Green back on
// Lets be annoying and beep more
digitalWrite(BEEP_BEEP, LOW);
delay(500);
digitalWrite(BEEP_BEEP, HIGH);
delay(500);
digitalWrite(BEEP_BEEP, LOW);
delay(500);
digitalWrite(BEEP_BEEP, HIGH);
}
@camalot
Copy link
Author

camalot commented Sep 6, 2017

Added support for the Wiegand 37 bit card format

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment