A library to read HID RFID cards through the wiegand protocol. This was tested with the HID ProxPoint Plus 6005BG00.

Dependents:   HID_ProxCard_Wiegand_Example

Wiegand Library for HID ProxPoint Plus

While this library should be able to read any wiegand input, the buffer can only store 64 bits, and it expects there to be less than a 5ms delay between each bit sent.

Here is a picture of some example wiring:

To use this library use the following pin attachments, the 6005BG00 has its pinouts on its back label (top right).

6005BG00 WireMBED PIN
data0p30
data1p29
holdp28
GNDGND
DRAINGND
5-16V (red)Vu

Here is a picuture of it wired up: /media/uploads/cbookman3/10264542_10152398127452363_476958199_n.jpg

include the mbed library with this snippet

void void onCardRead();
Wiegand rfid(p30, p29, p28, &onCardRead);

int main() {
  while(1) {
    rfid.doEvents(); //checks if data has been fully read, and calls the callback
  }
}

void onCardRead() {
  /*
    Do stuff with data, as we've fully read the card.
    WHen this function exits, RFID reader will be reset to read
    Another Card
  */
   //returns the unique student identifier on a buzzcard  (6 digit number on back of buzzcard below gatech seal)
    uint64_t rawCardData = rfid.getBits(14,33); 
}

Description of public methods

methoddescription
Wiegand(PinName pdata0, PinName pdata1, PinName pHold, void (*onCardRead)());constructor, call WIegand wiegand (...)
void doEvents(void)checks if all RFID data has been read though the use of a timer, and calls the onCardRead callback
uint8_t bitsRead(void)returns the number of bits read
uint64_t getBits(uint8_t start, uint8_t end)Returns the bits read from in [start,end] (Inclusive). If its an invalid range, returns 0

Example Program

Import programHID_ProxCard_Wiegand_Example

Example program to read HID ProxCards using the gatech BuzzCard format with a HID ProxPoint Plus 6005BG00.

Here is a video of the example program in action:

ProxPoint Plus 6005BG00 Oscilloscope Capture

/media/uploads/cbookman3/oscopecapture.jpg

Gatech BuzzCard Protocol

The rfid buzzcard unique student identifier can be found on the back of your buzzcard below the shiny gatech seal (6 digit number). Each buzzcard's rfid tag stores 35 bits of data, but only bits [14,33] contain your id (bit index starts at 0, and range is inclusive).

Wiegand.cpp

Committer:
cbookman3
Date:
2014-04-23
Revision:
2:47ffa4e32ce3
Parent:
1:a960b42eb198

File content as of revision 2:47ffa4e32ce3:

#include "Wiegand.h"
#include "mbed.h"

Wiegand::Wiegand(PinName pdata0, PinName pdata1, PinName pHold, void (*onCardRead)()) :  _data0ISR(pdata0), _data1ISR(pdata1), _hold(pHold) {
    _onCardRead = onCardRead;
    /*
        stop reader from sending us any data
        and ensure after this block that no data through 
        wiegand gets sent
    */
    _hold = 1;
    wait_ms(250); 
    _sizeOfBuffer = sizeof(_buffer)/sizeof(*_buffer);
    _resetBuffer();
    
    /* Attach our interrupts, and start the ISRs */
    _attachInterrupts();
    _hold = 0; //start sending data
}

/*
    Check if we've read all card data
*/
void Wiegand::doEvents(void) {
    if(_bitsRead > 0 && _lastISR.read_ms() > 5) {
        _onCardRead();
        _resetBuffer();
        _hold = 0;   
    }
}
    
/*
    return number of bits currently read
*/
uint8_t Wiegand::bitsRead(void) {
    return _bitsRead;
}
    
/*
    Returns the bits read from in [start,end] (Inclusive).
    if [start,end] not in range of the bits read, 0 is returned
*/
uint64_t Wiegand::getBits(uint8_t start, uint8_t end) {
    //make sure the start and end indexes don't over index our read bit buffer
    if(!(start < _bitsRead) || !(end < _bitsRead)) {
        return 0;
    }
    uint64_t output = 0;
    for(int i = start; i <= end; ++i) {
        output <<=1;
        output |= 0x1 & _buffer[i]; 
    }
    return output;
}

/*
    Resets the buffer to its intial state (0), and _bitsRead = 0
*/
void Wiegand::_resetBuffer(void) {
     for(int i = 0, l = _sizeOfBuffer; i <l; ++i) {  _buffer[i] = 0; }
    _bitsRead = 0;
}

/*
    Attach ISRs to the rising edge
*/
void Wiegand::_attachInterrupts(void) {
    _data0ISR.rise(this, &Wiegand::_data0ISRAction);
    _data1ISR.rise(this, &Wiegand::_data1ISRAction);
}

/*
    Data0ISR Routine, called by rising edge of data0
*/
void Wiegand::_data0ISRAction(void) {
    _lastISR.reset();
    _lastISR.start();
    _hold = 1;
    if(_bitsRead < _sizeOfBuffer) {
        _buffer[_bitsRead++] = 0;
    }
}

/*
    Data1ISR Routine, called by rising edge of data1
*/
void Wiegand::_data1ISRAction(void) {
    _lastISR.reset();
    _lastISR.start();
    _hold = 1;
    if(_bitsRead < _sizeOfBuffer) {
        _buffer[_bitsRead++] = 1;
    }
}