mirror of
https://github.com/RfidResearchGroup/proxmark3.git
synced 2024-11-10 17:49:32 +08:00
Merge pull request #114 from pwpiwi/iso14443b_fix
fixing iso14443b (issue #103): fix bug introduced during Bigbuf rework
This commit is contained in:
commit
01b7a6a898
12 changed files with 418 additions and 663 deletions
|
@ -17,7 +17,7 @@ APP_CFLAGS = -DWITH_LF -DWITH_ISO15693 -DWITH_ISO14443a -DWITH_ISO14443b -DWITH_
|
|||
SRC_LF = lfops.c hitag2.c lfsampling.c
|
||||
SRC_ISO15693 = iso15693.c iso15693tools.c
|
||||
SRC_ISO14443a = epa.c iso14443a.c mifareutil.c mifarecmd.c mifaresniff.c
|
||||
SRC_ISO14443b = iso14443.c
|
||||
SRC_ISO14443b = iso14443b.c
|
||||
SRC_CRAPTO1 = crapto1.c crypto1.c des.c aes.c
|
||||
SRC_CRC = iso14443crc.c crc.c crc16.c crc32.c
|
||||
|
||||
|
|
|
@ -250,55 +250,6 @@ void MeasureAntennaTuningHf(void)
|
|||
}
|
||||
|
||||
|
||||
void SimulateTagHfListen(void)
|
||||
{
|
||||
// ToDo: historically this used the free buffer, which was 2744 Bytes long.
|
||||
// There might be a better size to be defined:
|
||||
#define HF_14B_SNOOP_BUFFER_SIZE 2744
|
||||
uint8_t *dest = BigBuf_malloc(HF_14B_SNOOP_BUFFER_SIZE);
|
||||
uint8_t v = 0;
|
||||
int i;
|
||||
int p = 0;
|
||||
|
||||
// We're using this mode just so that I can test it out; the simulated
|
||||
// tag mode would work just as well and be simpler.
|
||||
FpgaDownloadAndGo(FPGA_BITSTREAM_HF);
|
||||
FpgaWriteConfWord(FPGA_MAJOR_MODE_HF_READER_RX_XCORR | FPGA_HF_READER_RX_XCORR_848_KHZ | FPGA_HF_READER_RX_XCORR_SNOOP);
|
||||
|
||||
// We need to listen to the high-frequency, peak-detected path.
|
||||
SetAdcMuxFor(GPIO_MUXSEL_HIPKD);
|
||||
|
||||
FpgaSetupSsc();
|
||||
|
||||
i = 0;
|
||||
for(;;) {
|
||||
if(AT91C_BASE_SSC->SSC_SR & (AT91C_SSC_TXRDY)) {
|
||||
AT91C_BASE_SSC->SSC_THR = 0xff;
|
||||
}
|
||||
if(AT91C_BASE_SSC->SSC_SR & (AT91C_SSC_RXRDY)) {
|
||||
uint8_t r = (uint8_t)AT91C_BASE_SSC->SSC_RHR;
|
||||
|
||||
v <<= 1;
|
||||
if(r & 1) {
|
||||
v |= 1;
|
||||
}
|
||||
p++;
|
||||
|
||||
if(p >= 8) {
|
||||
dest[i] = v;
|
||||
v = 0;
|
||||
p = 0;
|
||||
i++;
|
||||
|
||||
if(i >= HF_14B_SNOOP_BUFFER_SIZE) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
}
|
||||
DbpString("simulate tag (now type bitsamples)");
|
||||
}
|
||||
|
||||
void ReadMem(int addr)
|
||||
{
|
||||
const uint8_t *data = ((uint8_t *)addr);
|
||||
|
@ -782,20 +733,17 @@ void UsbPacketReceived(uint8_t *packet, int len)
|
|||
#endif
|
||||
|
||||
#ifdef WITH_ISO14443b
|
||||
case CMD_ACQUIRE_RAW_ADC_SAMPLES_ISO_14443:
|
||||
AcquireRawAdcSamplesIso14443(c->arg[0]);
|
||||
break;
|
||||
case CMD_READ_SRI512_TAG:
|
||||
ReadSTMemoryIso14443(0x0F);
|
||||
ReadSTMemoryIso14443b(0x0F);
|
||||
break;
|
||||
case CMD_READ_SRIX4K_TAG:
|
||||
ReadSTMemoryIso14443(0x7F);
|
||||
ReadSTMemoryIso14443b(0x7F);
|
||||
break;
|
||||
case CMD_SNOOP_ISO_14443:
|
||||
SnoopIso14443();
|
||||
case CMD_SNOOP_ISO_14443B:
|
||||
SnoopIso14443b();
|
||||
break;
|
||||
case CMD_SIMULATE_TAG_ISO_14443:
|
||||
SimulateIso14443Tag();
|
||||
case CMD_SIMULATE_TAG_ISO_14443B:
|
||||
SimulateIso14443bTag();
|
||||
break;
|
||||
case CMD_ISO_14443B_COMMAND:
|
||||
SendRawCommand14443B(c->arg[0],c->arg[1],c->arg[2],c->d.asBytes);
|
||||
|
@ -911,10 +859,6 @@ void UsbPacketReceived(uint8_t *packet, int len)
|
|||
break;
|
||||
#endif
|
||||
|
||||
case CMD_SIMULATE_TAG_HF_LISTEN:
|
||||
SimulateTagHfListen();
|
||||
break;
|
||||
|
||||
case CMD_BUFF_CLEAR:
|
||||
BigBuf_Clear();
|
||||
break;
|
||||
|
|
|
@ -141,10 +141,10 @@ void EM4xReadWord(uint8_t Address, uint32_t Pwd, uint8_t PwdMode);
|
|||
void EM4xWriteWord(uint32_t Data, uint8_t Address, uint32_t Pwd, uint8_t PwdMode);
|
||||
|
||||
/// iso14443.h
|
||||
void SimulateIso14443Tag(void);
|
||||
void AcquireRawAdcSamplesIso14443(uint32_t parameter);
|
||||
void ReadSTMemoryIso14443(uint32_t);
|
||||
void RAMFUNC SnoopIso14443(void);
|
||||
void SimulateIso14443bTag(void);
|
||||
void AcquireRawAdcSamplesIso14443b(uint32_t parameter);
|
||||
void ReadSTMemoryIso14443b(uint32_t);
|
||||
void RAMFUNC SnoopIso14443b(void);
|
||||
void SendRawCommand14443B(uint32_t, uint32_t, uint8_t, uint8_t[]);
|
||||
|
||||
/// iso14443a.h
|
||||
|
|
File diff suppressed because it is too large
Load diff
|
@ -378,7 +378,7 @@ uint16_t printTraceLine(uint16_t tracepos, uint16_t traceLen, uint8_t *trace, ui
|
|||
oddparity ^= (((frame[j] & 0xFF) >> k) & 0x01);
|
||||
}
|
||||
uint8_t parityBits = parityBytes[j>>3];
|
||||
if (isResponse && (oddparity != ((parityBits >> (7-(j&0x0007))) & 0x01))) {
|
||||
if (protocol != ISO_14443B && isResponse && (oddparity != ((parityBits >> (7-(j&0x0007))) & 0x01))) {
|
||||
snprintf(line[j/16]+(( j % 16) * 4),110, "%02x! ", frame[j]);
|
||||
|
||||
} else {
|
||||
|
|
|
@ -25,154 +25,23 @@
|
|||
|
||||
static int CmdHelp(const char *Cmd);
|
||||
|
||||
int CmdHF14BDemod(const char *Cmd)
|
||||
{
|
||||
int i, j, iold;
|
||||
int isum, qsum;
|
||||
int outOfWeakAt;
|
||||
bool negateI, negateQ;
|
||||
|
||||
uint8_t data[256];
|
||||
int dataLen = 0;
|
||||
|
||||
// As received, the samples are pairs, correlations against I and Q
|
||||
// square waves. So estimate angle of initial carrier (or just
|
||||
// quadrant, actually), and then do the demod.
|
||||
|
||||
// First, estimate where the tag starts modulating.
|
||||
for (i = 0; i < GraphTraceLen; i += 2) {
|
||||
if (abs(GraphBuffer[i]) + abs(GraphBuffer[i + 1]) > 40) {
|
||||
break;
|
||||
}
|
||||
}
|
||||
if (i >= GraphTraceLen) {
|
||||
PrintAndLog("too weak to sync");
|
||||
return 0;
|
||||
}
|
||||
PrintAndLog("out of weak at %d", i);
|
||||
outOfWeakAt = i;
|
||||
|
||||
// Now, estimate the phase in the initial modulation of the tag
|
||||
isum = 0;
|
||||
qsum = 0;
|
||||
for (; i < (outOfWeakAt + 16); i += 2) {
|
||||
isum += GraphBuffer[i + 0];
|
||||
qsum += GraphBuffer[i + 1];
|
||||
}
|
||||
negateI = (isum < 0);
|
||||
negateQ = (qsum < 0);
|
||||
|
||||
// Turn the correlation pairs into soft decisions on the bit.
|
||||
j = 0;
|
||||
for (i = 0; i < GraphTraceLen / 2; i++) {
|
||||
int si = GraphBuffer[j];
|
||||
int sq = GraphBuffer[j + 1];
|
||||
if (negateI) si = -si;
|
||||
if (negateQ) sq = -sq;
|
||||
GraphBuffer[i] = si + sq;
|
||||
j += 2;
|
||||
}
|
||||
GraphTraceLen = i;
|
||||
|
||||
i = outOfWeakAt / 2;
|
||||
while (GraphBuffer[i] > 0 && i < GraphTraceLen)
|
||||
i++;
|
||||
if (i >= GraphTraceLen) goto demodError;
|
||||
|
||||
iold = i;
|
||||
while (GraphBuffer[i] < 0 && i < GraphTraceLen)
|
||||
i++;
|
||||
if (i >= GraphTraceLen) goto demodError;
|
||||
if ((i - iold) > 23) goto demodError;
|
||||
|
||||
PrintAndLog("make it to demod loop");
|
||||
|
||||
for (;;) {
|
||||
iold = i;
|
||||
while (GraphBuffer[i] >= 0 && i < GraphTraceLen)
|
||||
i++;
|
||||
if (i >= GraphTraceLen) goto demodError;
|
||||
if ((i - iold) > 6) goto demodError;
|
||||
|
||||
uint16_t shiftReg = 0;
|
||||
if (i + 20 >= GraphTraceLen) goto demodError;
|
||||
|
||||
for (j = 0; j < 10; j++) {
|
||||
int soft = GraphBuffer[i] + GraphBuffer[i + 1];
|
||||
|
||||
if (abs(soft) < (abs(isum) + abs(qsum)) / 20) {
|
||||
PrintAndLog("weak bit");
|
||||
}
|
||||
|
||||
shiftReg >>= 1;
|
||||
if(GraphBuffer[i] + GraphBuffer[i+1] >= 0) {
|
||||
shiftReg |= 0x200;
|
||||
}
|
||||
|
||||
i+= 2;
|
||||
}
|
||||
|
||||
if ((shiftReg & 0x200) && !(shiftReg & 0x001))
|
||||
{
|
||||
// valid data byte, start and stop bits okay
|
||||
PrintAndLog(" %02x", (shiftReg >> 1) & 0xff);
|
||||
data[dataLen++] = (shiftReg >> 1) & 0xff;
|
||||
if (dataLen >= sizeof(data)) {
|
||||
return 0;
|
||||
}
|
||||
} else if (shiftReg == 0x000) {
|
||||
// this is EOF
|
||||
break;
|
||||
} else {
|
||||
goto demodError;
|
||||
}
|
||||
}
|
||||
|
||||
uint8_t first, second;
|
||||
ComputeCrc14443(CRC_14443_B, data, dataLen-2, &first, &second);
|
||||
PrintAndLog("CRC: %02x %02x (%s)\n", first, second,
|
||||
(first == data[dataLen-2] && second == data[dataLen-1]) ?
|
||||
"ok" : "****FAIL****");
|
||||
|
||||
RepaintGraphWindow();
|
||||
return 0;
|
||||
|
||||
demodError:
|
||||
PrintAndLog("demod error");
|
||||
RepaintGraphWindow();
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CmdHF14BList(const char *Cmd)
|
||||
{
|
||||
PrintAndLog("Deprecated command, use 'hf list 14b' instead");
|
||||
|
||||
return 0;
|
||||
}
|
||||
int CmdHF14BRead(const char *Cmd)
|
||||
{
|
||||
UsbCommand c = {CMD_ACQUIRE_RAW_ADC_SAMPLES_ISO_14443, {strtol(Cmd, NULL, 0), 0, 0}};
|
||||
SendCommand(&c);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CmdHF14Sim(const char *Cmd)
|
||||
int CmdHF14BSim(const char *Cmd)
|
||||
{
|
||||
UsbCommand c={CMD_SIMULATE_TAG_ISO_14443};
|
||||
SendCommand(&c);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CmdHFSimlisten(const char *Cmd)
|
||||
{
|
||||
UsbCommand c = {CMD_SIMULATE_TAG_HF_LISTEN};
|
||||
UsbCommand c={CMD_SIMULATE_TAG_ISO_14443B};
|
||||
SendCommand(&c);
|
||||
return 0;
|
||||
}
|
||||
|
||||
int CmdHF14BSnoop(const char *Cmd)
|
||||
{
|
||||
UsbCommand c = {CMD_SNOOP_ISO_14443};
|
||||
UsbCommand c = {CMD_SNOOP_ISO_14443B};
|
||||
SendCommand(&c);
|
||||
return 0;
|
||||
}
|
||||
|
@ -288,7 +157,7 @@ int CmdHF14BCmdRaw (const char *cmd) {
|
|||
if (WaitForResponseTimeout(CMD_ACK,&resp,1000)) {
|
||||
recv = resp.d.asBytes;
|
||||
PrintAndLog("received %i octets",resp.arg[0]);
|
||||
if(!resp.arg[0])
|
||||
if(resp.arg[0] == 0)
|
||||
return 0;
|
||||
hexout = (char *)malloc(resp.arg[0] * 3 + 1);
|
||||
if (hexout != NULL) {
|
||||
|
@ -298,11 +167,13 @@ int CmdHF14BCmdRaw (const char *cmd) {
|
|||
}
|
||||
PrintAndLog("%s", hexout);
|
||||
free(hexout);
|
||||
ComputeCrc14443(CRC_14443_B, recv, resp.arg[0]-2, &first, &second);
|
||||
if(recv[resp.arg[0]-2]==first && recv[resp.arg[0]-1]==second) {
|
||||
PrintAndLog("CRC OK");
|
||||
} else {
|
||||
PrintAndLog("CRC failed");
|
||||
if (resp.arg[0] > 2) {
|
||||
ComputeCrc14443(CRC_14443_B, recv, resp.arg[0]-2, &first, &second);
|
||||
if(recv[resp.arg[0]-2]==first && recv[resp.arg[0]-1]==second) {
|
||||
PrintAndLog("CRC OK");
|
||||
} else {
|
||||
PrintAndLog("CRC failed");
|
||||
}
|
||||
}
|
||||
} else {
|
||||
PrintAndLog("malloc failed your client has low memory?");
|
||||
|
@ -385,12 +256,9 @@ int CmdHF14BWrite( const char *Cmd){
|
|||
static command_t CommandTable[] =
|
||||
{
|
||||
{"help", CmdHelp, 1, "This help"},
|
||||
{"demod", CmdHF14BDemod, 1, "Demodulate ISO14443 Type B from tag"},
|
||||
{"list", CmdHF14BList, 0, "[Deprecated] List ISO 14443b history"},
|
||||
{"read", CmdHF14BRead, 0, "Read HF tag (ISO 14443)"},
|
||||
{"sim", CmdHF14Sim, 0, "Fake ISO 14443 tag"},
|
||||
{"simlisten", CmdHFSimlisten, 0, "Get HF samples as fake tag"},
|
||||
{"snoop", CmdHF14BSnoop, 0, "Eavesdrop ISO 14443"},
|
||||
{"sim", CmdHF14BSim, 0, "Fake ISO 14443B tag"},
|
||||
{"snoop", CmdHF14BSnoop, 0, "Eavesdrop ISO 14443B"},
|
||||
{"sri512read", CmdSri512Read, 0, "Read contents of a SRI512 tag"},
|
||||
{"srix4kread", CmdSrix4kRead, 0, "Read contents of a SRIX4K tag"},
|
||||
{"raw", CmdHF14BCmdRaw, 0, "Send raw hex data to tag"},
|
||||
|
|
|
@ -89,7 +89,6 @@ typedef struct {
|
|||
|
||||
// For the 13.56 MHz tags
|
||||
#define CMD_ACQUIRE_RAW_ADC_SAMPLES_ISO_15693 0x0300
|
||||
#define CMD_ACQUIRE_RAW_ADC_SAMPLES_ISO_14443 0x0301
|
||||
#define CMD_READ_SRI512_TAG 0x0303
|
||||
#define CMD_READ_SRIX4K_TAG 0x0304
|
||||
#define CMD_READER_ISO_15693 0x0310
|
||||
|
@ -105,9 +104,8 @@ typedef struct {
|
|||
#define CMD_SIMULATE_HITAG 0x0371
|
||||
#define CMD_READER_HITAG 0x0372
|
||||
|
||||
#define CMD_SIMULATE_TAG_HF_LISTEN 0x0380
|
||||
#define CMD_SIMULATE_TAG_ISO_14443 0x0381
|
||||
#define CMD_SNOOP_ISO_14443 0x0382
|
||||
#define CMD_SIMULATE_TAG_ISO_14443B 0x0381
|
||||
#define CMD_SNOOP_ISO_14443B 0x0382
|
||||
#define CMD_SNOOP_ISO_14443a 0x0383
|
||||
#define CMD_SIMULATE_TAG_ISO_14443a 0x0384
|
||||
#define CMD_READER_ISO_14443a 0x0385
|
||||
|
|
|
@ -59,7 +59,6 @@ local _commands = {
|
|||
|
||||
--// For the 13.56 MHz tags
|
||||
CMD_ACQUIRE_RAW_ADC_SAMPLES_ISO_15693 = 0x0300,
|
||||
CMD_ACQUIRE_RAW_ADC_SAMPLES_ISO_14443 = 0x0301,
|
||||
CMD_READ_SRI512_TAG = 0x0303,
|
||||
CMD_READ_SRIX4K_TAG = 0x0304,
|
||||
CMD_READER_ISO_15693 = 0x0310,
|
||||
|
@ -76,9 +75,8 @@ local _commands = {
|
|||
CMD_SIMULATE_HITAG = 0x0371,
|
||||
CMD_READER_HITAG = 0x0372,
|
||||
|
||||
CMD_SIMULATE_TAG_HF_LISTEN = 0x0380,
|
||||
CMD_SIMULATE_TAG_ISO_14443 = 0x0381,
|
||||
CMD_SNOOP_ISO_14443 = 0x0382,
|
||||
CMD_SIMULATE_TAG_ISO_14443B = 0x0381,
|
||||
CMD_SNOOP_ISO_14443B = 0x0382,
|
||||
CMD_SNOOP_ISO_14443a = 0x0383,
|
||||
CMD_SIMULATE_TAG_ISO_14443a = 0x0384,
|
||||
CMD_READER_ISO_14443a = 0x0385,
|
||||
|
|
BIN
fpga/fpga_hf.bit
BIN
fpga/fpga_hf.bit
Binary file not shown.
|
@ -73,9 +73,6 @@ wire hi_read_rx_xcorr_848 = conf_word[0];
|
|||
// and whether to drive the coil (reader) or just short it (snooper)
|
||||
wire hi_read_rx_xcorr_snoop = conf_word[1];
|
||||
|
||||
// Divide the expected subcarrier frequency for hi_read_rx_xcorr by 4
|
||||
wire hi_read_rx_xcorr_quarter = conf_word[2];
|
||||
|
||||
// For the high-frequency simulated tag: what kind of modulation to use.
|
||||
wire [2:0] hi_simulate_mod_type = conf_word[2:0];
|
||||
|
||||
|
@ -102,7 +99,7 @@ hi_read_rx_xcorr hrxc(
|
|||
hrxc_ssp_frame, hrxc_ssp_din, ssp_dout, hrxc_ssp_clk,
|
||||
cross_hi, cross_lo,
|
||||
hrxc_dbg,
|
||||
hi_read_rx_xcorr_848, hi_read_rx_xcorr_snoop, hi_read_rx_xcorr_quarter
|
||||
hi_read_rx_xcorr_848, hi_read_rx_xcorr_snoop
|
||||
);
|
||||
|
||||
hi_simulate hs(
|
||||
|
|
|
@ -10,7 +10,7 @@ module hi_read_rx_xcorr(
|
|||
ssp_frame, ssp_din, ssp_dout, ssp_clk,
|
||||
cross_hi, cross_lo,
|
||||
dbg,
|
||||
xcorr_is_848, snoop, xcorr_quarter_freq
|
||||
xcorr_is_848, snoop
|
||||
);
|
||||
input pck0, ck_1356meg, ck_1356megb;
|
||||
output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4;
|
||||
|
@ -20,58 +20,24 @@ module hi_read_rx_xcorr(
|
|||
output ssp_frame, ssp_din, ssp_clk;
|
||||
input cross_hi, cross_lo;
|
||||
output dbg;
|
||||
input xcorr_is_848, snoop, xcorr_quarter_freq;
|
||||
input xcorr_is_848, snoop;
|
||||
|
||||
// Carrier is steady on through this, unless we're snooping.
|
||||
assign pwr_hi = ck_1356megb & (~snoop);
|
||||
assign pwr_oe1 = 1'b0;
|
||||
assign pwr_oe2 = 1'b0;
|
||||
assign pwr_oe3 = 1'b0;
|
||||
assign pwr_oe4 = 1'b0;
|
||||
|
||||
reg ssp_clk;
|
||||
reg ssp_frame;
|
||||
wire adc_clk = ck_1356megb;
|
||||
|
||||
reg fc_div_2;
|
||||
always @(posedge ck_1356meg)
|
||||
fc_div_2 = ~fc_div_2;
|
||||
|
||||
reg fc_div_4;
|
||||
always @(posedge fc_div_2)
|
||||
fc_div_4 = ~fc_div_4;
|
||||
|
||||
reg fc_div_8;
|
||||
always @(posedge fc_div_4)
|
||||
fc_div_8 = ~fc_div_8;
|
||||
|
||||
reg adc_clk;
|
||||
|
||||
always @(xcorr_is_848 or xcorr_quarter_freq or ck_1356meg)
|
||||
if(~xcorr_quarter_freq)
|
||||
begin
|
||||
if(xcorr_is_848)
|
||||
// The subcarrier frequency is fc/16; we will sample at fc, so that
|
||||
// means the subcarrier is 1 1 1 1 1 1 1 1 0 0 0 0 0 0 0 0 1 1 ...
|
||||
adc_clk <= ck_1356meg;
|
||||
else
|
||||
// The subcarrier frequency is fc/32; we will sample at fc/2, and
|
||||
// the subcarrier will look identical.
|
||||
adc_clk <= fc_div_2;
|
||||
end
|
||||
else
|
||||
begin
|
||||
if(xcorr_is_848)
|
||||
// The subcarrier frequency is fc/64
|
||||
adc_clk <= fc_div_4;
|
||||
else
|
||||
// The subcarrier frequency is fc/128
|
||||
adc_clk <= fc_div_8;
|
||||
end
|
||||
always @(negedge ck_1356megb)
|
||||
fc_div_2 <= fc_div_2 + 1;
|
||||
|
||||
// When we're a reader, we just need to do the BPSK demod; but when we're an
|
||||
// eavesdropper, we also need to pick out the commands sent by the reader,
|
||||
// using AM. Do this the same way that we do it for the simulated tag.
|
||||
reg after_hysteresis, after_hysteresis_prev;
|
||||
reg after_hysteresis, after_hysteresis_prev, after_hysteresis_prev_prev;
|
||||
reg [11:0] has_been_low_for;
|
||||
always @(negedge adc_clk)
|
||||
begin
|
||||
|
@ -97,12 +63,24 @@ end
|
|||
// Let us report a correlation every 4 subcarrier cycles, or 4*16 samples,
|
||||
// so we need a 6-bit counter.
|
||||
reg [5:0] corr_i_cnt;
|
||||
reg [5:0] corr_q_cnt;
|
||||
// And a couple of registers in which to accumulate the correlations.
|
||||
reg signed [15:0] corr_i_accum;
|
||||
reg signed [15:0] corr_q_accum;
|
||||
// we would add at most 32 times adc_d, the result can be held in 13 bits.
|
||||
// Need one additional bit because it can be negative as well
|
||||
reg signed [13:0] corr_i_accum;
|
||||
reg signed [13:0] corr_q_accum;
|
||||
reg signed [7:0] corr_i_out;
|
||||
reg signed [7:0] corr_q_out;
|
||||
// clock and frame signal for communication to ARM
|
||||
reg ssp_clk;
|
||||
reg ssp_frame;
|
||||
|
||||
|
||||
always @(negedge adc_clk)
|
||||
begin
|
||||
if (xcorr_is_848 | fc_div_2)
|
||||
corr_i_cnt <= corr_i_cnt + 1;
|
||||
end
|
||||
|
||||
|
||||
// ADC data appears on the rising edge, so sample it on the falling edge
|
||||
always @(negedge adc_clk)
|
||||
|
@ -110,24 +88,24 @@ begin
|
|||
// These are the correlators: we correlate against in-phase and quadrature
|
||||
// versions of our reference signal, and keep the (signed) result to
|
||||
// send out later over the SSP.
|
||||
if(corr_i_cnt == 7'd63)
|
||||
if(corr_i_cnt == 6'd0)
|
||||
begin
|
||||
if(snoop)
|
||||
begin
|
||||
corr_i_out <= {corr_i_accum[12:6], after_hysteresis_prev};
|
||||
corr_q_out <= {corr_q_accum[12:6], after_hysteresis};
|
||||
// Send only 7 most significant bits of tag signal (signed), LSB is reader signal:
|
||||
corr_i_out <= {corr_i_accum[13:7], after_hysteresis_prev_prev};
|
||||
corr_q_out <= {corr_q_accum[13:7], after_hysteresis_prev};
|
||||
after_hysteresis_prev_prev <= after_hysteresis;
|
||||
end
|
||||
else
|
||||
begin
|
||||
// Only correlations need to be delivered.
|
||||
// 8 most significant bits of tag signal
|
||||
corr_i_out <= corr_i_accum[13:6];
|
||||
corr_q_out <= corr_q_accum[13:6];
|
||||
end
|
||||
|
||||
corr_i_accum <= adc_d;
|
||||
corr_q_accum <= adc_d;
|
||||
corr_q_cnt <= 4;
|
||||
corr_i_cnt <= 0;
|
||||
end
|
||||
else
|
||||
begin
|
||||
|
@ -136,18 +114,16 @@ begin
|
|||
else
|
||||
corr_i_accum <= corr_i_accum + adc_d;
|
||||
|
||||
if(corr_q_cnt[3])
|
||||
corr_q_accum <= corr_q_accum - adc_d;
|
||||
else
|
||||
if(corr_i_cnt[3] == corr_i_cnt[2]) // phase shifted by pi/2
|
||||
corr_q_accum <= corr_q_accum + adc_d;
|
||||
else
|
||||
corr_q_accum <= corr_q_accum - adc_d;
|
||||
|
||||
corr_i_cnt <= corr_i_cnt + 1;
|
||||
corr_q_cnt <= corr_q_cnt + 1;
|
||||
end
|
||||
|
||||
// The logic in hi_simulate.v reports 4 samples per bit. We report two
|
||||
// (I, Q) pairs per bit, so we should do 2 samples per pair.
|
||||
if(corr_i_cnt == 6'd31)
|
||||
if(corr_i_cnt == 6'd32)
|
||||
after_hysteresis_prev <= after_hysteresis;
|
||||
|
||||
// Then the result from last time is serialized and send out to the ARM.
|
||||
|
@ -168,7 +144,9 @@ begin
|
|||
end
|
||||
end
|
||||
|
||||
if(corr_i_cnt[5:2] == 4'b000 || corr_i_cnt[5:2] == 4'b1000)
|
||||
// set ssp_frame signal for corr_i_cnt = 0..3 and corr_i_cnt = 32..35
|
||||
// (send two frames with 8 Bits each)
|
||||
if(corr_i_cnt[5:2] == 4'b0000 || corr_i_cnt[5:2] == 4'b1000)
|
||||
ssp_frame = 1'b1;
|
||||
else
|
||||
ssp_frame = 1'b0;
|
||||
|
@ -181,5 +159,6 @@ assign dbg = corr_i_cnt[3];
|
|||
|
||||
// Unused.
|
||||
assign pwr_lo = 1'b0;
|
||||
assign pwr_oe2 = 1'b0;
|
||||
|
||||
endmodule
|
||||
|
|
|
@ -100,7 +100,6 @@ typedef struct{
|
|||
|
||||
// For the 13.56 MHz tags
|
||||
#define CMD_ACQUIRE_RAW_ADC_SAMPLES_ISO_15693 0x0300
|
||||
#define CMD_ACQUIRE_RAW_ADC_SAMPLES_ISO_14443 0x0301
|
||||
#define CMD_READ_SRI512_TAG 0x0303
|
||||
#define CMD_READ_SRIX4K_TAG 0x0304
|
||||
#define CMD_ISO_14443B_COMMAND 0x0305
|
||||
|
@ -118,9 +117,8 @@ typedef struct{
|
|||
#define CMD_SIMULATE_HITAG 0x0371
|
||||
#define CMD_READER_HITAG 0x0372
|
||||
|
||||
#define CMD_SIMULATE_TAG_HF_LISTEN 0x0380
|
||||
#define CMD_SIMULATE_TAG_ISO_14443 0x0381
|
||||
#define CMD_SNOOP_ISO_14443 0x0382
|
||||
#define CMD_SIMULATE_TAG_ISO_14443B 0x0381
|
||||
#define CMD_SNOOP_ISO_14443B 0x0382
|
||||
#define CMD_SNOOP_ISO_14443a 0x0383
|
||||
#define CMD_SIMULATE_TAG_ISO_14443a 0x0384
|
||||
#define CMD_READER_ISO_14443a 0x0385
|
||||
|
|
Loading…
Reference in a new issue