Exemple #1
0
// optional verify as writing config block may casue next read to fail
BOOL t55x7_write_block(BYTE block, BYTE *data, BOOL lock, BOOL verify)
{
    BYTE tmp[71], p;

    if(block > T55X7_DATABLOCKS - 1)
        return FALSE;

    // create 38 or 70 bit command block: T55X7_STD_WRITE_P0 + [PWD] + Lock Bit + 32 bits Data + 3 bits address
    memset(tmp, '\0', sizeof(tmp));

    // command
    memcpy(tmp, T55X7_STD_WRITE_P0, 2);
    p= 2;

    // password
    if(PWD_Mode)
    {
        hextobinstring(tmp + p, Password);
        p += 32;
    }

    // lockbit
    inttobinstring(tmp + p, (unsigned int) lock, 1);
    ++p;

    // data
    hextobinstring(tmp + p, data);
    p += T55X7_BLOCKSIZE;

    // address
    inttobinstring(tmp + p, (unsigned int) block, 3);
    p += 3;

    // send
    if(!t55x7_send_command(NULL, tmp, strlen(tmp), NO_RESET, NO_SYNC, 0))
         return FALSE;

    // no ack, so read back and verify
    // delay for long enough to allow write plus TX->RX period
    Delay_us((T55X7_WRITE_DELAY * RFIDlerConfig.FrameClock + RFIDlerConfig.RWD_Wait_Switch_TX_RX * RFIDlerConfig.FrameClock) / 100L);

    if(!verify)
        return TRUE;

    if(!t55x7_read_block(tmp, block))
        return FALSE;
    if(memcmp(tmp, data, HEXDIGITS(T55X7_BLOCKSIZE)) != 0)
        return FALSE;

    return TRUE;
}
Exemple #2
0
// set password and mode, and return UID
BOOL q5_login(BYTE *response, BYTE *pass)
{
    BYTE tmp[35];

    // check we need password - if we can get UID without, then we don't
    if(q5_get_uid(tmp))
        return FALSE;

    if(strlen(pass) == 0)
        pass= Q5_DEFAULT_PWD;

    memcpy(tmp, Q5_AOR, 2);
    hextobinstring(tmp + 2, pass);
    tmp[34]= '\0';

    // send password
    if (!q5_send_command(response, tmp, strlen(tmp), RESET, NO_SYNC, 0))
        return FALSE;

    // see if we can now get UID
    if(!q5_get_uid(tmp))
        return FALSE;

    PWD_Mode= TRUE;
    strcpy(Password, pass);
    strcpy(response, pass);
    return TRUE;
}
Exemple #3
0
BOOL q5_read_block(BYTE *response, BYTE block)
{
    BYTE tmp[39], retry, reset= FALSE;

    if(block > Q5_DATABLOCKS - 1)
        return FALSE;

    // create 6 or 38 bit command block: Q5_DIRECT_ACCESS + PWD_Mode + [PWD] + 3 bits address
    memset(tmp, '\0', 39);
    memcpy(tmp, Q5_DIRECT_ACCESS, 2);
    if(PWD_Mode)
    {
        tmp[2]= '1';
        hextobinstring(tmp + 3, Password);
        inttobinstring(tmp + 34, (unsigned int) block, 3);
    }
    else
    {
        tmp[2]= '0';
        inttobinstring(tmp + 3, (unsigned int) block, 3);
    }

    retry= RFIDlerConfig.Repeat;
    while(retry--)
    {
        //DEBUG_PIN_4= !DEBUG_PIN_4;
        //DEBUG_PIN_4= !DEBUG_PIN_4;
        if(q5_send_command(response, tmp, strlen(tmp), reset, NO_SYNC, 32))
            return TRUE;
        // try resetting tag
        reset= TRUE;
    }

    return FALSE;
}
Exemple #4
0
// auth in password mode
BOOL hitag2_pwd_auth(BYTE *response, BYTE *pwd)
{
    BYTE tmp[37];

    // restart the tag
    if(!hitag2_get_uid(tmp))
        return FALSE;

    if(strlen(pwd) == 0)
        pwd= HITAG2_PWD_DEFAULT;

    // use default transport key if none specified
    if(!hextobinstring(tmp, pwd))
        return FALSE;

    // wait for RX->TX period, then send 32 bit PWD
    if(!rwd_send(tmp, strlen(tmp), NO_RESET, BLOCK, RWD_STATE_WAKING, RFIDlerConfig.FrameClock, 0, RFIDlerConfig.RWD_Wait_Switch_RX_TX, RFIDlerConfig.RWD_Zero_Period, RFIDlerConfig.RWD_One_Period, RFIDlerConfig.RWD_Gap_Period, RFIDlerConfig.RWD_Wait_Switch_TX_RX))
        return FALSE;

    // skip 1/2 bit to synchronise manchester
    HW_Skip_Bits= 1;
    // get 37 bit response: sync + config byte + 24 bit TAG pwd
    if(read_ask_data(RFIDlerConfig.FrameClock, RFIDlerConfig.DataRate, tmp, 37, RFIDlerConfig.Sync, RFIDlerConfig.SyncBits, RFIDlerConfig.Timeout, ONESHOT_READ, BINARY) == 37)
    {
        // check sync bits
        if (memcmp(tmp, Hitag2Sync, 5) != 0)
            return FALSE;
        binarraytohex(response, tmp + 5, 32);
        return TRUE;
    }
    return FALSE;
}
Exemple #5
0
BOOL hitag1_write_page(BYTE block, BYTE *data)
{
    BYTE crc, command[21], tmp[33], tmp1[4];

    if(block > HITAG1_DATABLOCKS - 1)
        return FALSE;

    // get tag's UID for select command
    if(!hitag1_get_uid(tmp))
        return FALSE;

    // select for read/write
    hitag1_select(tmp, tmp);

    // convert data to binstring for send
    if(hextobinstring(tmp, data) != 32)
        return FALSE;

    // create and send 12 bit command block: HITAG1_WRPPAGE (4 bits) + 8 bit address
    memcpy(command, HITAG1_WRPPAGE, 4);
    inttobinstring(command + 4, (unsigned int) block, 8);
    command[12]= '\0';
    if(!hitag1_send_command(tmp1, command, NO_RESET, NO_SYNC, 0, ACK))
        return FALSE;

    // delay to switch back to write mode
    Delay_us((RFIDlerConfig.RWD_Wait_Switch_RX_TX * RFIDlerConfig.FrameClock) / 100);

    // now send data
    if(!hitag1_send_command(tmp1, tmp, NO_RESET, NO_SYNC, 0, ACK))
        return FALSE;

    // read back and verify
    // delay for long enough to allow write plus RX->TX period
    Delay_us((HITAG1_WRITE_DELAY * RFIDlerConfig.FrameClock + RFIDlerConfig.RWD_Wait_Switch_RX_TX * RFIDlerConfig.FrameClock) / 100);
    if(!hitag1_read_page(tmp, block))
        return FALSE;

    if(memcmp(tmp, data, 8) != 0)
        return FALSE;

    return TRUE;
}
Exemple #6
0
// select HITAG1 for read/write operations - return config page
BOOL hitag1_select(BYTE *response, BYTE *uid)
{
    BYTE command[38], tmp1[33]; // command: 5 bit command + 32 bit uid + NULL

    strcpy(command, HITAG1_SELECT);
    if(!hextobinstring(command + 5, uid))
        return FALSE;

    // send command and get back 1 sync bit + 32 bit configpage
    if(!hitag1_send_command(tmp1, command, NO_RESET, NO_SYNC, 33, NO_ACK))
        return FALSE;

    // check sync bit
    if(tmp1[0] == 0x01)
    {
        binarraytohex(response, tmp1 + 1, 32);
        return TRUE;
    }
    return FALSE;
}
Exemple #7
0
BOOL hitag2_write_page(BYTE block, BYTE *data)
{
    BYTE command[11], tmp[37], tmp1[37], tmp2[37], tmphex[9];

    if(block > HITAG2_DATABLOCKS - 1)
        return FALSE;

    // create 10 bit command block: HITAG2_WRIE_PAGE + 3 bits address + invert(HITAG2_WRITE_PAGE + 3 bits address)
    memcpy(command, HITAG2_WRITE_PAGE, 2);
    inttobinstring(command + 2, (unsigned int) block, 3);
    invertbinstring(command + 5, command);
    command[10]= '\0';

    // encrypt command if in crypto mode
    if(CryptoActive)
        hitag2_binstring_crypt(tmp, command);
    else
        memcpy(tmp, command, 11);

    // convert data to binstring for send
    if(hextobinstring(tmp1, data) != 32)
        return FALSE;

    // send command with RX->TX delay and no reset
    if(!rwd_send(tmp, strlen(tmp), NO_RESET, BLOCK, RWD_STATE_WAKING, RFIDlerConfig.FrameClock, 0, RFIDlerConfig.RWD_Wait_Switch_RX_TX, RFIDlerConfig.RWD_Zero_Period, RFIDlerConfig.RWD_One_Period, RFIDlerConfig.RWD_Gap_Period, RFIDlerConfig.RWD_Wait_Switch_TX_RX))
        return FALSE;

    // skip 1/2 bit to synchronise manchester
    HW_Skip_Bits= 1;
    // get ACK - 10 bytes + sync
    if(read_ask_data(RFIDlerConfig.FrameClock, RFIDlerConfig.DataRate, tmp2, 15, RFIDlerConfig.Sync, RFIDlerConfig.SyncBits, RFIDlerConfig.Timeout, ONESHOT_READ, BINARY) == 15)
    {
        // check sync bits
        if (memcmp(tmp2, Hitag2Sync, 5) != 0)
            return FALSE;

        // decrypt
        if(CryptoActive)
            hitag2_binarray_crypt(tmp2 + 5, tmp2 + 5, 10);

        // check ACK - should be our original command echo'd back
        binarraytobinstring(tmp2 + 5, tmp2 + 5, 10);
        if(memcmp(command, tmp2 + 5, 10) != 0)
            return FALSE;
    }

    // encrypt data if in crypto mode
    if(CryptoActive)
        hitag2_binstring_crypt(tmp1, tmp1);

    // send data with RX->TX delay and no reset
    if(!rwd_send(tmp1, strlen(tmp1), NO_RESET, BLOCK, RWD_STATE_WAKING, RFIDlerConfig.FrameClock, 0, RFIDlerConfig.RWD_Wait_Switch_RX_TX, RFIDlerConfig.RWD_Zero_Period, RFIDlerConfig.RWD_One_Period, RFIDlerConfig.RWD_Gap_Period, RFIDlerConfig.RWD_Wait_Switch_TX_RX))
        return FALSE;

    // no ack, so read back and verify
    // delay for long enough to allow write plus RX->TX period
    Delay_us((HITAG2_WRITE_DELAY * RFIDlerConfig.FrameClock + RFIDlerConfig.RWD_Wait_Switch_RX_TX * RFIDlerConfig.FrameClock) / 100);
    if(!hitag2_read_page(tmp, block))
        return FALSE;
    if(memcmp(tmp, data, 8) != 0)
        return FALSE;

    return TRUE;
}