diff --git a/.gitignore b/.gitignore index 8469c8449..30cc1020a 100644 --- a/.gitignore +++ b/.gitignore @@ -80,17 +80,7 @@ tools/mfd_aes_brute/mfd_aes_brute tools/mfd_aes_brute/mfd_multi_brute tools/mfd_aes_brute/brute_key -fpga/* -!fpga/tests -!fpga/fpga_lf.bit -!fpga/fpga_hf.bit -!fpga/*.v -!fpga/Makefile -!fpga/fpga.ucf -!fpga/xst_lf.scr -!fpga/xst_hf.scr -!fpga/go.bat -!fpga/sim.tcl +fpga/__build* # offcial dumps folder dumps/* diff --git a/armsrc/Makefile b/armsrc/Makefile index 5203b0292..c481a6f22 100644 --- a/armsrc/Makefile +++ b/armsrc/Makefile @@ -103,9 +103,6 @@ endif # Generic standalone Mode injection of source code include Standalone/Makefile.inc -#the FPGA bitstream files. Note: order matters! -FPGA_BITSTREAMS = fpga_lf.bit fpga_hf.bit fpga_felica.bit fpga_hf_15.bit - #the lz4 source files required for decompressing the fpga config at run time SRC_LZ4 = lz4.c #additional defines required to compile lz4 diff --git a/armsrc/fpgaloader.c b/armsrc/fpgaloader.c index 6f8dd7a0b..6715aa962 100644 --- a/armsrc/fpgaloader.c +++ b/armsrc/fpgaloader.c @@ -404,16 +404,22 @@ static int bitparse_find_section(int bitstream_version, char section_name, uint3 /* Four byte length field */ current_length += get_from_fpga_stream(bitstream_version, compressed_fpga_stream, output_buffer) << 24; current_length += get_from_fpga_stream(bitstream_version, compressed_fpga_stream, output_buffer) << 16; - numbytes += 2; - default: /* Fall through, two byte length field */ + current_length += get_from_fpga_stream(bitstream_version, compressed_fpga_stream, output_buffer) << 8; + current_length += get_from_fpga_stream(bitstream_version, compressed_fpga_stream, output_buffer) << 0; + numbytes += 4; + if (current_length > 300*1024) { + /* section e should never exceed about 300KB, if the length is too big limit it but still send the bitstream just in case */ + current_length = 300*1024; + } + break; + default: /* Two byte length field */ current_length += get_from_fpga_stream(bitstream_version, compressed_fpga_stream, output_buffer) << 8; current_length += get_from_fpga_stream(bitstream_version, compressed_fpga_stream, output_buffer) << 0; numbytes += 2; - } - - if (current_name != 'e' && current_length > 255) { - /* Maybe a parse error */ - break; + if (current_length > 64) { + /* if text field is too long, keep it but truncate it */ + current_length = 64; + } } if (current_name == section_name) { diff --git a/common_arm/Makefile.common b/common_arm/Makefile.common index 99f4d9ecd..18d931b46 100644 --- a/common_arm/Makefile.common +++ b/common_arm/Makefile.common @@ -44,7 +44,7 @@ OBJDIR = obj INCLUDE = -I../include -I../common_arm -I../common_fpga -I../common -I. # Also search prerequisites in the common directory (for usb.c), the fpga directory (for fpga.bit), and the lz4 directory -VPATH = . ../common_arm ../common ../common/crapto1 ../common/mbedtls ../common/lz4 ../fpga-$(PLATFORM_FPGA) ../armsrc/Standalone +VPATH = . ../common_arm ../common ../common/crapto1 ../common/mbedtls ../common/lz4 ../fpga ../armsrc/Standalone INCLUDES = ../include/proxmark3_arm.h ../include/at91sam7s512.h ../include/config_gpio.h ../include/pm3_cmd.h diff --git a/common_arm/Makefile.hal b/common_arm/Makefile.hal index a65514784..9679382ce 100644 --- a/common_arm/Makefile.hal +++ b/common_arm/Makefile.hal @@ -92,18 +92,26 @@ PLTNAME = Unknown Platform PLATFORM_FPGA = fpga-undefined ifeq ($(PLATFORM),PM3RDV4) + # FPGA bitstream files, the order matters! + FPGA_BITSTREAMS = fpga_pm3_lf.bit fpga_pm3_hf.bit fpga_pm3_felica.bit fpga_pm3_hf_15.bit PLATFORM_DEFS = -DWITH_SMARTCARD -DWITH_FLASH -DRDV4 PLTNAME = Proxmark3 RDV4 PLATFORM_FPGA = xc2s30 RDV4 = yes else ifeq ($(PLATFORM),PM3OTHER) $(warning PLATFORM=PM3OTHER is deprecated, please use PLATFORM=PM3GENERIC) + # FPGA bitstream files, the order matters! + FPGA_BITSTREAMS = fpga_pm3_lf.bit fpga_pm3_hf.bit fpga_pm3_felica.bit fpga_pm3_hf_15.bit PLTNAME = Proxmark3 generic target PLATFORM_FPGA = xc2s30 else ifeq ($(PLATFORM),PM3GENERIC) + # FPGA bitstream files, the order matters! + FPGA_BITSTREAMS = fpga_pm3_lf.bit fpga_pm3_hf.bit fpga_pm3_felica.bit fpga_pm3_hf_15.bit PLTNAME = Proxmark3 generic target PLATFORM_FPGA = xc2s30 else ifeq ($(PLATFORM),PM3ICOPYX) + # FPGA bitstream files, the order matters - only hf has a bitstream, the other 3 files are 0 bytes + FPGA_BITSTREAMS = fpga_icopyx_lf.bit fpga_icopyx_hf.bit fpga_icopyx_felica.bit fpga_icopyx_hf_15.bit PLATFORM_DEFS = -DWITH_FLASH -DICOPYX -DXC3 PLTNAME = iCopy-X with XC3S100E PLATFORM_FPGA = xc3s100e @@ -246,6 +254,7 @@ export PLATFORM_DEFS export PLATFORM_DEFS_INFO export PLATFORM_DEFS_INFO_STANDALONE export PLATFORM_CHANGED +export FPGA_BITSTREAMS $(info ===================================================================) $(info Version info: $(shell tools/mkversion.sh --short 2>/dev/null || ../tools/mkversion.sh --short 2>/dev/null)) diff --git a/fpga-xc2s30/Makefile b/fpga-xc2s30/Makefile deleted file mode 100644 index 2bf9273ba..000000000 --- a/fpga-xc2s30/Makefile +++ /dev/null @@ -1,60 +0,0 @@ -# -# FPGA Makefile -# -RMDIR = rm -rf -# rmdir only if dir is empty, tolerate failure -RMDIR_SOFT = -rmdir -# -all: fpga_lf.bit fpga_hf.bit fpga_felica.bit fpga_hf_15.bit -clean: - $(Q)$(RM) *.bgn *.drc *.ncd *.ngd *_par.xrpt *-placed.* *-placed_pad.* *_usage.xml xst_hf.srp xst_lf.srp xst_felica.srp xst_hf_15.srp - $(Q)$(RM) *.map *.ngc *.xrpt *.pcf *.rbt *.bld *.mrp *.ngm *.unroutes *_summary.xml netlist.lst - $(Q)$(RMDIR) *_auto_* xst - -#fpga_hf.ngc: fpga_hf.v fpga.ucf xst_hf.scr util.v hi_simulate.v hi_reader.v hi_iso14443a.v hi_sniffer.v hi_flite.v hi_get_trace.v -fpga_hf.ngc: fpga_hf.v fpga.ucf xst_hf.scr util.v hi_simulate.v hi_reader.v hi_iso14443a.v hi_sniffer.v hi_get_trace.v - $(Q)$(RM) $@ - $(info [-] XST $@) - $(Q)$(XILINX_TOOLS_PREFIX)xst -ifn xst_hf.scr - -fpga_felica.ngc: fpga_felica.v fpga.ucf xst_felica.scr util.v hi_simulate.v hi_reader.v hi_sniffer.v hi_flite.v hi_get_trace.v - $(Q)$(RM) $@ - $(info [-] XST $@) - $(Q)$(XILINX_TOOLS_PREFIX)xst -ifn xst_felica.scr - -fpga_hf_15.ngc: fpga_hf_15.v fpga.ucf xst_hf_15.scr util.v hi_simulate.v hi_reader_15.v hi_sniffer.v hi_get_trace.v - $(Q)$(RM) $@ - $(info [-] XST $@) - $(Q)$(XILINX_TOOLS_PREFIX)xst -ifn xst_hf_15.scr - -fpga_lf.ngc: fpga_lf.v fpga.ucf xst_lf.scr util.v clk_divider.v lo_edge_detect.v lo_read.v lo_passthru.v lp20khz_1MSa_iir_filter.v min_max_tracker.v lf_edge_detect.v - $(Q)$(RM) $@ - $(info [-] XST $@) - $(Q)$(XILINX_TOOLS_PREFIX)xst -ifn xst_lf.scr - -%.ngd: %.ngc - $(Q)$(RM) $@ - $(info [-] NGD $@) - $(Q)$(XILINX_TOOLS_PREFIX)ngdbuild -aul -p xc2s30-5-vq100 -nt timestamp -uc fpga.ucf $< $@ - -%.ncd: %.ngd - $(Q)$(RM) $@ - $(info [-] MAP $@) - $(Q)$(XILINX_TOOLS_PREFIX)map -p xc2s30-5-vq100 $< - -%-placed.ncd: %.ncd - $(Q)$(RM) $@ - $(info [-] PAR $@) - $(Q)$(XILINX_TOOLS_PREFIX)par $< $@ - -%.bit: %-placed.ncd - $(Q)$(RM) $@ $*.drc $*.rbt - $(info [=] BITGEN $@) - $(Q)$(XILINX_TOOLS_PREFIX)bitgen $< $@ - -.PHONY: all clean help -help: - @echo Possible targets: - @echo + all - Make fpga.bit, the FPGA bitstream - @echo + clean - Clean intermediate files, does not clean fpga.bit - diff --git a/fpga-xc2s30/fpga.ucf b/fpga-xc2s30/fpga.ucf deleted file mode 100644 index f20e2da02..000000000 --- a/fpga-xc2s30/fpga.ucf +++ /dev/null @@ -1,54 +0,0 @@ -# See the schematic for the pin assignment. - -NET "adc_d<0>" LOC = "P62" ; -NET "adc_d<1>" LOC = "P60" ; -NET "adc_d<2>" LOC = "P58" ; -NET "adc_d<3>" LOC = "P57" ; -NET "adc_d<4>" LOC = "P56" ; -NET "adc_d<5>" LOC = "P55" ; -NET "adc_d<6>" LOC = "P54" ; -NET "adc_d<7>" LOC = "P53" ; -#NET "cross_hi" LOC = "P88" ; -#NET "miso" LOC = "P40" ; -#PACE: Start of Constraints generated by PACE - -#PACE: Start of PACE I/O Pin Assignments -NET "adc_clk" LOC = "P46" ; -NET "adc_noe" LOC = "P47" ; -NET "ck_1356meg" LOC = "P91" ; -NET "ck_1356megb" LOC = "P93" ; -NET "cross_lo" LOC = "P87" ; -NET "dbg" LOC = "P22" ; -NET "mosi" LOC = "P43" ; -NET "ncs" LOC = "P44" ; -NET "pck0" LOC = "P36" ; -NET "pwr_hi" LOC = "P80" ; -NET "pwr_lo" LOC = "P81" ; -NET "pwr_oe1" LOC = "P82" ; -NET "pwr_oe2" LOC = "P83" ; -NET "pwr_oe3" LOC = "P84" ; -NET "pwr_oe4" LOC = "P86" ; -NET "spck" LOC = "P39" ; -NET "ssp_clk" LOC = "P71" ; -NET "ssp_din" LOC = "P32" ; -NET "ssp_dout" LOC = "P34" ; -NET "ssp_frame" LOC = "P31" ; - -#PACE: Start of PACE Area Constraints - -#PACE: Start of PACE Prohibit Constraints - -#PACE: End of Constraints generated by PACE - -# definition of Clock nets: -NET "ck_1356meg" TNM_NET = "clk_net_1356" ; -NET "ck_1356megb" TNM_NET = "clk_net_1356b" ; -NET "pck0" TNM_NET = "clk_net_pck0" ; -NET "spck" TNM_NET = "clk_net_spck" ; - -# Timing specs of clock nets: -TIMEGRP "clk_net_1356_all" = "clk_net_1356" "clk_net_1356b" ; -TIMESPEC "TS_1356MHz" = PERIOD "clk_net_1356_all" 74 ns HIGH 37 ns ; -TIMESPEC "TS_24MHz" = PERIOD "clk_net_pck0" 42 ns HIGH 21 ns ; -TIMESPEC "TS_4MHz" = PERIOD "clk_net_spck" 250 ns HIGH 125 ns ; - diff --git a/fpga-xc2s30/fpga_felica.bit b/fpga-xc2s30/fpga_felica.bit deleted file mode 100644 index 30ea16e33..000000000 Binary files a/fpga-xc2s30/fpga_felica.bit and /dev/null differ diff --git a/fpga-xc2s30/fpga_felica.v b/fpga-xc2s30/fpga_felica.v deleted file mode 100644 index 6fb53927c..000000000 --- a/fpga-xc2s30/fpga_felica.v +++ /dev/null @@ -1,240 +0,0 @@ -//----------------------------------------------------------------------------- -// Copyright (C) Proxmark3 contributors. See AUTHORS.md for details. -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// See LICENSE.txt for the text of the license. -//----------------------------------------------------------------------------- -// -// The FPGA is responsible for interfacing between the A/D, the coil drivers, -// and the ARM. In the low-frequency modes it passes the data straight -// through, so that the ARM gets raw A/D samples over the SSP. In the high- -// frequency modes, the FPGA might perform some demodulation first, to -// reduce the amount of data that we must send to the ARM. -// -// I am not really an FPGA/ASIC designer, so I am sure that a lot of this -// could be improved. -// -// Jonathan Westhues, March 2006 -// -// Added ISO14443-A support -// - - -// Defining commands, modes and options. This must be aligned to the definitions in fpgaloader.h -// Note: the definitions here are without shifts - -// Commands: -`define FPGA_CMD_SET_CONFREG 1 -`define FPGA_CMD_TRACE_ENABLE 2 - -// Major modes: -`define FPGA_MAJOR_MODE_HF_READER 0 -`define FPGA_MAJOR_MODE_HF_SIMULATOR 1 -`define FPGA_MAJOR_MODE_HF_ISO14443A 2 -`define FPGA_MAJOR_MODE_HF_SNIFF 3 -`define FPGA_MAJOR_MODE_HF_ISO18092 4 -`define FPGA_MAJOR_MODE_HF_GET_TRACE 5 -`define FPGA_MAJOR_MODE_OFF 7 - -// Options for the generic HF reader -`define FPGA_HF_READER_MODE_RECEIVE_IQ 0 -`define FPGA_HF_READER_MODE_RECEIVE_AMPLITUDE 1 -`define FPGA_HF_READER_MODE_RECEIVE_PHASE 2 -`define FPGA_HF_READER_MODE_SEND_FULL_MOD 3 -`define FPGA_HF_READER_MODE_SEND_SHALLOW_MOD 4 -`define FPGA_HF_READER_MODE_SNIFF_IQ 5 -`define FPGA_HF_READER_MODE_SNIFF_AMPLITUDE 6 -`define FPGA_HF_READER_MODE_SNIFF_PHASE 7 -`define FPGA_HF_READER_MODE_SEND_JAM 8 - -`define FPGA_HF_READER_SUBCARRIER_848_KHZ 0 -`define FPGA_HF_READER_SUBCARRIER_424_KHZ 1 -`define FPGA_HF_READER_SUBCARRIER_212_KHZ 2 - -// Options for the HF simulated tag, how to modulate -`define FPGA_HF_SIMULATOR_NO_MODULATION 0 -`define FPGA_HF_SIMULATOR_MODULATE_BPSK 1 -`define FPGA_HF_SIMULATOR_MODULATE_212K 2 -`define FPGA_HF_SIMULATOR_MODULATE_424K 4 -`define FPGA_HF_SIMULATOR_MODULATE_424K_8BIT 5 - -// Options for ISO14443A -`define FPGA_HF_ISO14443A_SNIFFER 0 -`define FPGA_HF_ISO14443A_TAGSIM_LISTEN 1 -`define FPGA_HF_ISO14443A_TAGSIM_MOD 2 -`define FPGA_HF_ISO14443A_READER_LISTEN 3 -`define FPGA_HF_ISO14443A_READER_MOD 4 - -//options for ISO18092 / Felica -`define FPGA_HF_ISO18092_FLAG_NOMOD 1 // 0001 disable modulation module -`define FPGA_HF_ISO18092_FLAG_424K 2 // 0010 should enable 414k mode (untested). No autodetect -`define FPGA_HF_ISO18092_FLAG_READER 4 // 0100 enables antenna power, to act as a reader instead of tag - -`include "hi_reader.v" -`include "hi_simulate.v" -//`include "hi_iso14443a.v" -`include "hi_sniffer.v" -`include "util.v" -`include "hi_flite.v" -`include "hi_get_trace.v" - -module fpga_felica( - input spck, output miso, input mosi, input ncs, - input pck0, input ck_1356meg, input ck_1356megb, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, output adc_noe, - output ssp_frame, output ssp_din, input ssp_dout, output ssp_clk, - input cross_hi, input cross_lo, - output dbg -); - -//----------------------------------------------------------------------------- -// The SPI receiver. This sets up the configuration word, which the rest of -// the logic looks at to determine how to connect the A/D and the coil -// drivers (i.e., which section gets it). Also assign some symbolic names -// to the configuration bits, for use below. -//----------------------------------------------------------------------------- - -/* - Attempt to write up how its hooked up. Iceman 2020. - - Communication between ARM / FPGA is done inside armsrc/fpgaloader.c see: function FpgaSendCommand() - Send 16 bit command / data pair to FPGA - The bit format is: C3 C2 C1 C0 D11 D10 D9 D8 D7 D6 D5 D4 D3 D2 D1 D0 - where - C is 4bit command - D is 12bit data - - shift_reg receive this 16bit frame - - ------+--------- frame layout -------------------- -bit | 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 ------+------------------------------------------- -cmd | x x x x -major| x x x -opt | x x x -divi | x x x x x x x x -thres| x x x x x x x x ------+------------------------------------------- -*/ - -reg [15:0] shift_reg; -reg [8:0] conf_word; -reg trace_enable; - -// We switch modes between transmitting to the 13.56 MHz tag and receiving -// from it, which means that we must make sure that we can do so without -// glitching, or else we will glitch the transmitted carrier. -always @(posedge ncs) -begin - case(shift_reg[15:12]) - `FPGA_CMD_SET_CONFREG: conf_word <= shift_reg[8:0]; - `FPGA_CMD_TRACE_ENABLE: trace_enable <= shift_reg[0]; - endcase -end - -always @(posedge spck) -begin - if(~ncs) - begin - shift_reg[15:1] <= shift_reg[14:0]; - shift_reg[0] <= mosi; - end -end - -// select module (outputs) based on major mode -wire [2:0] major_mode = conf_word[8:6]; - -// configuring the HF reader -wire [1:0] subcarrier_frequency = conf_word[5:4]; -wire [3:0] minor_mode = conf_word[3:0]; - -//----------------------------------------------------------------------------- -// And then we instantiate the modules corresponding to each of the FPGA's -// major modes, and use muxes to connect the outputs of the active mode to -// the output pins. -//----------------------------------------------------------------------------- - -// 000 - HF reader -hi_reader hr( - ck_1356megb, - hr_pwr_lo, hr_pwr_hi, hr_pwr_oe1, hr_pwr_oe2, hr_pwr_oe3, hr_pwr_oe4, - adc_d, hr_adc_clk, - hr_ssp_frame, hr_ssp_din, ssp_dout, hr_ssp_clk, - hr_dbg, - subcarrier_frequency, minor_mode -); - -// 001 - HF simulated tag -hi_simulate hs( - ck_1356meg, - hs_pwr_lo, hs_pwr_hi, hs_pwr_oe1, hs_pwr_oe2, hs_pwr_oe3, hs_pwr_oe4, - adc_d, hs_adc_clk, - hs_ssp_frame, hs_ssp_din, ssp_dout, hs_ssp_clk, - hs_dbg, - minor_mode -); - -// 011 - HF sniff -hi_sniffer he( - ck_1356megb, - he_pwr_lo, he_pwr_hi, he_pwr_oe1, he_pwr_oe2, he_pwr_oe3, he_pwr_oe4, - adc_d, he_adc_clk, - he_ssp_frame, he_ssp_din, he_ssp_clk -); - -// 100 - HF ISO18092 FeliCa -hi_flite hfl( - ck_1356megb, - hfl_pwr_lo, hfl_pwr_hi, hfl_pwr_oe1, hfl_pwr_oe2, hfl_pwr_oe3, hfl_pwr_oe4, - adc_d, hfl_adc_clk, - hfl_ssp_frame, hfl_ssp_din, ssp_dout, hfl_ssp_clk, - hfl_dbg, - minor_mode -); - -// 101 - HF get trace -hi_get_trace gt( - ck_1356megb, - adc_d, trace_enable, major_mode, - gt_ssp_frame, gt_ssp_din, gt_ssp_clk -); - -// Major modes: -// 000 -- HF reader; subcarrier frequency and modulation depth selectable -// 001 -- HF simulated tag -// 010 -- HF ISO14443-A - removed for space... -// 011 -- HF sniff -// 100 -- HF ISO18092 FeliCa -// 101 -- HF get trace -// 110 -- unused -// 111 -- FPGA_MAJOR_MODE_OFF - -// 000 001 010 011 100 101 110 111 -mux8 mux_ssp_clk (major_mode, ssp_clk, hr_ssp_clk, hs_ssp_clk, 1'b0, he_ssp_clk, hfl_ssp_clk, gt_ssp_clk, 1'b0, 1'b0); -mux8 mux_ssp_din (major_mode, ssp_din, hr_ssp_din, hs_ssp_din, 1'b0, he_ssp_din, hfl_ssp_din, gt_ssp_din, 1'b0, 1'b0); -mux8 mux_ssp_frame (major_mode, ssp_frame, hr_ssp_frame, hs_ssp_frame, 1'b0, he_ssp_frame, hfl_ssp_frame, gt_ssp_frame, 1'b0, 1'b0); -mux8 mux_pwr_oe1 (major_mode, pwr_oe1, hr_pwr_oe1, hs_pwr_oe1, 1'b0, he_pwr_oe1, hfl_pwr_oe1, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe2 (major_mode, pwr_oe2, hr_pwr_oe2, hs_pwr_oe2, 1'b0, he_pwr_oe2, hfl_pwr_oe2, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe3 (major_mode, pwr_oe3, hr_pwr_oe3, hs_pwr_oe3, 1'b0, he_pwr_oe3, hfl_pwr_oe3, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe4 (major_mode, pwr_oe4, hr_pwr_oe4, hs_pwr_oe4, 1'b0, he_pwr_oe4, hfl_pwr_oe4, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_lo (major_mode, pwr_lo, hr_pwr_lo, hs_pwr_lo, 1'b0, he_pwr_lo, hfl_pwr_lo, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_hi (major_mode, pwr_hi, hr_pwr_hi, hs_pwr_hi, 1'b0, he_pwr_hi, hfl_pwr_hi, 1'b0, 1'b0, 1'b0); -mux8 mux_adc_clk (major_mode, adc_clk, hr_adc_clk, hs_adc_clk, 1'b0, he_adc_clk, hfl_adc_clk, 1'b0, 1'b0, 1'b0); -mux8 mux_dbg (major_mode, dbg, hr_dbg, hs_dbg, 1'b0, he_dbg, hfl_dbg, 1'b0, 1'b0, 1'b0); - -// In all modes, let the ADC's outputs be enabled. -assign adc_noe = 1'b0; - -endmodule diff --git a/fpga-xc2s30/fpga_hf.bit b/fpga-xc2s30/fpga_hf.bit deleted file mode 100644 index 72f3d619e..000000000 Binary files a/fpga-xc2s30/fpga_hf.bit and /dev/null differ diff --git a/fpga-xc2s30/fpga_hf.v b/fpga-xc2s30/fpga_hf.v deleted file mode 100644 index 8ee85e26b..000000000 --- a/fpga-xc2s30/fpga_hf.v +++ /dev/null @@ -1,255 +0,0 @@ -//----------------------------------------------------------------------------- -// Copyright (C) Proxmark3 contributors. See AUTHORS.md for details. -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// See LICENSE.txt for the text of the license. -//----------------------------------------------------------------------------- -// -// The FPGA is responsible for interfacing between the A/D, the coil drivers, -// and the ARM. In the low-frequency modes it passes the data straight -// through, so that the ARM gets raw A/D samples over the SSP. In the high- -// frequency modes, the FPGA might perform some demodulation first, to -// reduce the amount of data that we must send to the ARM. -// -// I am not really an FPGA/ASIC designer, so I am sure that a lot of this -// could be improved. -// -// Jonathan Westhues, March 2006 -//----------------------------------------------------------------------------- -// Added ISO14443-A support -// - - -// Defining commands, modes and options. This must be aligned to the definitions in fpgaloader.h -// Note: the definitions here are without shifts - -// Commands: -`define FPGA_CMD_SET_CONFREG 1 -`define FPGA_CMD_TRACE_ENABLE 2 - -// Major modes: -`define FPGA_MAJOR_MODE_HF_READER 0 -`define FPGA_MAJOR_MODE_HF_SIMULATOR 1 -`define FPGA_MAJOR_MODE_HF_ISO14443A 2 -`define FPGA_MAJOR_MODE_HF_SNIFF 3 -`define FPGA_MAJOR_MODE_HF_ISO18092 4 -`define FPGA_MAJOR_MODE_HF_GET_TRACE 5 -`define FPGA_MAJOR_MODE_OFF 7 - -// Options for the generic HF reader -`define FPGA_HF_READER_MODE_RECEIVE_IQ 0 -`define FPGA_HF_READER_MODE_RECEIVE_AMPLITUDE 1 -`define FPGA_HF_READER_MODE_RECEIVE_PHASE 2 -`define FPGA_HF_READER_MODE_SEND_FULL_MOD 3 -`define FPGA_HF_READER_MODE_SEND_SHALLOW_MOD 4 -`define FPGA_HF_READER_MODE_SNIFF_IQ 5 -`define FPGA_HF_READER_MODE_SNIFF_AMPLITUDE 6 -`define FPGA_HF_READER_MODE_SNIFF_PHASE 7 -`define FPGA_HF_READER_MODE_SEND_JAM 8 - -`define FPGA_HF_READER_SUBCARRIER_848_KHZ 0 -`define FPGA_HF_READER_SUBCARRIER_424_KHZ 1 -`define FPGA_HF_READER_SUBCARRIER_212_KHZ 2 - -// Options for the HF simulated tag, how to modulate -`define FPGA_HF_SIMULATOR_NO_MODULATION 0 -`define FPGA_HF_SIMULATOR_MODULATE_BPSK 1 -`define FPGA_HF_SIMULATOR_MODULATE_212K 2 -`define FPGA_HF_SIMULATOR_MODULATE_424K 4 -`define FPGA_HF_SIMULATOR_MODULATE_424K_8BIT 5 - -// Options for ISO14443A -`define FPGA_HF_ISO14443A_SNIFFER 0 -`define FPGA_HF_ISO14443A_TAGSIM_LISTEN 1 -`define FPGA_HF_ISO14443A_TAGSIM_MOD 2 -`define FPGA_HF_ISO14443A_READER_LISTEN 3 -`define FPGA_HF_ISO14443A_READER_MOD 4 - -//options for ISO18092 / Felica -`define FPGA_HF_ISO18092_FLAG_NOMOD 1 // 0001 disable modulation module -`define FPGA_HF_ISO18092_FLAG_424K 2 // 0010 should enable 414k mode (untested). No autodetect -`define FPGA_HF_ISO18092_FLAG_READER 4 // 0100 enables antenna power, to act as a reader instead of tag - -`include "hi_reader.v" -`include "hi_simulate.v" -`include "hi_iso14443a.v" -`include "hi_sniffer.v" -`include "util.v" -// `include "hi_flite.v" -`include "hi_get_trace.v" - -module fpga_hf( - input spck, output miso, input mosi, input ncs, - input pck0, input ck_1356meg, input ck_1356megb, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, output adc_noe, - output ssp_frame, output ssp_din, input ssp_dout, output ssp_clk, - input cross_hi, input cross_lo, - output dbg -); - -//----------------------------------------------------------------------------- -// The SPI receiver. This sets up the configuration word, which the rest of -// the logic looks at to determine how to connect the A/D and the coil -// drivers (i.e., which section gets it). Also assign some symbolic names -// to the configuration bits, for use below. -//----------------------------------------------------------------------------- - -/* - Attempt to write up how its hooked up. - / Iceman, 2020 - - Communication between ARM / FPGA is done inside armsrc/fpgaloader.c see: function FpgaSendCommand() - Send 16 bit command / data pair to FPGA - The bit format is: C3 C2 C1 C0 D11 D10 D9 D8 D7 D6 D5 D4 D3 D2 D1 D0 - where - C is 4bit command - D is 12bit data - - shift_reg receive this 16bit frame - - ------+--------- frame layout -------------------- -bit | 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 ------+------------------------------------------- -cmd | x x x x -major| x x x -opt | x x x x -sub | x x -divi | x x x x x x x x -thres| x x x x x x x x ------+------------------------------------------- -*/ - -reg [15:0] shift_reg; -reg [8:0] conf_word; -reg trace_enable; - -// We switch modes between transmitting to the 13.56 MHz tag and receiving -// from it, which means that we must make sure that we can do so without -// glitching, or else we will glitch the transmitted carrier. -always @(posedge ncs) -begin - case(shift_reg[15:12]) - `FPGA_CMD_SET_CONFREG: conf_word <= shift_reg[8:0]; - `FPGA_CMD_TRACE_ENABLE: trace_enable <= shift_reg[0]; - endcase -end - -always @(posedge spck) -begin - if(~ncs) - begin - shift_reg[15:1] <= shift_reg[14:0]; - shift_reg[0] <= mosi; - end -end - -// select module (outputs) based on major mode -wire [2:0] major_mode = conf_word[8:6]; - -// configuring the HF reader -wire [1:0] subcarrier_frequency = conf_word[5:4]; -wire [3:0] minor_mode = conf_word[3:0]; - -//----------------------------------------------------------------------------- -// And then we instantiate the modules corresponding to each of the FPGA's -// major modes, and use muxes to connect the outputs of the active mode to -// the output pins. -//----------------------------------------------------------------------------- - -// 000 - HF reader -hi_reader hr( - ck_1356megb, - hr_pwr_lo, hr_pwr_hi, hr_pwr_oe1, hr_pwr_oe2, hr_pwr_oe3, hr_pwr_oe4, - adc_d, hr_adc_clk, - hr_ssp_frame, hr_ssp_din, ssp_dout, hr_ssp_clk, - hr_dbg, - subcarrier_frequency, minor_mode -); - -// 001 - HF simulated tag -hi_simulate hs( - ck_1356meg, - hs_pwr_lo, hs_pwr_hi, hs_pwr_oe1, hs_pwr_oe2, hs_pwr_oe3, hs_pwr_oe4, - adc_d, hs_adc_clk, - hs_ssp_frame, hs_ssp_din, ssp_dout, hs_ssp_clk, - hs_dbg, - minor_mode -); - -// 010 - HF ISO14443-A -hi_iso14443a hisn( - ck_1356meg, - hisn_pwr_lo, hisn_pwr_hi, hisn_pwr_oe1, hisn_pwr_oe2, hisn_pwr_oe3, hisn_pwr_oe4, - adc_d, hisn_adc_clk, - hisn_ssp_frame, hisn_ssp_din, ssp_dout, hisn_ssp_clk, - hisn_dbg, - minor_mode -); - -// 011 - HF sniff -hi_sniffer he( - ck_1356megb, - he_pwr_lo, he_pwr_hi, he_pwr_oe1, he_pwr_oe2, he_pwr_oe3, he_pwr_oe4, - adc_d, he_adc_clk, - he_ssp_frame, he_ssp_din, he_ssp_clk -); - -// 100 - HF ISO18092 FeliCa -/* -hi_flite hfl( - ck_1356megb, - hfl_pwr_lo, hfl_pwr_hi, hfl_pwr_oe1, hfl_pwr_oe2, hfl_pwr_oe3, hfl_pwr_oe4, - adc_d, hfl_adc_clk, - hfl_ssp_frame, hfl_ssp_din, ssp_dout, hfl_ssp_clk, - hfl_dbg, - minor_mode -); -*/ - -// 101 - HF get trace -hi_get_trace gt( - ck_1356megb, - adc_d, trace_enable, major_mode, - gt_ssp_frame, gt_ssp_din, gt_ssp_clk -); - -// Major modes: -// 000 -- HF reader; subcarrier frequency and modulation depth selectable -// 001 -- HF simulated tag -// 010 -- HF ISO14443-A -// 011 -- HF sniff -// 100 -- HF ISO18092 FeliCa -// 101 -- HF get trace -// 110 -- unused -// 111 -- FPGA_MAJOR_MODE_OFF - -// 000 001 010 011 100 101 110 111 - -mux8 mux_ssp_clk (major_mode, ssp_clk, hr_ssp_clk, hs_ssp_clk, hisn_ssp_clk, he_ssp_clk, hfl_ssp_clk, gt_ssp_clk, 1'b0, 1'b0); -mux8 mux_ssp_din (major_mode, ssp_din, hr_ssp_din, hs_ssp_din, hisn_ssp_din, he_ssp_din, hfl_ssp_din, gt_ssp_din, 1'b0, 1'b0); -mux8 mux_ssp_frame (major_mode, ssp_frame, hr_ssp_frame, hs_ssp_frame, hisn_ssp_frame, he_ssp_frame, hfl_ssp_frame, gt_ssp_frame, 1'b0, 1'b0); -mux8 mux_pwr_oe1 (major_mode, pwr_oe1, hr_pwr_oe1, hs_pwr_oe1, hisn_pwr_oe1, he_pwr_oe1, hfl_pwr_oe1, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe2 (major_mode, pwr_oe2, hr_pwr_oe2, hs_pwr_oe2, hisn_pwr_oe2, he_pwr_oe2, hfl_pwr_oe2, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe3 (major_mode, pwr_oe3, hr_pwr_oe3, hs_pwr_oe3, hisn_pwr_oe3, he_pwr_oe3, hfl_pwr_oe3, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe4 (major_mode, pwr_oe4, hr_pwr_oe4, hs_pwr_oe4, hisn_pwr_oe4, he_pwr_oe4, hfl_pwr_oe4, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_lo (major_mode, pwr_lo, hr_pwr_lo, hs_pwr_lo, hisn_pwr_lo, he_pwr_lo, hfl_pwr_lo, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_hi (major_mode, pwr_hi, hr_pwr_hi, hs_pwr_hi, hisn_pwr_hi, he_pwr_hi, hfl_pwr_hi, 1'b0, 1'b0, 1'b0); -mux8 mux_adc_clk (major_mode, adc_clk, hr_adc_clk, hs_adc_clk, hisn_adc_clk, he_adc_clk, hfl_adc_clk, 1'b0, 1'b0, 1'b0); -mux8 mux_dbg (major_mode, dbg, hr_dbg, hs_dbg, hisn_dbg, he_dbg, hfl_dbg, 1'b0, 1'b0, 1'b0); - -// In all modes, let the ADC's outputs be enabled. -assign adc_noe = 1'b0; - -endmodule diff --git a/fpga-xc2s30/fpga_hf_15.bit b/fpga-xc2s30/fpga_hf_15.bit deleted file mode 100644 index 5d99a0032..000000000 Binary files a/fpga-xc2s30/fpga_hf_15.bit and /dev/null differ diff --git a/fpga-xc2s30/fpga_hf_15.v b/fpga-xc2s30/fpga_hf_15.v deleted file mode 100644 index b107ec180..000000000 --- a/fpga-xc2s30/fpga_hf_15.v +++ /dev/null @@ -1,233 +0,0 @@ -//----------------------------------------------------------------------------- -// Copyright (C) Proxmark3 contributors. See AUTHORS.md for details. -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// See LICENSE.txt for the text of the license. -//----------------------------------------------------------------------------- -// -// The FPGA is responsible for interfacing between the A/D, the coil drivers, -// and the ARM. In the low-frequency modes it passes the data straight -// through, so that the ARM gets raw A/D samples over the SSP. In the high- -// frequency modes, the FPGA might perform some demodulation first, to -// reduce the amount of data that we must send to the ARM. -//----------------------------------------------------------------------------- - - -// Defining commands, modes and options. This must be aligned to the definitions in fpgaloader.h -// Note: the definitions here are without shifts - -// Commands: -`define FPGA_CMD_SET_CONFREG 1 -`define FPGA_CMD_TRACE_ENABLE 2 - -// Major modes: -`define FPGA_MAJOR_MODE_HF_READER 0 -`define FPGA_MAJOR_MODE_HF_SIMULATOR 1 -`define FPGA_MAJOR_MODE_HF_ISO14443A 2 -`define FPGA_MAJOR_MODE_HF_SNIFF 3 -`define FPGA_MAJOR_MODE_HF_ISO18092 4 -`define FPGA_MAJOR_MODE_HF_GET_TRACE 5 -`define FPGA_MAJOR_MODE_HF_FSK_READER 6 -`define FPGA_MAJOR_MODE_OFF 7 - -// Options for the generic HF reader -`define FPGA_HF_READER_MODE_RECEIVE_IQ 0 -`define FPGA_HF_READER_MODE_RECEIVE_AMPLITUDE 1 -`define FPGA_HF_READER_MODE_RECEIVE_PHASE 2 -`define FPGA_HF_READER_MODE_SEND_FULL_MOD 3 -`define FPGA_HF_READER_MODE_SEND_SHALLOW_MOD 4 -`define FPGA_HF_READER_MODE_SNIFF_IQ 5 -`define FPGA_HF_READER_MODE_SNIFF_AMPLITUDE 6 -`define FPGA_HF_READER_MODE_SNIFF_PHASE 7 -`define FPGA_HF_READER_MODE_SEND_JAM 8 - -`define FPGA_HF_READER_SUBCARRIER_848_KHZ 0 -`define FPGA_HF_READER_SUBCARRIER_424_KHZ 1 -`define FPGA_HF_READER_SUBCARRIER_212_KHZ 2 -`define FPGA_HF_READER_2SUBCARRIERS_424_484_KHZ 3 - -`define FPGA_HF_FSK_READER_OUTPUT_1695_KHZ 0 -`define FPGA_HF_FSK_READER_OUTPUT_848_KHZ 1 -`define FPGA_HF_FSK_READER_OUTPUT_424_KHZ 2 -`define FPGA_HF_FSK_READER_OUTPUT_212_KHZ 3 - -`define FPGA_HF_FSK_READER_NOPOWER 0 -`define FPGA_HF_FSK_READER_WITHPOWER 1 - -// Options for the HF simulated tag, how to modulate -`define FPGA_HF_SIMULATOR_NO_MODULATION 0 -`define FPGA_HF_SIMULATOR_MODULATE_BPSK 1 -`define FPGA_HF_SIMULATOR_MODULATE_212K 2 -`define FPGA_HF_SIMULATOR_MODULATE_424K 4 -`define FPGA_HF_SIMULATOR_MODULATE_424K_8BIT 5 - -// Options for ISO14443A -`define FPGA_HF_ISO14443A_SNIFFER 0 -`define FPGA_HF_ISO14443A_TAGSIM_LISTEN 1 -`define FPGA_HF_ISO14443A_TAGSIM_MOD 2 -`define FPGA_HF_ISO14443A_READER_LISTEN 3 -`define FPGA_HF_ISO14443A_READER_MOD 4 - -//options for ISO18092 / Felica -`define FPGA_HF_ISO18092_FLAG_NOMOD 1 // 0001 disable modulation module -`define FPGA_HF_ISO18092_FLAG_424K 2 // 0010 should enable 414k mode (untested). No autodetect -`define FPGA_HF_ISO18092_FLAG_READER 4 // 0100 enables antenna power, to act as a reader instead of tag - -`include "hi_reader_15.v" -`include "hi_simulate.v" -`include "hi_sniffer.v" -`include "util.v" -`include "hi_get_trace.v" - -module fpga_hf_15( - input spck, output miso, input mosi, input ncs, - input pck0, input ck_1356meg, input ck_1356megb, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, output adc_noe, - output ssp_frame, output ssp_din, input ssp_dout, output ssp_clk, - input cross_hi, input cross_lo, - output dbg -); - -//----------------------------------------------------------------------------- -// The SPI receiver. This sets up the configuration word, which the rest of -// the logic looks at to determine how to connect the A/D and the coil -// drivers (i.e., which section gets it). Also assign some symbolic names -// to the configuration bits, for use below. -//----------------------------------------------------------------------------- - -/* - Attempt to write up how its hooked up. - / Iceman, 2020 - - Communication between ARM / FPGA is done inside armsrc/fpgaloader.c see: function FpgaSendCommand() - Send 16 bit command / data pair to FPGA - The bit format is: C3 C2 C1 C0 D11 D10 D9 D8 D7 D6 D5 D4 D3 D2 D1 D0 - where - C is 4bit command - D is 12bit data - - shift_reg receive this 16bit frame - - ------+--------- frame layout -------------------- -bit | 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 ------+------------------------------------------- -cmd | x x x x -major| x x x -opt | x x x x -sub | x x -divi | x x x x x x x x -thres| x x x x x x x x ------+------------------------------------------- -*/ - -reg [15:0] shift_reg; -reg [8:0] conf_word; -reg trace_enable; - -// We switch modes between transmitting to the 13.56 MHz tag and receiving -// from it, which means that we must make sure that we can do so without -// glitching, or else we will glitch the transmitted carrier. -always @(posedge ncs) -begin - case(shift_reg[15:12]) - `FPGA_CMD_SET_CONFREG: conf_word <= shift_reg[8:0]; - `FPGA_CMD_TRACE_ENABLE: trace_enable <= shift_reg[0]; - endcase -end - -always @(posedge spck) -begin - if(~ncs) - begin - shift_reg[15:1] <= shift_reg[14:0]; - shift_reg[0] <= mosi; - end -end - -// select module (outputs) based on major mode -wire [2:0] major_mode = conf_word[8:6]; - -// configuring the HF reader -wire [1:0] subcarrier_frequency = conf_word[5:4]; -wire [3:0] minor_mode = conf_word[3:0]; - -//----------------------------------------------------------------------------- -// And then we instantiate the modules corresponding to each of the FPGA's -// major modes, and use muxes to connect the outputs of the active mode to -// the output pins. -//----------------------------------------------------------------------------- - -// 000 - HF 15 reader -hi_15_reader hr( - ck_1356megb, - hr_pwr_lo, hr_pwr_hi, hr_pwr_oe1, hr_pwr_oe2, hr_pwr_oe3, hr_pwr_oe4, - adc_d, hr_adc_clk, - hr_ssp_frame, hr_ssp_din, ssp_dout, hr_ssp_clk, - hr_dbg, - subcarrier_frequency, minor_mode -); - -// 001 - HF simulated tag -hi_simulate hs( - ck_1356meg, - hs_pwr_lo, hs_pwr_hi, hs_pwr_oe1, hs_pwr_oe2, hs_pwr_oe3, hs_pwr_oe4, - adc_d, hs_adc_clk, - hs_ssp_frame, hs_ssp_din, ssp_dout, hs_ssp_clk, - hs_dbg, - minor_mode -); - -// 011 - HF sniff -hi_sniffer he( - ck_1356megb, - he_pwr_lo, he_pwr_hi, he_pwr_oe1, he_pwr_oe2, he_pwr_oe3, he_pwr_oe4, - adc_d, he_adc_clk, - he_ssp_frame, he_ssp_din, he_ssp_clk -); - -// 101 - HF get trace -hi_get_trace gt( - ck_1356megb, - adc_d, trace_enable, major_mode, - gt_ssp_frame, gt_ssp_din, gt_ssp_clk -); - -// Major modes: -// 000 -- HF 15 reader; subcarrier frequency and modulation depth selectable -// 001 -- HF simulated tag -// 010 -- -// 011 -- HF sniff -// 100 -- -// 101 -- HF get trace -// 110 -- unused -// 111 -- FPGA_MAJOR_MODE_OFF - -// 000 001 010 011 100 101 110 111 -mux8 mux_ssp_clk (major_mode, ssp_clk, hr_ssp_clk, hs_ssp_clk, 1'b0, he_ssp_clk, 1'b0, gt_ssp_clk, 1'b0, 1'b0); -mux8 mux_ssp_din (major_mode, ssp_din, hr_ssp_din, hs_ssp_din, 1'b0, he_ssp_din, 1'b0, gt_ssp_din, 1'b0, 1'b0); -mux8 mux_ssp_frame (major_mode, ssp_frame, hr_ssp_frame, hs_ssp_frame, 1'b0, he_ssp_frame, 1'b0, gt_ssp_frame, 1'b0, 1'b0); -mux8 mux_pwr_oe1 (major_mode, pwr_oe1, hr_pwr_oe1, hs_pwr_oe1, 1'b0, he_pwr_oe1, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe2 (major_mode, pwr_oe2, hr_pwr_oe2, hs_pwr_oe2, 1'b0, he_pwr_oe2, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe3 (major_mode, pwr_oe3, hr_pwr_oe3, hs_pwr_oe3, 1'b0, he_pwr_oe3, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe4 (major_mode, pwr_oe4, hr_pwr_oe4, hs_pwr_oe4, 1'b0, he_pwr_oe4, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_lo (major_mode, pwr_lo, hr_pwr_lo, hs_pwr_lo, 1'b0, he_pwr_lo, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_hi (major_mode, pwr_hi, hr_pwr_hi, hs_pwr_hi, 1'b0, he_pwr_hi, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_adc_clk (major_mode, adc_clk, hr_adc_clk, hs_adc_clk, 1'b0, he_adc_clk, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_dbg (major_mode, dbg, hr_dbg, hs_dbg, 1'b0, he_dbg, 1'b0, 1'b0, 1'b0, 1'b0); - -// In all modes, let the ADC's outputs be enabled. -assign adc_noe = 1'b0; - -endmodule diff --git a/fpga-xc2s30/fpga_lf.bit b/fpga-xc2s30/fpga_lf.bit deleted file mode 100644 index f5e5ce630..000000000 Binary files a/fpga-xc2s30/fpga_lf.bit and /dev/null differ diff --git a/fpga-xc2s30/fpga_lf.v b/fpga-xc2s30/fpga_lf.v deleted file mode 100644 index bb9116f10..000000000 --- a/fpga-xc2s30/fpga_lf.v +++ /dev/null @@ -1,245 +0,0 @@ -//----------------------------------------------------------------------------- -// Copyright (C) Proxmark3 contributors. See AUTHORS.md for details. -// -// This program is free software: you can redistribute it and/or modify -// it under the terms of the GNU General Public License as published by -// the Free Software Foundation, either version 3 of the License, or -// (at your option) any later version. -// -// This program is distributed in the hope that it will be useful, -// but WITHOUT ANY WARRANTY; without even the implied warranty of -// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the -// GNU General Public License for more details. -// -// See LICENSE.txt for the text of the license. -//----------------------------------------------------------------------------- -// - - -// Defining commands, modes and options. This must be aligned to the definitions in fpgaloader.h -// Note: the definitions here are without shifts - -// Commands: -`define FPGA_CMD_SET_CONFREG 1 -`define FPGA_CMD_SET_DIVISOR 2 -`define FPGA_CMD_SET_EDGE_DETECT_THRESHOLD 3 - -// Major modes: -`define FPGA_MAJOR_MODE_LF_READER 0 -`define FPGA_MAJOR_MODE_LF_EDGE_DETECT 1 -`define FPGA_MAJOR_MODE_LF_PASSTHRU 2 -`define FPGA_MAJOR_MODE_LF_ADC 3 - -// Options for LF_READER -`define FPGA_LF_ADC_READER_FIELD 1 - -// Options for LF_EDGE_DETECT -`define FPGA_LF_EDGE_DETECT_READER_FIELD 1 -`define FPGA_LF_EDGE_DETECT_TOGGLE_MODE 2 - -`include "lo_read.v" -`include "lo_passthru.v" -`include "lo_edge_detect.v" -`include "lo_adc.v" -`include "util.v" -`include "clk_divider.v" - -module fpga_lf( - input spck, output miso, input mosi, input ncs, - input pck0, input ck_1356meg, input ck_1356megb, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, output adc_noe, - output ssp_frame, output ssp_din, input ssp_dout, output ssp_clk, - input cross_hi, input cross_lo, - output dbg -); - -//----------------------------------------------------------------------------- -// The SPI receiver. This sets up the configuration word, which the rest of -// the logic looks at to determine how to connect the A/D and the coil -// drivers (i.e., which section gets it). Also assign some symbolic names -// to the configuration bits, for use below. -//----------------------------------------------------------------------------- - -/* - Attempt to write up how its hooked up. Iceman 2020. - - Communication between ARM / FPGA is done inside armsrc/fpgaloader.c see: function FpgaSendCommand() - Send 16 bit command / data pair to FPGA - The bit format is: C3 C2 C1 C0 D11 D10 D9 D8 D7 D6 D5 D4 D3 D2 D1 D0 - where - C is 4bit command - D is 12bit data - - shift_reg receive this 16bit frame - - LF command - ---------- - shift_reg[15:12] == 4bit command - LF has three commands (FPGA_CMD_SET_CONFREG, FPGA_CMD_SET_DIVISOR, FPGA_CMD_SET_EDGE_DETECT_THRESHOLD) - Current commands uses only 2bits. We have room for up to 4bits of commands total (7). - - LF data - ------- - shift_reg[11:0] == 12bit data - lf data is divided into MAJOR MODES and configuration values. - - The major modes uses 3bits (0,1,2,3,7 | 000, 001, 010, 011, 111) - 000 FPGA_MAJOR_MODE_LF_READER = Act as LF reader (modulate) - 001 FPGA_MAJOR_MODE_LF_EDGE_DETECT = Simulate LF - 010 FPGA_MAJOR_MODE_LF_PASSTHRU = Passthrough mode, CROSS_LO line connected to SSP_DIN. SSP_DOUT logic level controls if we modulate / listening - 011 FPGA_MAJOR_MODE_LF_ADC = refactor hitag2, clear ADC sampling - 111 FPGA_MAJOR_MODE_OFF = turn off sampling. - - Each one of this major modes can have options. Currently these two major modes uses options. - - FPGA_MAJOR_MODE_LF_READER - - FPGA_MAJOR_MODE_LF_EDGE_DETECT - - FPGA_MAJOR_MODE_LF_READER - ------------------------------------- - lf_field = 1bit (FPGA_LF_ADC_READER_FIELD) - - You can send FPGA_CMD_SET_DIVISOR to set with FREQUENCY the fpga should sample at - divisor = 8bits shift_reg[7:0] - - FPGA_MAJOR_MODE_LF_EDGE_DETECT - ------------------------------------------ - lf_ed_toggle_mode = 1bits - lf_ed_threshold = 8bits threshold defaults to 127 - - You can send FPGA_CMD_SET_EDGE_DETECT_THRESHOLD to set a custom threshold - lf_ed_threshold = 8bits threshold value. - - conf_word 12bits - conf_word[8:6] = 3bit major mode. - conf_word[0] = 1bit lf_field - conf_word[1] = 1bit lf_ed_toggle_mode - conf_word[7:0] = 8bit divisor - conf_word[7:0] = 8bit threshold - ------+--------- frame layout -------------------- -bit | 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 ------+------------------------------------------- -cmd | x x x x -major| x x x -opt | x x -divi | x x x x x x x x -thres| x x x x x x x x ------+------------------------------------------- -*/ - -reg [15:0] shift_reg; -reg [7:0] divisor; -reg [7:0] lf_ed_threshold; -reg [11:0] conf_word; - -wire [2:0] major_mode = conf_word[8:6]; -wire lf_field = conf_word[0]; -wire lf_ed_toggle_mode = conf_word[1]; - -// Handles cmd / data frame from ARM -always @(posedge ncs) -begin - // 4 bit command - case (shift_reg[15:12]) - `FPGA_CMD_SET_CONFREG: - begin - // 12 bit data - conf_word <= shift_reg[11:0]; - if (shift_reg[8:6] == `FPGA_MAJOR_MODE_LF_EDGE_DETECT) - begin - lf_ed_threshold <= 127; // default threshold - end - end - - `FPGA_CMD_SET_DIVISOR: - divisor <= shift_reg[7:0]; // 8bits - - `FPGA_CMD_SET_EDGE_DETECT_THRESHOLD: - lf_ed_threshold <= shift_reg[7:0]; // 8 bits - endcase -end - -// Receive 16bits of data from ARM here. -always @(posedge spck) -begin - if (~ncs) - begin - shift_reg[15:1] <= shift_reg[14:0]; - shift_reg[0] <= mosi; - end -end - -//----------------------------------------------------------------------------- -// And then we instantiate the modules corresponding to each of the FPGA's -// major modes, and use muxes to connect the outputs of the active mode to -// the output pins. -//----------------------------------------------------------------------------- -wire [7:0] pck_cnt; -wire pck_divclk; -clk_divider div_clk(pck0, divisor, pck_cnt, pck_divclk); - -lo_read lr( - pck0, pck_cnt, pck_divclk, - lr_pwr_lo, lr_pwr_hi, lr_pwr_oe1, lr_pwr_oe2, lr_pwr_oe3, lr_pwr_oe4, - adc_d, lr_adc_clk, - lr_ssp_frame, lr_ssp_din, lr_ssp_clk, - lr_dbg, lf_field -); - -lo_passthru lp( - pck_divclk, - lp_pwr_lo, lp_pwr_hi, lp_pwr_oe1, lp_pwr_oe2, lp_pwr_oe3, lp_pwr_oe4, - lp_adc_clk, - lp_ssp_din, ssp_dout, - cross_lo, - lp_dbg -); - -lo_edge_detect le( - pck0, pck_divclk, - le_pwr_lo, le_pwr_hi, le_pwr_oe1, le_pwr_oe2, le_pwr_oe3, le_pwr_oe4, - adc_d, le_adc_clk, - le_ssp_frame, ssp_dout, le_ssp_clk, - cross_lo, - le_dbg, - lf_field, - lf_ed_toggle_mode, lf_ed_threshold -); - -lo_adc la( - pck0, - la_pwr_lo, la_pwr_hi, la_pwr_oe1, la_pwr_oe2, la_pwr_oe3, la_pwr_oe4, - adc_d, la_adc_clk, - la_ssp_frame, la_ssp_din, ssp_dout, la_ssp_clk, - la_dbg, divisor, - lf_field -); - -// Major modes: -// 000 -- LF reader (generic) -// 001 -- LF edge detect (generic) -// 010 -- LF passthrough -// 011 -- LF ADC (read/write) -// 100 -- unused -// 101 -- unused -// 110 -- unused -// 111 -- FPGA_MAJOR_MODE_OFF -// 000 001 010 011 100 101 110 111 -mux8 mux_ssp_clk (major_mode, ssp_clk, lr_ssp_clk, le_ssp_clk, 1'b0, la_ssp_clk, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_ssp_din (major_mode, ssp_din, lr_ssp_din, 1'b0, lp_ssp_din, la_ssp_din, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_ssp_frame (major_mode, ssp_frame, lr_ssp_frame, le_ssp_frame, 1'b0, la_ssp_frame, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe1 (major_mode, pwr_oe1, lr_pwr_oe1, le_pwr_oe1, lp_pwr_oe1, la_pwr_oe1, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe2 (major_mode, pwr_oe2, lr_pwr_oe2, le_pwr_oe2, lp_pwr_oe2, la_pwr_oe2, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe3 (major_mode, pwr_oe3, lr_pwr_oe3, le_pwr_oe3, lp_pwr_oe3, la_pwr_oe3, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe4 (major_mode, pwr_oe4, lr_pwr_oe4, le_pwr_oe4, lp_pwr_oe4, la_pwr_oe4, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_lo (major_mode, pwr_lo, lr_pwr_lo, le_pwr_lo, lp_pwr_lo, la_pwr_lo, 1'b0, 1'b0, 1'b1, 1'b0); -mux8 mux_pwr_hi (major_mode, pwr_hi, lr_pwr_hi, le_pwr_hi, lp_pwr_hi, la_pwr_hi, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_adc_clk (major_mode, adc_clk, lr_adc_clk, le_adc_clk, lp_adc_clk, la_adc_clk, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_dbg (major_mode, dbg, lr_dbg, le_dbg, lp_dbg, la_dbg, 1'b0, 1'b0, 1'b0, 1'b0); - -// In all modes, let the ADC's outputs be enabled. -assign adc_noe = 1'b0; - -endmodule diff --git a/fpga-xc2s30/go.bat b/fpga-xc2s30/go.bat deleted file mode 100644 index d9704e08d..000000000 --- a/fpga-xc2s30/go.bat +++ /dev/null @@ -1,68 +0,0 @@ -@echo off - -rmdir/s/q xst - -del fpga_lf.ngc -xst -ifn xst_lf.scr -if errorlevel 0 goto ok1 -goto done -:ok1 - -del fpga_lf.ngd -ngdbuild -aul -p xc2s30-6vq100 -nt timestamp -uc fpga.ucf fpga_lf.ngc fpga_lf.ngd -if errorlevel 0 goto ok2 -goto done -:ok2 - -del fpga_lf.ncd -map -p xc2s30-6vq100 fpga_lf.ngd -if errorlevel 0 goto ok3 -goto done -:ok3 - -del fpga_lf-placed.ncd -par fpga_lf.ncd fpga_lf-placed.ncd -if errorlevel 0 goto ok4 -goto done -:ok4 - -del fpga_lf.bit fpga_lf.drc fpga_lf.rbt -bitgen -b fpga_lf-placed.ncd fpga_lf.bit -if errorlevel 0 goto ok5 -goto done -:ok5 - -del fpga_hf.ngc -xst -ifn xst_hf.scr -if errorlevel 0 goto ok6 -goto done -:ok6 - -del fpga_hf.ngd -ngdbuild -aul -p xc2s30-6vq100 -nt timestamp -uc fpga.ucf fpga_hf.ngc fpga_hf.ngd -if errorlevel 0 goto ok7 -goto done -:ok7 - -del fpga_hf.ncd -map -p xc2s30-6vq100 fpga_hf.ngd -if errorlevel 0 goto ok8 -goto done -:ok8 - -del fpga_hf-placed.ncd -par fpga_hf.ncd fpga_hf-placed.ncd -if errorlevel 0 goto ok9 -goto done -:ok9 - -del fpga_hf.bit fpga_hf.drc fpga_hf.rbt -bitgen -b fpga_hf-placed.ncd fpga_hf.bit -if errorlevel 0 goto ok10 -goto done -:ok10 - -echo okay -perl ..\tools\rbt2c.pl fpga_lf.rbt > ..\armsrc\fpgaimg.c - -:done diff --git a/fpga-xc2s30/xst_felica.scr b/fpga-xc2s30/xst_felica.scr deleted file mode 100644 index b069fab13..000000000 --- a/fpga-xc2s30/xst_felica.scr +++ /dev/null @@ -1 +0,0 @@ -run -ifn fpga_felica.v -ifmt Verilog -ofn fpga_felica.ngc -ofmt NGC -p xc2s30-5-vq100 -top fpga_felica -opt_mode area -opt_level 2 -resource_sharing yes -fsm_style bram -fsm_encoding compact diff --git a/fpga-xc2s30/xst_hf.scr b/fpga-xc2s30/xst_hf.scr deleted file mode 100644 index dd2fdc859..000000000 --- a/fpga-xc2s30/xst_hf.scr +++ /dev/null @@ -1 +0,0 @@ -run -ifn fpga_hf.v -ifmt Verilog -ofn fpga_hf.ngc -ofmt NGC -p xc2s30-5-vq100 -top fpga_hf -opt_mode area -opt_level 2 -resource_sharing yes -fsm_style bram -fsm_encoding compact diff --git a/fpga-xc2s30/xst_hf_15.scr b/fpga-xc2s30/xst_hf_15.scr deleted file mode 100644 index d8bb5ae7c..000000000 --- a/fpga-xc2s30/xst_hf_15.scr +++ /dev/null @@ -1 +0,0 @@ -run -ifn fpga_hf_15.v -ifmt Verilog -ofn fpga_hf_15.ngc -ofmt NGC -p xc2s30-5-vq100 -top fpga_hf_15 -opt_mode area -opt_level 2 -resource_sharing yes -fsm_style bram -fsm_encoding compact diff --git a/fpga-xc2s30/xst_lf.scr b/fpga-xc2s30/xst_lf.scr deleted file mode 100644 index 2d6c7e951..000000000 --- a/fpga-xc2s30/xst_lf.scr +++ /dev/null @@ -1 +0,0 @@ -run -ifn fpga_lf.v -ifmt Verilog -ofn fpga_lf.ngc -ofmt NGC -p xc2s30-5-vq100 -top fpga_lf -opt_mode area -opt_level 2 -resource_sharing yes -fsm_style bram -fsm_encoding compact diff --git a/fpga-xc3s100e/.gitignore b/fpga-xc3s100e/.gitignore deleted file mode 100644 index b21d41545..000000000 --- a/fpga-xc3s100e/.gitignore +++ /dev/null @@ -1,68 +0,0 @@ -# intermediate build files -*.bgn -*.bit -*.bld -*.cmd_log -*.drc -*.ll -*.lso -*.msd -*.msk -*.ncd -*.ngc -*.ngd -*.ngr -*.pad -*.par -*.pcf -*.prj -*.ptwx -*.rbb -*.rbd -*.stx -*.syr -*.twr -*.twx -*.unroutes -*.ut -*.xpi -*.xst -*_bitgen.xwbt -*_envsettings.html -*_map.map -*_map.mrp -*_map.ngm -*_map.xrpt -*_ngdbuild.xrpt -*_pad.csv -*_pad.txt -*_par.xrpt -*_summary.html -*_summary.xml -*_usage.xml -*_xst.xrpt - -# iMPACT generated files -_impactbatch.log -impact.xsl -impact_impact.xwbt -ise_impact.cmd -webtalk_impact.xml - -# Core Generator generated files -xaw2verilog.log - -# project-wide generated files -*.gise -par_usage_statistics.html -usage_statistics_webtalk.html -webtalk.log -webtalk_pn.xml - -# generated folders -iseconfig/ -xlnx_auto_0_xdb/ -xst/ -_ngo/ -_xmsgs/ -fpga_hf_xdb/tmp/ diff --git a/fpga-xc3s100e/clk_divider.v b/fpga-xc3s100e/clk_divider.v deleted file mode 100644 index 9a57879b0..000000000 --- a/fpga-xc3s100e/clk_divider.v +++ /dev/null @@ -1,25 +0,0 @@ -//----------------------------------------------------------------------------- -// Copyright (C) 2014 iZsh -// -// This code is licensed to you under the terms of the GNU GPL, version 2 or, -// at your option, any later version. See the LICENSE.txt file for the text of -// the license. -//----------------------------------------------------------------------------- -module clk_divider(input clk, input [7:0] divisor, output [7:0] div_cnt, output div_clk); - - reg [7:0] div_cnt_ = 0; - reg div_clk_; - assign div_cnt = div_cnt_; - assign div_clk = div_clk_; - - always @(posedge clk) - begin - if(div_cnt == divisor) begin - div_cnt_ <= 8'd0; - div_clk_ = !div_clk_; - end else - div_cnt_ <= div_cnt_ + 1; - end - -endmodule - diff --git a/fpga-xc3s100e/compile.sh b/fpga-xc3s100e/compile.sh deleted file mode 100755 index 741ed0bb8..000000000 --- a/fpga-xc3s100e/compile.sh +++ /dev/null @@ -1,9 +0,0 @@ -#!/bin/bash - -( - cd iseproj/fpga_hf - xtclsh fpga_hf.tcl run_process - mv fpga_hf.bit ../.. - git checkout fpga_hf.ise - git clean -dfx . -) diff --git a/fpga-xc3s100e/define.v b/fpga-xc3s100e/define.v deleted file mode 100644 index adced9003..000000000 --- a/fpga-xc3s100e/define.v +++ /dev/null @@ -1,49 +0,0 @@ -// Defining commands, modes and options. This must be aligned to the definitions in fpgaloader.h -// Note: the definitions here are without shifts - -// Commands: -`define FPGA_CMD_SET_CONFREG 1 -`define FPGA_CMD_TRACE_ENABLE 2 - -// Major modes: -`define FPGA_MAJOR_MODE_HF_READER 0 -`define FPGA_MAJOR_MODE_HF_SIMULATOR 1 -`define FPGA_MAJOR_MODE_HF_ISO14443A 2 -`define FPGA_MAJOR_MODE_HF_SNIFF 3 -`define FPGA_MAJOR_MODE_HF_ISO18092 4 -`define FPGA_MAJOR_MODE_HF_GET_TRACE 5 -`define FPGA_MAJOR_MODE_OFF 7 - -// Options for the generic HF reader -`define FPGA_HF_READER_MODE_RECEIVE_IQ 0 -`define FPGA_HF_READER_MODE_RECEIVE_AMPLITUDE 1 -`define FPGA_HF_READER_MODE_RECEIVE_PHASE 2 -`define FPGA_HF_READER_MODE_SEND_FULL_MOD 3 -`define FPGA_HF_READER_MODE_SEND_SHALLOW_MOD 4 -`define FPGA_HF_READER_MODE_SNIFF_IQ 5 -`define FPGA_HF_READER_MODE_SNIFF_AMPLITUDE 6 -`define FPGA_HF_READER_MODE_SNIFF_PHASE 7 -`define FPGA_HF_READER_MODE_SEND_JAM 8 - -`define FPGA_HF_READER_SUBCARRIER_848_KHZ 0 -`define FPGA_HF_READER_SUBCARRIER_424_KHZ 1 -`define FPGA_HF_READER_SUBCARRIER_212_KHZ 2 - -// Options for the HF simulated tag, how to modulate -`define FPGA_HF_SIMULATOR_NO_MODULATION 0 -`define FPGA_HF_SIMULATOR_MODULATE_BPSK 1 -`define FPGA_HF_SIMULATOR_MODULATE_212K 2 -`define FPGA_HF_SIMULATOR_MODULATE_424K 4 -`define FPGA_HF_SIMULATOR_MODULATE_424K_8BIT 5 - -// Options for ISO14443A -`define FPGA_HF_ISO14443A_SNIFFER 0 -`define FPGA_HF_ISO14443A_TAGSIM_LISTEN 1 -`define FPGA_HF_ISO14443A_TAGSIM_MOD 2 -`define FPGA_HF_ISO14443A_READER_LISTEN 3 -`define FPGA_HF_ISO14443A_READER_MOD 4 - -//options for ISO18092 / Felica -`define FPGA_HF_ISO18092_FLAG_NOMOD 1 // 0001 disable modulation module -`define FPGA_HF_ISO18092_FLAG_424K 2 // 0010 should enable 414k mode (untested). No autodetect -`define FPGA_HF_ISO18092_FLAG_READER 4 // 0100 enables antenna power, to act as a reader instead of tag diff --git a/fpga-xc3s100e/fpga.ucf b/fpga-xc3s100e/fpga.ucf deleted file mode 100644 index 4cb06a9d6..000000000 --- a/fpga-xc3s100e/fpga.ucf +++ /dev/null @@ -1,56 +0,0 @@ -# See the schematic for the pin assignment. - -#NET "cross_hi" LOC = "P88" ; -#NET "miso" LOC = "P40" ; - -# definition of Clock nets: -NET "ck_1356meg" TNM_NET = "clk_net_1356" ; -NET "ck_1356megb" TNM_NET = "clk_net_1356b" ; -NET "pck0" TNM_NET = "clk_net_pck0" ; -NET "spck" TNM_NET = "clk_net_spck" ; - -# Timing specs of clock nets: -TIMEGRP "clk_net_1356_all" = "clk_net_1356" "clk_net_1356b" ; -TIMESPEC "TS_1356MHz" = PERIOD "clk_net_1356_all" 74 ns HIGH 37 ns ; -TIMESPEC "TS_24MHz" = PERIOD "clk_net_pck0" 42 ns HIGH 21 ns ; -TIMESPEC "TS_4MHz" = PERIOD "clk_net_spck" 250 ns HIGH 125 ns ; -NET "FPGA_SWITCH" CLOCK_DEDICATED_ROUTE = FALSE ; -#PACE: Start of Constraints generated by PACE - -#PACE: Start of PACE I/O Pin Assignments -NET "adc_clk" LOC = "P65" ; -NET "adc_d<0>" LOC = "P79" ; -NET "adc_d<1>" LOC = "P78" ; -NET "adc_d<2>" LOC = "P71" ; -NET "adc_d<3>" LOC = "P70" ; -NET "adc_d<4>" LOC = "P69" ; -NET "adc_d<5>" LOC = "P68" ; -NET "adc_d<6>" LOC = "P67" ; -NET "adc_d<7>" LOC = "P66" ; -NET "adc_noe" LOC = "P62" ; -NET "ck_1356meg" LOC = "p88" ; -NET "ck_1356megb" LOC = "p89" ; -NET "cross_lo" LOC = "P90" ; -NET "dbg" LOC = "P22" ; -NET "FPGA_SWITCH" LOC = "P38" ; -NET "mosi" LOC = "P43" ; -NET "ncs" LOC = "P40" ; -NET "pck0" LOC = "P36" ; -NET "pwr_hi" LOC = "P85" ; -NET "pwr_lo" LOC = "P83" ; -NET "PWR_LO_EN" LOC = "P94" ; -NET "pwr_oe1" LOC = "P84" ; -NET "pwr_oe2" LOC = "P91" ; -NET "pwr_oe3" LOC = "P92" ; -NET "pwr_oe4" LOC = "P86" ; -NET "spck" LOC = "P39" ; -NET "ssp_clk" LOC = "P33" ; -NET "ssp_din" LOC = "P32" ; -NET "ssp_dout" LOC = "P34" ; -NET "ssp_frame" LOC = "P27" ; - -#PACE: Start of PACE Area Constraints - -#PACE: Start of PACE Prohibit Constraints - -#PACE: End of Constraints generated by PACE diff --git a/fpga-xc3s100e/fpga_hf.bit b/fpga-xc3s100e/fpga_hf.bit deleted file mode 100644 index df1fb45f6..000000000 Binary files a/fpga-xc3s100e/fpga_hf.bit and /dev/null differ diff --git a/fpga-xc3s100e/fpga_hfmod.v b/fpga-xc3s100e/fpga_hfmod.v deleted file mode 100644 index 53040aead..000000000 --- a/fpga-xc3s100e/fpga_hfmod.v +++ /dev/null @@ -1,193 +0,0 @@ -//----------------------------------------------------------------------------- -// The FPGA is responsible for interfacing between the A/D, the coil drivers, -// and the ARM. In the low-frequency modes it passes the data straight -// through, so that the ARM gets raw A/D samples over the SSP. In the high- -// frequency modes, the FPGA might perform some demodulation first, to -// reduce the amount of data that we must send to the ARM. -// -// I am not really an FPGA/ASIC designer, so I am sure that a lot of this -// could be improved. -// -// Jonathan Westhues, March 2006 -// Added ISO14443-A support by Gerhard de Koning Gans, April 2008 -// iZsh , June 2014 -// Piwi, Feb 2019 -//----------------------------------------------------------------------------- - -//For ISE 10.1 PROJ,IDE cannot apply definition to all files -`include "define.v" - - -//For ISE 10.1 PROJ,IDE auto include -//`include "hi_reader.v" -//`include "hi_simulate.v" -//`include "hi_iso14443a.v" -//`include "hi_sniffer.v" -//`include "util.v" -//`include "hi_flite.v" -//`include "hi_get_trace.v" - -module fpga_hfmod( - input spck, output miso, input mosi, input ncs, - input pck0, input ck_1356meg, input ck_1356megb, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, output adc_noe, - output ssp_frame, output ssp_din, input ssp_dout, output ssp_clk, - input cross_hi, input cross_lo, - output dbg -); - -//----------------------------------------------------------------------------- -// The SPI receiver. This sets up the configuration word, which the rest of -// the logic looks at to determine how to connect the A/D and the coil -// drivers (i.e., which section gets it). Also assign some symbolic names -// to the configuration bits, for use below. -//----------------------------------------------------------------------------- - -/* - Attempt to write up how its hooked up. Iceman 2020. - - Communication between ARM / FPGA is done inside armsrc/fpgaloader.c see: function FpgaSendCommand() - Send 16 bit command / data pair to FPGA - The bit format is: C3 C2 C1 C0 D11 D10 D9 D8 D7 D6 D5 D4 D3 D2 D1 D0 - where - C is 4bit command - D is 12bit data - - shift_reg receive this 16bit frame - - ------+--------- frame layout -------------------- -bit | 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 ------+------------------------------------------- -cmd | x x x x -major| x x x -opt | x x x -divi | x x x x x x x x -thres| x x x x x x x x ------+------------------------------------------- -*/ - -reg [15:0] shift_reg; -reg [8:0] conf_word; -reg trace_enable; - -// We switch modes between transmitting to the 13.56 MHz tag and receiving -// from it, which means that we must make sure that we can do so without -// glitching, or else we will glitch the transmitted carrier. -always @(posedge ncs) -begin - case(shift_reg[15:12]) - `FPGA_CMD_SET_CONFREG: conf_word <= shift_reg[8:0]; - `FPGA_CMD_TRACE_ENABLE: trace_enable <= shift_reg[0]; - endcase -end - -always @(posedge spck) -begin - if(~ncs) - begin - shift_reg[15:1] <= shift_reg[14:0]; - shift_reg[0] <= mosi; - end -end - -// select module (outputs) based on major mode -wire [2:0] major_mode = conf_word[8:6]; - -// configuring the HF reader -wire [1:0] subcarrier_frequency = conf_word[5:4]; -wire [3:0] minor_mode = conf_word[3:0]; - -//----------------------------------------------------------------------------- -// And then we instantiate the modules corresponding to each of the FPGA's -// major modes, and use muxes to connect the outputs of the active mode to -// the output pins. -//----------------------------------------------------------------------------- - -// 000 - HF reader -hi_reader hr( - ck_1356megb, - hr_pwr_lo, hr_pwr_hi, hr_pwr_oe1, hr_pwr_oe2, hr_pwr_oe3, hr_pwr_oe4, - adc_d, hr_adc_clk, - hr_ssp_frame, hr_ssp_din, ssp_dout, hr_ssp_clk, - hr_dbg, - subcarrier_frequency, minor_mode -); - -// 001 - HF simulated tag -hi_simulate hs( - ck_1356meg, - hs_pwr_lo, hs_pwr_hi, hs_pwr_oe1, hs_pwr_oe2, hs_pwr_oe3, hs_pwr_oe4, - adc_d, hs_adc_clk, - hs_ssp_frame, hs_ssp_din, ssp_dout, hs_ssp_clk, - hs_dbg, - minor_mode -); - -// 010 - HF ISO14443-A -hi_iso14443a hisn( - ck_1356meg, - hisn_pwr_lo, hisn_pwr_hi, hisn_pwr_oe1, hisn_pwr_oe2, hisn_pwr_oe3, hisn_pwr_oe4, - adc_d, hisn_adc_clk, - hisn_ssp_frame, hisn_ssp_din, ssp_dout, hisn_ssp_clk, - hisn_dbg, - minor_mode -); - -// 011 - HF sniff -hi_sniffer he( - ck_1356megb, - he_pwr_lo, he_pwr_hi, he_pwr_oe1, he_pwr_oe2, he_pwr_oe3, he_pwr_oe4, - adc_d, he_adc_clk, - he_ssp_frame, he_ssp_din, he_ssp_clk -); - -// 100 - HF ISO18092 FeliCa - -hi_flite hfl( - ck_1356megb, - hfl_pwr_lo, hfl_pwr_hi, hfl_pwr_oe1, hfl_pwr_oe2, hfl_pwr_oe3, hfl_pwr_oe4, - adc_d, hfl_adc_clk, - hfl_ssp_frame, hfl_ssp_din, ssp_dout, hfl_ssp_clk, - hfl_dbg, - minor_mode -); - - -// 101 - HF get trace -hi_get_trace gt( - ck_1356megb, - adc_d, trace_enable, major_mode, - gt_ssp_frame, gt_ssp_din, gt_ssp_clk -); - -// Major modes: -// 000 -- HF reader; subcarrier frequency and modulation depth selectable -// 001 -- HF simulated tag -// 010 -- HF ISO14443-A -// 011 -- HF sniff -// 100 -- HF ISO18092 FeliCa -// 101 -- HF get trace -// 110 -- unused -// 111 -- FPGA_MAJOR_MODE_OFF - -// 000 001 010 011 100 101 110 111 - -mux8 mux_ssp_clk (major_mode, ssp_clk, hr_ssp_clk, hs_ssp_clk, hisn_ssp_clk, he_ssp_clk, hfl_ssp_clk, gt_ssp_clk, 1'b0, 1'b0); -mux8 mux_ssp_din (major_mode, ssp_din, hr_ssp_din, hs_ssp_din, hisn_ssp_din, he_ssp_din, hfl_ssp_din, gt_ssp_din, 1'b0, 1'b0); -mux8 mux_ssp_frame (major_mode, ssp_frame, hr_ssp_frame, hs_ssp_frame, hisn_ssp_frame, he_ssp_frame, hfl_ssp_frame, gt_ssp_frame, 1'b0, 1'b0); -mux8 mux_pwr_oe1 (major_mode, pwr_oe1, hr_pwr_oe1, hs_pwr_oe1, hisn_pwr_oe1, he_pwr_oe1, hfl_pwr_oe1, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe2 (major_mode, pwr_oe2, hr_pwr_oe2, hs_pwr_oe2, hisn_pwr_oe2, he_pwr_oe2, hfl_pwr_oe2, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe3 (major_mode, pwr_oe3, hr_pwr_oe3, hs_pwr_oe3, hisn_pwr_oe3, he_pwr_oe3, hfl_pwr_oe3, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe4 (major_mode, pwr_oe4, hr_pwr_oe4, hs_pwr_oe4, hisn_pwr_oe4, he_pwr_oe4, hfl_pwr_oe4, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_lo (major_mode, pwr_lo, hr_pwr_lo, hs_pwr_lo, hisn_pwr_lo, he_pwr_lo, hfl_pwr_lo, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_hi (major_mode, pwr_hi, hr_pwr_hi, hs_pwr_hi, hisn_pwr_hi, he_pwr_hi, hfl_pwr_hi, 1'b0, 1'b0, 1'b0); -mux8 mux_adc_clk (major_mode, adc_clk, hr_adc_clk, hs_adc_clk, hisn_adc_clk, he_adc_clk, hfl_adc_clk, 1'b0, 1'b0, 1'b0); -mux8 mux_dbg (major_mode, dbg, hr_dbg, hs_dbg, hisn_dbg, he_dbg, hfl_dbg, 1'b0, 1'b0, 1'b0); - -// In all modes, let the ADC's outputs be enabled. -assign adc_noe = 1'b0; - -endmodule diff --git a/fpga-xc3s100e/fpga_lfmod.v b/fpga-xc3s100e/fpga_lfmod.v deleted file mode 100644 index 5982a74e8..000000000 --- a/fpga-xc3s100e/fpga_lfmod.v +++ /dev/null @@ -1,236 +0,0 @@ -//----------------------------------------------------------------------------- -// Jonathan Westhues, March 2006 -// iZsh , June 2014 -// Piwi, Feb 2019 -// Anon, 2019 -//----------------------------------------------------------------------------- -// Defining commands, modes and options. This must be aligned to the definitions in fpgaloader.h -// Note: the definitions here are without shifts - -// Commands: -`define FPGA_CMD_SET_CONFREG 1 -`define FPGA_CMD_SET_DIVISOR 2 -`define FPGA_CMD_SET_EDGE_DETECT_THRESHOLD 3 - -// Major modes: -`define FPGA_MAJOR_MODE_LF_READER 0 -`define FPGA_MAJOR_MODE_LF_EDGE_DETECT 1 -`define FPGA_MAJOR_MODE_LF_PASSTHRU 2 -`define FPGA_MAJOR_MODE_LF_ADC 3 - -// Options for LF_READER -`define FPGA_LF_ADC_READER_FIELD 1 - -// Options for LF_EDGE_DETECT -`define FPGA_LF_EDGE_DETECT_READER_FIELD 1 -`define FPGA_LF_EDGE_DETECT_TOGGLE_MODE 2 - -//For ISE 10.1 PROJ,IDE auto include -//`include "lo_read.v" -//`include "lo_passthru.v" -//`include "lo_edge_detect.v" -//`include "lo_adc.v" -//`include "util.v" -//`include "clk_divider.v" - -module fpga_lfmod( - input spck, output miso, input mosi, input ncs, - input pck0, input ck_1356meg, input ck_1356megb, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, output adc_noe, - output ssp_frame, output ssp_din, input ssp_dout, output ssp_clk, - input cross_hi, input cross_lo, - output dbg, - output PWR_LO_EN -); - -//----------------------------------------------------------------------------- -// The SPI receiver. This sets up the configuration word, which the rest of -// the logic looks at to determine how to connect the A/D and the coil -// drivers (i.e., which section gets it). Also assign some symbolic names -// to the configuration bits, for use below. -//----------------------------------------------------------------------------- - -/* - Attempt to write up how its hooked up. Iceman 2020. - - Communication between ARM / FPGA is done inside armsrc/fpgaloader.c see: function FpgaSendCommand() - Send 16 bit command / data pair to FPGA - The bit format is: C3 C2 C1 C0 D11 D10 D9 D8 D7 D6 D5 D4 D3 D2 D1 D0 - where - C is 4bit command - D is 12bit data - - shift_reg receive this 16bit frame - - LF command - ---------- - shift_reg[15:12] == 4bit command - LF has three commands (FPGA_CMD_SET_CONFREG, FPGA_CMD_SET_DIVISOR, FPGA_CMD_SET_EDGE_DETECT_THRESHOLD) - Current commands uses only 2bits. We have room for up to 4bits of commands total (7). - - LF data - ------- - shift_reg[11:0] == 12bit data - lf data is divided into MAJOR MODES and configuration values. - - The major modes uses 3bits (0,1,2,3,7 | 000, 001, 010, 011, 111) - 000 FPGA_MAJOR_MODE_LF_READER = Act as LF reader (modulate) - 001 FPGA_MAJOR_MODE_LF_EDGE_DETECT = Simulate LF - 010 FPGA_MAJOR_MODE_LF_PASSTHRU = Passthrough mode, CROSS_LO line connected to SSP_DIN. SSP_DOUT logic level controls if we modulate / listening - 011 FPGA_MAJOR_MODE_LF_ADC = refactor hitag2, clear ADC sampling - 111 FPGA_MAJOR_MODE_OFF = turn off sampling. - - Each one of this major modes can have options. Currently these two major modes uses options. - - FPGA_MAJOR_MODE_LF_READER - - FPGA_MAJOR_MODE_LF_EDGE_DETECT - - FPGA_MAJOR_MODE_LF_READER - ------------------------------------- - lf_field = 1bit (FPGA_LF_ADC_READER_FIELD) - - You can send FPGA_CMD_SET_DIVISOR to set with FREQUENCY the fpga should sample at - divisor = 8bits shift_reg[7:0] - - FPGA_MAJOR_MODE_LF_EDGE_DETECT - ------------------------------------------ - lf_ed_toggle_mode = 1bits - lf_ed_threshold = 8bits threshold defaults to 127 - - You can send FPGA_CMD_SET_EDGE_DETECT_THRESHOLD to set a custom threshold - lf_ed_threshold = 8bits threshold value. - - conf_word 12bits - conf_word[7:5] = 3bit major mode. - conf_word[0] = 1bit lf_field - conf_word[1] = 1bit lf_ed_toggle_mode - conf_word[7:0] = 8bit divisor - conf_word[7:0] = 8bit threshold - ------+--------- frame layout -------------------- -bit | 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 ------+------------------------------------------- -cmd | x x x x -major| x x x -opt | x x -divi | x x x x x x x x -thres| x x x x x x x x ------+------------------------------------------- -*/ - -reg [15:0] shift_reg; -reg [7:0] divisor; -reg [7:0] lf_ed_threshold; -reg [11:0] conf_word; - -wire [2:0] major_mode = conf_word[8:6]; -wire lf_field = conf_word[0]; -wire lf_ed_toggle_mode = conf_word[1]; - -// Handles cmd / data frame from ARM -always @(posedge ncs) -begin - // 4 bit command - case (shift_reg[15:12]) - `FPGA_CMD_SET_CONFREG: - begin - // 12 bit data - conf_word <= shift_reg[11:0]; - if (shift_reg[8:6] == `FPGA_MAJOR_MODE_LF_EDGE_DETECT) - begin - lf_ed_threshold <= 127; // default threshold - end - end - - `FPGA_CMD_SET_DIVISOR: - divisor <= shift_reg[7:0]; // 8bits - - `FPGA_CMD_SET_EDGE_DETECT_THRESHOLD: - lf_ed_threshold <= shift_reg[7:0]; // 8 bits - endcase -end - -// Receive 16bits of data from ARM here. -always @(posedge spck) -begin - if (~ncs) - begin - shift_reg[15:1] <= shift_reg[14:0]; - shift_reg[0] <= mosi; - end -end - -//----------------------------------------------------------------------------- -// And then we instantiate the modules corresponding to each of the FPGA's -// major modes, and use muxes to connect the outputs of the active mode to -// the output pins. -//----------------------------------------------------------------------------- -wire [7:0] pck_cnt; -wire pck_divclk; -clk_divider div_clk(pck0, divisor, pck_cnt, pck_divclk); - -lo_read lr( - pck0, pck_cnt, pck_divclk, - lr_pwr_lo, lr_pwr_hi, lr_pwr_oe1, lr_pwr_oe2, lr_pwr_oe3, lr_pwr_oe4, - adc_d, lr_adc_clk, - lr_ssp_frame, lr_ssp_din, lr_ssp_clk, - lr_dbg, lf_field -); - -lo_passthru lp( - pck_divclk, - lp_pwr_lo, lp_pwr_hi, lp_pwr_oe1, lp_pwr_oe2, lp_pwr_oe3, lp_pwr_oe4, - lp_adc_clk, - lp_ssp_din, ssp_dout, - cross_lo, - lp_dbg -); - -lo_edge_detect le( - pck0, pck_divclk, - le_pwr_lo, le_pwr_hi, le_pwr_oe1, le_pwr_oe2, le_pwr_oe3, le_pwr_oe4, - adc_d, le_adc_clk, - le_ssp_frame, ssp_dout, le_ssp_clk, - cross_lo, - le_dbg, - lf_field, - lf_ed_toggle_mode, lf_ed_threshold -); - -lo_adc la( - pck0, - la_pwr_lo, la_pwr_hi, la_pwr_oe1, la_pwr_oe2, la_pwr_oe3, la_pwr_oe4, - adc_d, la_adc_clk, - la_ssp_frame, la_ssp_din, ssp_dout, la_ssp_clk, - la_dbg, divisor, - lf_field -); - -// Major modes: -// 000 -- LF reader (generic) -// 001 -- LF edge detect (generic) -// 010 -- LF passthrough -// 011 -- LF ADC (read/write) -// 100 -- unused -// 101 -- unused -// 110 -- unused -// 111 -- FPGA_MAJOR_MODE_OFF -// 000 001 010 011 100 101 110 111 -mux8 mux_ssp_clk (major_mode, ssp_clk, lr_ssp_clk, le_ssp_clk, 1'b0, la_ssp_clk, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_ssp_din (major_mode, ssp_din, lr_ssp_din, 1'b0, lp_ssp_din, la_ssp_din, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_ssp_frame (major_mode, ssp_frame, lr_ssp_frame, le_ssp_frame, 1'b0, la_ssp_frame, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe1 (major_mode, pwr_oe1, lr_pwr_oe1, le_pwr_oe1, lp_pwr_oe1, la_pwr_oe1, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe2 (major_mode, pwr_oe2, lr_pwr_oe2, le_pwr_oe2, lp_pwr_oe2, la_pwr_oe2, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe3 (major_mode, pwr_oe3, lr_pwr_oe3, le_pwr_oe3, lp_pwr_oe3, la_pwr_oe3, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_oe4 (major_mode, pwr_oe4, lr_pwr_oe4, le_pwr_oe4, lp_pwr_oe4, la_pwr_oe4, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_pwr_lo (major_mode, pwr_lo, lr_pwr_lo, le_pwr_lo, lp_pwr_lo, la_pwr_lo, 1'b0, 1'b0, 1'b1, 1'b0); -mux8 mux_pwr_hi (major_mode, pwr_hi, lr_pwr_hi, le_pwr_hi, lp_pwr_hi, la_pwr_hi, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_adc_clk (major_mode, adc_clk, lr_adc_clk, le_adc_clk, lp_adc_clk, la_adc_clk, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_dbg (major_mode, dbg, lr_dbg, le_dbg, lp_dbg, la_dbg, 1'b0, 1'b0, 1'b0, 1'b0); -mux8 mux_ant (major_mode, PWR_LO_EN, 1'b1, 1'b1, 1'b1, 1'b1, 1'b0, 1'b0, 1'b0, 1'b0); - -// In all modes, let the ADC's outputs be enabled. -assign adc_noe = 1'b0; - -endmodule diff --git a/fpga-xc3s100e/hi_flite.v b/fpga-xc3s100e/hi_flite.v deleted file mode 100644 index 6cb87825e..000000000 --- a/fpga-xc3s100e/hi_flite.v +++ /dev/null @@ -1,368 +0,0 @@ -/* - This code demodulates and modulates signal as described in ISO/IEC 18092. - That includes packets used for Felica, NFC Tag 3, etc. (which do overlap) - simple envelope following algorithm is used (modification of fail0verflow LF one) - is used to combat some nasty aliasing effect with testing phone (envelope looked like sine wave) - - Speeds supported: only 212 kbps (fc/64) for now. Todo: 414 kbps - though for reader, the selection has to come from ARM. modulation waits for market sprocket -doesn't really mean anything - - mod_type: bits 210: - bit 2 : reader drive/power on/off - bit 1 : speed bit, 0 : 212, 1 :424 - bit 0 : listen or modulate -*/ - -module hi_flite( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, - mod_type -); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [3:0] mod_type; - -assign dbg = 0; - -wire power = mod_type[2]; -wire speed = mod_type[1]; -wire disabl = mod_type[0]; - -// Most off, oe4 for modulation; -// Trying reader emulation (would presumably just require switching power on, but I am not sure) -assign pwr_lo = 1'b0; - -// 512x64/fc -wait before ts0, 32768 ticks -// tslot: 256*64/fc -assign adc_clk = ck_1356meg; - -///heuristic values for initial thresholds. seem to work OK -`define imin 70 // (13'd256) -`define imax 180 // (-13'd256) -`define ithrmin 91 // -13'd8 -`define ithrmax 160 // 13'd8 - -`define min_bitdelay_212 8 -//minimum values and corresponding thresholds -reg [8:0] curmin=`imin; -reg [8:0] curminthres=`ithrmin; -reg [8:0] curmaxthres=`ithrmax; -reg [8:0] curmax=`imax; - -//signal state, 1-not modulated, 0 -modulated -reg after_hysteresis = 1'b1; - -//state machine for envelope tracking -reg [1:0] state=1'd0; - -//lower edge detected, trying to detect first bit of SYNC (b24d, 1011001001001101) -reg try_sync=1'b0; - -//detected first sync bit, phase frozen -reg did_sync=0; - -`define bithalf_212 32 // half-bit length for 212 kbit -`define bitmlen_212 63 // bit transition edge - -`define bithalf_424 16 // half-bit length for 212 kbit -`define bitmlen_424 31 // bit transition edge - -wire [7:0] bithalf = speed ? `bithalf_424 : `bithalf_212; -wire [7:0] bitmlen = speed ? `bitmlen_424 : `bitmlen_212; - - -//ssp clock and current values -reg ssp_clk; -reg ssp_frame; -reg curbit = 1'b0; - -reg [7:0] fccount = 8'd0; // in-bit tick counter. Counts carrier cycles from the first lower edge detected, reset on every manchester bit detected - -reg [7:0] tsinceedge = 8'd0;// ticks from last edge, desync if the valye is too large - -reg zero = 1'b0; // Manchester first halfbit low second high corresponds to this value. It has been known to change. SYNC is used to set it - -//ssp counter for transfer and framing -reg [8:0] ssp_cnt = 9'd0; - -always @(posedge adc_clk) - ssp_cnt <= (ssp_cnt + 1); - -//maybe change it so that ARM sends preamble as well. -//then: ready bits sent to ARM, 8 bits sent from ARM (all ones), then preamble (all zeros, presumably) - which starts modulation - -always @(negedge adc_clk) -begin - //count fc/64 - transfer bits to ARM at the rate they are received - if( ((~speed) && (ssp_cnt[5:0] == 6'b000000)) || (speed && (ssp_cnt[4:0] == 5'b00000))) - begin - ssp_clk <= 1'b1; - ssp_din <= curbit; - end - if( ( (~speed) && (ssp_cnt[5:0] == 6'b100000)) ||(speed && ssp_cnt[4:0] == 5'b10000)) - ssp_clk <= 1'b0; - //create frame pulses. TBH, I still don't know what they do exactly, but they are crucial for ARM->FPGA transfer. If the frame is in the beginning of the byte, transfer slows to a crawl for some reason - // took me a day to figure THAT out. - if(( (~speed) && (ssp_cnt[8:0] == 9'd31)) || (speed && ssp_cnt[7:0] == 8'd15)) - begin - ssp_frame <= 1'b1; - end - if(( (~speed) && (ssp_cnt[8:0] == 9'b1011111)) || (speed &&ssp_cnt[7:0] == 8'b101111) ) - begin - ssp_frame <= 1'b0; - end -end - -//send current bit (detected in SNIFF mode or the one being modulated in MOD mode, 0 otherwise) -reg ssp_din; - -//previous signal value, mostly to detect SYNC -reg prv = 1'b1; - -// for simple error correction in mod/demod detection, use maximum of modded/demodded in given interval. Maybe 1 bit is extra? but better safe than sorry. -reg[7:0] mid = 8'd128; - -// set TAGSIM__MODULATE on ARM if we want to write... (frame would get lost if done mid-frame...) -// start sending over 1s on ssp->arm when we start sending preamble -// reg sending = 1'b0; // are we actively modulating? -reg [11:0] bit_counts = 12'd0; // for timeslots. only support ts=0 for now, at 212 speed -512 fullbits from end of frame. One hopes. might remove those? - - -//we need some way to flush bit_counts triggers on mod_type changes don't compile -reg dlay; -always @(negedge adc_clk) // every data ping? -begin - //envelope follow code... - //////////// - if (fccount == bitmlen) - begin - if ((~try_sync) && (adc_d < curminthres) && disabl ) - begin - fccount <= 1; - end - else - begin - fccount <= 0; - end - dlay <= ssp_dout; - if (bit_counts > 768) // should be over ts0 now, without ARM interference... stop counting... - begin - bit_counts <= 0; - end - else - if (power) - bit_counts <= 0; - else - bit_counts <= bit_counts + 1; - end - else - begin - if((~try_sync) && (adc_d < curminthres) && disabl) - begin - fccount <= 1; - end - else - begin - fccount <= fccount + 1; - end - end - - // rising edge - if (adc_d > curmaxthres) - begin - case (state) - 0: begin - curmax <= adc_d > `imax? adc_d : `imax; - state <= 2; - end - 1: begin - curminthres <= ((curmin >> 1) + (curmin >> 2) + (curmin >> 4) + (curmax >> 3) + (curmax >> 4)); //threshold: 0.1875 max + 0.8125 min - curmaxthres <= ((curmax >> 1) + (curmax >> 2) + (curmax >> 4) + (curmin >> 3) + (curmin >> 4)); - curmax <= adc_d > 155 ? adc_d : 155; // to hopefully prevent overflow from spikes going up to 255 - state <= 2; - end - 2: begin - if (adc_d > curmax) - curmax <= adc_d; - end - default: - begin - end - endcase - after_hysteresis <= 1'b1; - if(try_sync) - tsinceedge <= 0; - end - else if (adc_d> 1) + (curmin >> 2) + (curmin >> 4) + (curmax >> 3) + (curmax >> 4)); - curmaxthres <= ( (curmax >> 1) + (curmax >> 2) + (curmax >> 4) + (curmin >> 3) + (curmin >> 4)); - curmin <= adc_d < `imin ? adc_d : `imin; - state <= 1; - end - default: - begin - end - endcase - after_hysteresis <= 0; - if (~try_sync ) //begin modulation, lower edge... - begin - try_sync <= 1; - fccount <= 1; - did_sync <= 0; - curbit <= 0; - mid <= 8'd127; - tsinceedge <= 0; - prv <= 1; - end - else - begin - tsinceedge <= 0; - end - end - else //stable state, low or high - begin - curminthres <= ( (curmin >> 1) + (curmin >> 2) + (curmin >> 4) + (curmax >> 3) + (curmax >> 4)); - curmaxthres <= ( (curmax >> 1) + (curmax >> 2) + (curmax >> 4) + (curmin >> 3) + (curmin >> 4)); - state <= 0; - - if (try_sync ) - begin - if (tsinceedge >= (128)) - begin - //we might need to start counting... assuming ARM wants to reply to the frame. - bit_counts <= 1;// i think? 128 is about 2 bits passed... but 1 also works - try_sync <= 0; - did_sync <= 0;//desync - curmin <= `imin; //reset envelope - curmax <= `imax; - curminthres <= `ithrmin; - curmaxthres <= `ithrmax; - prv <= 1; - tsinceedge <= 0; - after_hysteresis <= 1'b1; - curbit <= 0; - mid <= 8'd128; - end - else - tsinceedge <= (tsinceedge + 1); - end - end - - - if (try_sync && tsinceedge < 128) - begin - //detect bits in their middle ssp sampling is in sync, so it would sample all bits in order - if (fccount == bithalf) - begin - if ((~did_sync) && ((prv == 1 && (mid > 128))||(prv == 0 && (mid <= 128)))) - begin - //sync the Zero, and set curbit roperly - did_sync <= 1'b1; - zero <= ~prv;// 1-prv - curbit <= 1; - end - else - curbit <= (mid > 128) ? (~zero) : zero; - - prv <= (mid > 128) ? 1 : 0; - - if (adc_d > curmaxthres) - mid <= 8'd129; - else if (adc_d < curminthres) - mid <= 8'd127; - else - begin - if (after_hysteresis) - begin - mid <= 8'd129; - end - else - begin - mid <= 8'd127; - end - end - - end - else - begin - if (fccount==bitmlen) - begin - // fccount <= 0; - prv <= (mid > 128) ? 1 : 0; - mid <= 128; - end - else - begin - // minimum-maximum calc - if(adc_d > curmaxthres) - mid <= mid + 1; - else if (adc_d < curminthres) - mid <= mid - 1; - else - begin - if (after_hysteresis) - begin - mid <= mid + 1; - end - else - begin - mid <= mid - 1; - end - end - end - end - end - else - begin - end -// sending <= 0; -end -//put modulation here to maintain the correct clock. Seems that some readers are sensitive to that -reg pwr_hi; -reg pwr_oe1; -reg pwr_oe2; -reg pwr_oe3; -reg pwr_oe4; - -wire mod = ((fccount >= bithalf) ^ dlay) & (~disabl); - -always @(ck_1356meg or ssp_dout or power or disabl or mod) -begin - if (power) - begin - pwr_hi <= ck_1356meg; - pwr_oe1 <= 1'b0;//mod; - pwr_oe2 <= 1'b0;//mod; - pwr_oe3 <= 1'b0;//mod; - pwr_oe4 <= mod;//1'b0; - end - else - begin - pwr_hi <= 1'b0; - pwr_oe1 <= 1'b0; - pwr_oe2 <= 1'b0; - pwr_oe3 <= 1'b0; - pwr_oe4 <= mod; - end -end - -endmodule diff --git a/fpga-xc3s100e/hi_get_trace.v b/fpga-xc3s100e/hi_get_trace.v deleted file mode 100644 index 2b1cf393b..000000000 --- a/fpga-xc3s100e/hi_get_trace.v +++ /dev/null @@ -1,164 +0,0 @@ -//----------------------------------------------------------------------------- -// -// piwi, Feb 2019 -//----------------------------------------------------------------------------- -//For ISE 10.1 PROJ,IDE cannot apply definition to all files -`include "define.v" - -module hi_get_trace( - ck_1356megb, - adc_d, trace_enable, major_mode, - ssp_frame, ssp_din, ssp_clk -); - input ck_1356megb; - input [7:0] adc_d; - input trace_enable; - input [2:0] major_mode; - output ssp_frame, ssp_din, ssp_clk; - -// clock divider -reg [6:0] clock_cnt; -always @(negedge ck_1356megb) -begin - clock_cnt <= clock_cnt + 1; -end - -// sample at 13,56MHz / 8. The highest signal frequency (subcarrier) is 848,5kHz, i.e. in this case we oversample by a factor of 2 -reg [2:0] sample_clock; -always @(negedge ck_1356megb) -begin - if (sample_clock == 3'd7) - sample_clock <= 3'd0; - else - sample_clock <= sample_clock + 1; -end - - -reg [11:0] addr; -reg [11:0] start_addr; -reg [2:0] previous_major_mode; -reg write_enable1; -reg write_enable2; -always @(negedge ck_1356megb) -begin - previous_major_mode <= major_mode; - if (major_mode == `FPGA_MAJOR_MODE_HF_GET_TRACE) - begin - write_enable1 <= 1'b0; - write_enable2 <= 1'b0; - if (previous_major_mode != `FPGA_MAJOR_MODE_HF_GET_TRACE) // just switched into GET_TRACE mode - addr <= start_addr; - if (clock_cnt == 7'd0) - begin - if (addr == 12'd3071) - addr <= 12'd0; - else - addr <= addr + 1; - end - end - else if (major_mode != `FPGA_MAJOR_MODE_OFF) - begin - if (trace_enable) - begin - if (addr[11] == 1'b0) - begin - write_enable1 <= 1'b1; - write_enable2 <= 1'b0; - end - else - begin - write_enable1 <= 1'b0; - write_enable2 <= 1'b1; - end - if (sample_clock == 3'b000) - begin - if (addr == 12'd3071) - begin - addr <= 12'd0; - write_enable1 <= 1'b1; - write_enable2 <= 1'b0; - end - else - begin - addr <= addr + 1; - end - end - end - else - begin - write_enable1 <= 1'b0; - write_enable2 <= 1'b0; - start_addr <= addr; - end - end - else // major_mode == `FPGA_MAJOR_MODE_OFF - begin - write_enable1 <= 1'b0; - write_enable2 <= 1'b0; - if (previous_major_mode != `FPGA_MAJOR_MODE_OFF && previous_major_mode != `FPGA_MAJOR_MODE_HF_GET_TRACE) // just switched off - begin - start_addr <= addr; - end - end -end - - -// (2+1)k RAM -reg [7:0] D_out1, D_out2; -reg [7:0] ram1 [2047:0]; // 2048 u8 -reg [7:0] ram2 [1023:0]; // 1024 u8 - -always @(negedge ck_1356megb) -begin - if (write_enable1) - begin - ram1[addr[10:0]] <= adc_d; - D_out1 <= adc_d; - end - else - D_out1 <= ram1[addr[10:0]]; - if (write_enable2) -begin - ram2[addr[9:0]] <= adc_d; - D_out2 <= adc_d; - end - else - D_out2 <= ram2[addr[9:0]]; -end - - -// SSC communication to ARM -reg ssp_clk; -reg ssp_frame; -reg [7:0] shift_out; - -always @(negedge ck_1356megb) -begin - if (clock_cnt[3:0] == 4'd0) // update shift register every 16 clock cycles - begin - if (clock_cnt[6:4] == 3'd0) // either load new value - begin - if (addr[11] == 1'b0) - shift_out <= D_out1; - else - shift_out <= D_out2; - end - else - begin - // or shift left - shift_out[7:1] <= shift_out[6:0]; - end - end - - ssp_clk <= ~clock_cnt[3]; // ssp_clk frequency = 13,56MHz / 16 = 847,5 kHz - - if (clock_cnt[6:4] == 3'b000) // set ssp_frame for 0...31 - ssp_frame <= 1'b1; - else - ssp_frame <= 1'b0; - -end - -assign ssp_din = shift_out[7]; - -endmodule diff --git a/fpga-xc3s100e/hi_iso14443a.v b/fpga-xc3s100e/hi_iso14443a.v deleted file mode 100644 index 26ab0f9d9..000000000 --- a/fpga-xc3s100e/hi_iso14443a.v +++ /dev/null @@ -1,584 +0,0 @@ -//----------------------------------------------------------------------------- -// ISO14443-A support for the Proxmark III -// Gerhard de Koning Gans, April 2008 -//----------------------------------------------------------------------------- - -module hi_iso14443a( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, - mod_type -); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [3:0] mod_type; - - -wire adc_clk = ck_1356meg; - - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// Reader -> PM3: -// detecting and shaping the reader's signal. Reader will modulate the carrier by 100% (signal is either on or off). Use a -// hysteresis (Schmitt Trigger) to avoid false triggers during slowly increasing or decreasing carrier amplitudes -reg after_hysteresis; -reg [11:0] has_been_low_for; - -always @(negedge adc_clk) -begin - if(adc_d >= 16) after_hysteresis <= 1'b1; // U >= 1,14V -> after_hysteresis = 1 - else if(adc_d < 8) after_hysteresis <= 1'b0; // U < 1,04V -> after_hysteresis = 0 - // Note: was >= 3,53V and <= 1,19V. The new trigger values allow more reliable detection of the first bit - // (it might not reach 3,53V due to the high time constant of the high pass filter in the analogue RF part). - // In addition, the new values are more in line with ISO14443-2: "The PICC shall detect the ”End of Pause” after the field exceeds - // 5% of H_INITIAL and before it exceeds 60% of H_INITIAL." Depending on the signal strength, 60% might well be less than 3,53V. - - - // detecting a loss of reader's field (adc_d < 192 for 4096 clock cycles). If this is the case, - // set the detected reader signal (after_hysteresis) to '1' (unmodulated) - if(adc_d >= 192) - begin - has_been_low_for <= 12'd0; - end - else - begin - if(has_been_low_for == 12'd4095) - begin - has_been_low_for <= 12'd0; - after_hysteresis <= 1'b1; - end - else - begin - has_been_low_for <= has_been_low_for + 1; - end - end - -end - - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// Reader -> PM3 -// detect when a reader is active (modulating). We assume that the reader is active, if we see the carrier off for at least 8 -// carrier cycles. We assume that the reader is inactive, if the carrier stayed high for at least 256 carrier cycles. -reg deep_modulation; -reg [2:0] deep_counter; -reg [8:0] saw_deep_modulation; - -always @(negedge adc_clk) -begin - if(~(| adc_d[7:0])) // if adc_d == 0 (U <= 0,94V) - begin - if(deep_counter == 3'd7) // adc_d == 0 for 8 adc_clk ticks -> deep_modulation (by reader) - begin - deep_modulation <= 1'b1; - saw_deep_modulation <= 8'd0; - end - else - deep_counter <= deep_counter + 1; - end - else - begin - deep_counter <= 3'd0; - if(saw_deep_modulation == 8'd255) // adc_d != 0 for 256 adc_clk ticks -> deep_modulation is over, probably waiting for tag's response - deep_modulation <= 1'b0; - else - saw_deep_modulation <= saw_deep_modulation + 1; - end -end - - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// Tag -> PM3 -// filter the input for a tag's signal. The filter box needs the 4 previous input values and is a gaussian derivative filter -// for noise reduction and edge detection. -// store 4 previous samples: -reg [7:0] input_prev_4, input_prev_3, input_prev_2, input_prev_1; - -always @(negedge adc_clk) -begin - input_prev_4 <= input_prev_3; - input_prev_3 <= input_prev_2; - input_prev_2 <= input_prev_1; - input_prev_1 <= adc_d; -end - -// adc_d_filtered = 2*input_prev4 + 1*input_prev3 + 0*input_prev2 - 1*input_prev1 - 2*input -// = (2*input_prev4 + input_prev3) - (2*input + input_prev1) -wire [8:0] input_prev_4_times_2 = input_prev_4 << 1; -wire [8:0] adc_d_times_2 = adc_d << 1; - -wire [9:0] tmp1 = input_prev_4_times_2 + input_prev_3; -wire [9:0] tmp2 = adc_d_times_2 + input_prev_1; - -// convert intermediate signals to signed and calculate the filter output -wire signed [10:0] adc_d_filtered = {1'b0, tmp1} - {1'b0, tmp2}; - - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// internal FPGA timing. Maximum required period is 128 carrier clock cycles for a full 8 Bit transfer to ARM. (i.e. we need a -// 7 bit counter). Adjust its frequency to external reader's clock when simulating a tag or sniffing. -reg pre_after_hysteresis; -reg [3:0] reader_falling_edge_time; -reg [6:0] negedge_cnt; - -always @(negedge adc_clk) -begin - // detect a reader signal's falling edge and remember its timing: - pre_after_hysteresis <= after_hysteresis; - if (pre_after_hysteresis && ~after_hysteresis) - begin - reader_falling_edge_time[3:0] <= negedge_cnt[3:0]; - end - - // adjust internal timer counter if necessary: - if (negedge_cnt[3:0] == 4'd13 && (mod_type == `FPGA_HF_ISO14443A_SNIFFER || mod_type == `FPGA_HF_ISO14443A_TAGSIM_LISTEN) && deep_modulation) - begin - if (reader_falling_edge_time == 4'd1) // reader signal changes right after sampling. Better sample earlier next time. - begin - negedge_cnt <= negedge_cnt + 2; // time warp - end - else if (reader_falling_edge_time == 4'd0) // reader signal changes right before sampling. Better sample later next time. - begin - negedge_cnt <= negedge_cnt; // freeze time - end - else - begin - negedge_cnt <= negedge_cnt + 1; // Continue as usual - end - reader_falling_edge_time[3:0] <= 4'd8; // adjust only once per detected edge - end - else if (negedge_cnt == 7'd127) // normal operation: count from 0 to 127 - begin - negedge_cnt <= 0; - end - else - begin - negedge_cnt <= negedge_cnt + 1; - end -end - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// Tag -> PM3: -// determine best possible time for starting/resetting the modulation detector. -reg [3:0] mod_detect_reset_time; - -always @(negedge adc_clk) -begin - if (mod_type == `FPGA_HF_ISO14443A_READER_LISTEN) - // (our) reader signal changes at negedge_cnt[3:0]=9, tag response expected to start n*16+4 ticks later, further delayed by - // 3 ticks ADC conversion. The maximum filter output (edge detected) will be detected after subcarrier zero crossing (+7 ticks). - // To allow some timing variances, we want to have the maximum filter outputs well within the detection window, i.e. - // at mod_detect_reset_time+4 and mod_detect_reset_time+12 (-4 ticks). - // 9 + 4 + 3 + 7 - 4 = 19. 19 mod 16 = 3 - begin - mod_detect_reset_time <= 4'd4; - end - else - if (mod_type == `FPGA_HF_ISO14443A_SNIFFER) - begin - // detect a rising edge of reader's signal and sync modulation detector to the tag's answer: - if (~pre_after_hysteresis && after_hysteresis && deep_modulation) - // reader signal rising edge detected at negedge_cnt[3:0]. This signal had been delayed - // 9 ticks by the RF part + 3 ticks by the A/D converter + 1 tick to assign to after_hysteresis. - // Then the same as above. - // - 9 - 3 - 1 + 4 + 3 + 7 - 4 = -3 - begin - mod_detect_reset_time <= negedge_cnt[3:0] - 4'd3; - end - end -end - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// Tag -> PM3: -// modulation detector. Looks for the steepest falling and rising edges within a 16 clock period. If there is both a significant -// falling and rising edge (in any order), a modulation is detected. -reg signed [10:0] rx_mod_falling_edge_max; -reg signed [10:0] rx_mod_rising_edge_max; -reg curbit; - -`define EDGE_DETECT_THRESHOLD 3 -`define EDGE_DETECT_THRESHOLDHIGH 20 - -always @(negedge adc_clk) -begin - if(negedge_cnt[3:0] == mod_detect_reset_time) - begin - if (mod_type == `FPGA_HF_ISO14443A_SNIFFER) - begin - // detect modulation signal: if modulating, there must have been a falling AND a rising edge - if ((rx_mod_falling_edge_max > `EDGE_DETECT_THRESHOLDHIGH) && (rx_mod_rising_edge_max < -`EDGE_DETECT_THRESHOLDHIGH)) - curbit <= 1'b1; // modulation - else - curbit <= 1'b0; // no modulation - end - else - begin - // detect modulation signal: if modulating, there must have been a falling AND a rising edge - if ((rx_mod_falling_edge_max > `EDGE_DETECT_THRESHOLD) && (rx_mod_rising_edge_max < -`EDGE_DETECT_THRESHOLD)) - curbit <= 1'b1; // modulation - else - curbit <= 1'b0; // no modulation - end - // reset modulation detector - rx_mod_rising_edge_max <= 0; - rx_mod_falling_edge_max <= 0; - end - else // look for steepest edges (slopes) - begin - if (adc_d_filtered > 0) - begin - if (adc_d_filtered > rx_mod_falling_edge_max) - rx_mod_falling_edge_max <= adc_d_filtered; - end - else - begin - if (adc_d_filtered < rx_mod_rising_edge_max) - rx_mod_rising_edge_max <= adc_d_filtered; - end - end - -end - - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// Tag+Reader -> PM3 -// sample 4 bits reader data and 4 bits tag data for sniffing -reg [3:0] reader_data; -reg [3:0] tag_data; - -always @(negedge adc_clk) -begin - if(negedge_cnt[3:0] == 4'd0) - begin - reader_data[3:0] <= {reader_data[2:0], after_hysteresis}; - tag_data[3:0] <= {tag_data[2:0], curbit}; - end -end - - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// PM3 -> Reader: -// a delay line to ensure that we send the (emulated) tag's answer at the correct time according to ISO14443-3 -reg [31:0] mod_sig_buf; -reg [4:0] mod_sig_ptr; -reg mod_sig; - -always @(negedge adc_clk) -begin - if(negedge_cnt[3:0] == 4'd0) // sample data at rising edge of ssp_clk - ssp_dout changes at the falling edge. - begin - mod_sig_buf[31:2] <= mod_sig_buf[30:1]; // shift - if (~ssp_dout && ~mod_sig_buf[1]) - mod_sig_buf[1] <= 1'b0; // delete the correction bit (a single 1 preceded and succeeded by 0) - else - mod_sig_buf[1] <= mod_sig_buf[0]; - mod_sig_buf[0] <= ssp_dout; // add new data to the delay line - - mod_sig = mod_sig_buf[mod_sig_ptr]; // the delayed signal. - end -end - - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// PM3 -> Reader, internal timing: -// a timer for the 1172 cycles fdt (Frame Delay Time). Start the timer with a rising edge of the reader's signal. -// set fdt_elapsed when we no longer need to delay data. Set fdt_indicator when we can start sending data. -// Note: the FPGA only takes care for the 1172 delay. To achieve an additional 1236-1172=64 ticks delay, the ARM must send -// a correction bit (before the start bit). The correction bit will be coded as 00010000, i.e. it adds 4 bits to the -// transmission stream, causing the required additional delay. -reg [10:0] fdt_counter; -reg fdt_indicator, fdt_elapsed; -reg [3:0] mod_sig_flip; -reg [3:0] sub_carrier_cnt; - -// we want to achieve a delay of 1172. The RF part already has delayed the reader signals's rising edge -// by 9 ticks, the ADC took 3 ticks and there is always a delay of 32 ticks by the mod_sig_buf. Therefore need to -// count to 1172 - 9 - 3 - 32 = 1128 -`define FDT_COUNT 11'd1128 - -// The ARM must not send too early, otherwise the mod_sig_buf will overflow, therefore signal that we are ready -// with fdt_indicator. The mod_sig_buf can buffer 29 excess data bits, i.e. a maximum delay of 29 * 16 = 464 adc_clk ticks. -// fdt_indicator is assigned to sendbit after at least 1 tick, the transfer to ARM needs minimum 8 ticks. Response from -// ARM could appear at ssp_dout 8 ticks later. -// 1128 - 464 - 1 - 8 - 8 = 647 -`define FDT_INDICATOR_COUNT 11'd647 -// Note: worst case, assignment to sendbit takes 15 ticks more, and transfer to ARM needs 7*16 = 112 ticks more. -// When the ARM's response then appears, the fdt_count is already 647 + 15 + 112 = 774, which still allows the ARM a possible -// response window of 1128 - 774 = 354 ticks. - -// reset on a pause in listen mode. I.e. the counter starts when the pause is over: -assign fdt_reset = ~after_hysteresis && mod_type == `FPGA_HF_ISO14443A_TAGSIM_LISTEN; - -always @(negedge adc_clk) -begin - if (fdt_reset) - begin - fdt_counter <= 11'd0; - fdt_elapsed <= 1'b0; - fdt_indicator <= 1'b0; - end - else - begin - if(fdt_counter == `FDT_COUNT) - begin - if(~fdt_elapsed) // just reached fdt. - begin - mod_sig_flip <= negedge_cnt[3:0]; // start modulation at this time - sub_carrier_cnt <= 4'd0; // subcarrier phase in sync with start of modulation - fdt_elapsed <= 1'b1; - end - else - begin - sub_carrier_cnt <= sub_carrier_cnt + 1; - end - end - else - begin - fdt_counter <= fdt_counter + 1; - end - end - - if(fdt_counter == `FDT_INDICATOR_COUNT) fdt_indicator <= 1'b1; -end - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// PM3 -> Reader or Tag -// assign a modulation signal to the antenna. This signal is either a delayed signal (to achieve fdt when sending to a reader) -// or undelayed when sending to a tag -reg mod_sig_coil; - -always @(negedge adc_clk) -begin - if (mod_type == `FPGA_HF_ISO14443A_TAGSIM_MOD) // need to take care of proper fdt timing - begin - if(fdt_counter == `FDT_COUNT) - begin - if(fdt_elapsed) - begin - if(negedge_cnt[3:0] == mod_sig_flip) mod_sig_coil <= mod_sig; - end - else - begin - mod_sig_coil <= mod_sig; // just reached fdt. Immediately assign signal to coil - end - end - end - else // other modes: don't delay - begin - mod_sig_coil <= ssp_dout; - end -end - - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// PM3 -> Reader -// determine the required delay in the mod_sig_buf (set mod_sig_ptr). -reg temp_buffer_reset; - -always @(negedge adc_clk) -begin - if(fdt_reset) - begin - mod_sig_ptr <= 5'd0; - temp_buffer_reset = 1'b0; - end - else - begin - if(fdt_counter == `FDT_COUNT && ~fdt_elapsed) // if we just reached fdt - if(~(| mod_sig_ptr[4:0])) - mod_sig_ptr <= 5'd8; // ... but didn't buffer a 1 yet, delay next 1 by n*128 ticks. - else - temp_buffer_reset = 1'b1; // else no need for further delays. - - if(negedge_cnt[3:0] == 4'd0) // at rising edge of ssp_clk - ssp_dout changes at the falling edge. - begin - if((ssp_dout || (| mod_sig_ptr[4:0])) && ~fdt_elapsed) // buffer a 1 (and all subsequent data) until fdt is reached. - if (mod_sig_ptr == 5'd31) - mod_sig_ptr <= 5'd0; // buffer overflow - data loss. - else - mod_sig_ptr <= mod_sig_ptr + 1; // increase buffer (= increase delay by 16 adc_clk ticks). mod_sig_ptr always points ahead of first 1. - else if(fdt_elapsed && ~temp_buffer_reset) - begin - // wait for the next 1 after fdt_elapsed before fixing the delay and starting modulation. This ensures that the response can only happen - // at intervals of 8 * 16 = 128 adc_clk ticks (as defined in ISO14443-3) - if(ssp_dout) - temp_buffer_reset = 1'b1; - if(mod_sig_ptr == 5'd1) - mod_sig_ptr <= 5'd8; // still nothing received, need to go for the next interval - else - mod_sig_ptr <= mod_sig_ptr - 1; // decrease buffer. - end - end - end -end - - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// FPGA -> ARM communication: -// buffer 8 bits data to be sent to ARM. Shift them out bit by bit. -reg [7:0] to_arm; - -always @(negedge adc_clk) -begin - if (negedge_cnt[5:0] == 6'd63) // fill the buffer - begin - if (mod_type == `FPGA_HF_ISO14443A_SNIFFER) - begin - if(deep_modulation) // a reader is sending (or there's no field at all) - begin - to_arm <= {reader_data[3:0], 4'b0000}; // don't send tag data - end - else - begin - to_arm <= {reader_data[3:0], tag_data[3:0]}; - end - end - else - begin - to_arm[7:0] <= {mod_sig_ptr[4:0], mod_sig_flip[3:1]}; // feedback timing information - end - end - - if(negedge_cnt[2:0] == 3'b000 && mod_type == `FPGA_HF_ISO14443A_SNIFFER) // shift at double speed - begin - // Don't shift if we just loaded new data, obviously. - if(negedge_cnt[5:0] != 6'd0) - begin - to_arm[7:1] <= to_arm[6:0]; - end - end - - if(negedge_cnt[3:0] == 4'b0000 && mod_type != `FPGA_HF_ISO14443A_SNIFFER) - begin - // Don't shift if we just loaded new data, obviously. - if(negedge_cnt[6:0] != 7'd0) - begin - to_arm[7:1] <= to_arm[6:0]; - end - end - -end - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// FPGA <-> ARM communication: -// generate a ssp clock and ssp frame signal for the synchronous transfer from/to the ARM -reg ssp_clk; -reg ssp_frame; - -always @(negedge adc_clk) -begin - if(mod_type == `FPGA_HF_ISO14443A_SNIFFER) - // FPGA_HF_ISO14443A_SNIFFER mode (ssp_clk = adc_clk / 8, ssp_frame clock = adc_clk / 64)): - begin - if(negedge_cnt[2:0] == 3'd0) - ssp_clk <= 1'b1; - if(negedge_cnt[2:0] == 3'd4) - ssp_clk <= 1'b0; - - if(negedge_cnt[5:0] == 6'd0) // ssp_frame rising edge indicates start of frame - ssp_frame <= 1'b1; - if(negedge_cnt[5:0] == 6'd8) - ssp_frame <= 1'b0; - end - else - // all other modes (ssp_clk = adc_clk / 16, ssp_frame clock = adc_clk / 128): - begin - if(negedge_cnt[3:0] == 4'd0) - ssp_clk <= 1'b1; - if(negedge_cnt[3:0] == 4'd8) - ssp_clk <= 1'b0; - - if(negedge_cnt[6:0] == 7'd7) // ssp_frame rising edge indicates start of frame, sampled on falling edge of ssp_clk - ssp_frame <= 1'b1; - if(negedge_cnt[6:0] == 7'd23) - ssp_frame <= 1'b0; - end -end - - - -//////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// -// FPGA -> ARM communication: -// select the data to be sent to ARM -reg bit_to_arm; -reg sendbit; - -always @(negedge adc_clk) -begin - if(negedge_cnt[3:0] == 4'd0) - begin - // What do we communicate to the ARM - if(mod_type == `FPGA_HF_ISO14443A_TAGSIM_LISTEN) - sendbit = after_hysteresis; - else if(mod_type == `FPGA_HF_ISO14443A_TAGSIM_MOD) - /* if(fdt_counter > 11'd772) sendbit = mod_sig_coil; // huh? - else */ - sendbit = fdt_indicator; - else if (mod_type == `FPGA_HF_ISO14443A_READER_LISTEN) - sendbit = curbit; - else - sendbit = 1'b0; - end - - - if(mod_type == `FPGA_HF_ISO14443A_SNIFFER) - // send sampled reader and tag data: - bit_to_arm = to_arm[7]; - else if (mod_type == `FPGA_HF_ISO14443A_TAGSIM_MOD && fdt_elapsed && temp_buffer_reset) - // send timing information: - bit_to_arm = to_arm[7]; - else - // send data or fdt_indicator - bit_to_arm = sendbit; -end - - - - -assign ssp_din = bit_to_arm; - -// Subcarrier (adc_clk/16, for FPGA_HF_ISO14443A_TAGSIM_MOD only). -wire sub_carrier; -assign sub_carrier = ~sub_carrier_cnt[3]; - -// in FPGA_HF_ISO14443A_READER_MOD: drop carrier for mod_sig_coil==1 (pause); in FPGA_HF_ISO14443A_READER_LISTEN: carrier always on; in other modes: carrier always off -assign pwr_hi = (ck_1356meg & (((mod_type == `FPGA_HF_ISO14443A_READER_MOD) & ~mod_sig_coil) || (mod_type == `FPGA_HF_ISO14443A_READER_LISTEN))); - - -// Enable HF antenna drivers: -assign pwr_oe1 = 1'b0; -assign pwr_oe3 = 1'b0; - -// FPGA_HF_ISO14443A_TAGSIM_MOD: short circuit antenna with different resistances (modulated by sub_carrier modulated by mod_sig_coil) -// for pwr_oe4 = 1 (tristate): antenna load = 10k || 33 = 32,9 Ohms -// for pwr_oe4 = 0 (active): antenna load = 10k || 33 || 33 = 16,5 Ohms -assign pwr_oe4 = mod_sig_coil & sub_carrier & (mod_type == `FPGA_HF_ISO14443A_TAGSIM_MOD); - -// This is all LF, so doesn't matter. -assign pwr_oe2 = 1'b0; -assign pwr_lo = 1'b0; - - -assign dbg = negedge_cnt[3]; - -endmodule diff --git a/fpga-xc3s100e/hi_reader.v b/fpga-xc3s100e/hi_reader.v deleted file mode 100644 index c5ffa7b85..000000000 --- a/fpga-xc3s100e/hi_reader.v +++ /dev/null @@ -1,335 +0,0 @@ -//----------------------------------------------------------------------------- -// -// Jonathan Westhues, April 2006 -//----------------------------------------------------------------------------- - -module hi_reader( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, - subcarrier_frequency, minor_mode -); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [1:0] subcarrier_frequency; - input [3:0] minor_mode; - -assign adc_clk = ck_1356meg; // sample frequency is 13,56 MHz - -// 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, after_hysteresis_prev_prev; -reg [11:0] has_been_low_for; -always @(negedge adc_clk) -begin - if (& adc_d[7:0]) after_hysteresis <= 1'b1; - else if (~(| adc_d[7:0])) after_hysteresis <= 1'b0; - - if (after_hysteresis) - begin - has_been_low_for <= 12'd0; - end - else - begin - if (has_been_low_for == 12'd4095) - begin - has_been_low_for <= 12'd0; - after_hysteresis <= 1'b1; - end - else - has_been_low_for <= has_been_low_for + 1; - end -end - - -// Let us report a correlation every 64 samples. I.e. -// one Q/I pair after 4 subcarrier cycles for the 848kHz subcarrier, -// one Q/I pair after 2 subcarrier cycles for the 424kHz subcarriers, -// one Q/I pair for each subcarrier cyle for the 212kHz subcarrier. -// We need a 6-bit counter for the timing. -reg [5:0] corr_i_cnt; -always @(negedge adc_clk) -begin - corr_i_cnt <= corr_i_cnt + 1; -end - - -// A couple of registers in which to accumulate the correlations. From the 64 samples -// we would add at most 32 times the difference between unmodulated and modulated signal. It should -// be safe to assume that a tag will not be able to modulate the carrier signal by more than 25%. -// 32 * 255 * 0,25 = 2040, which can be held in 11 bits. Add 1 bit for sign. -// Temporary we might need more bits. For the 212kHz subcarrier we could possible add 32 times the -// maximum signal value before a first subtraction would occur. 32 * 255 = 8160 can be held in 13 bits. -// Add one bit for sign -> need 14 bit registers but final result will fit into 12 bits. -reg signed [13:0] corr_i_accum; -reg signed [13:0] corr_q_accum; -// we will report maximum 8 significant bits -reg signed [7:0] corr_i_out; -reg signed [7:0] corr_q_out; - - -// the amplitude of the subcarrier is sqrt(ci^2 + cq^2). -// approximate by amplitude = max(|ci|,|cq|) + 1/2*min(|ci|,|cq|) -reg [13:0] corr_amplitude, abs_ci, abs_cq, max_ci_cq; -reg [12:0] min_ci_cq_2; // min_ci_cq / 2 - -always @(*) -begin - if (corr_i_accum[13] == 1'b0) - abs_ci <= corr_i_accum; - else - abs_ci <= -corr_i_accum; - - if (corr_q_accum[13] == 1'b0) - abs_cq <= corr_q_accum; - else - abs_cq <= -corr_q_accum; - - if (abs_ci > abs_cq) - begin - max_ci_cq <= abs_ci; - min_ci_cq_2 <= abs_cq / 2; - end - else - begin - max_ci_cq <= abs_cq; - min_ci_cq_2 <= abs_ci / 2; - end - - corr_amplitude <= max_ci_cq + min_ci_cq_2; - -end - - -// The subcarrier reference signals -reg subcarrier_I; -reg subcarrier_Q; - -always @(*) -begin - if (subcarrier_frequency == `FPGA_HF_READER_SUBCARRIER_848_KHZ) - begin - subcarrier_I = ~corr_i_cnt[3]; - subcarrier_Q = ~(corr_i_cnt[3] ^ corr_i_cnt[2]); - end - else if (subcarrier_frequency == `FPGA_HF_READER_SUBCARRIER_212_KHZ) - begin - subcarrier_I = ~corr_i_cnt[5]; - subcarrier_Q = ~(corr_i_cnt[5] ^ corr_i_cnt[4]); - end - else - begin // 424 kHz - subcarrier_I = ~corr_i_cnt[4]; - subcarrier_Q = ~(corr_i_cnt[4] ^ corr_i_cnt[3]); - end -end - - -// ADC data appears on the rising edge, so sample it on the falling edge -always @(negedge adc_clk) -begin - // These are the correlators: we correlate against in-phase and quadrature - // versions of our reference signal, and keep the (signed) results or the - // resulting amplitude to send out later over the SSP. - if (corr_i_cnt == 6'd0) - begin - if (minor_mode == `FPGA_HF_READER_MODE_SNIFF_AMPLITUDE) - begin - // send amplitude plus 2 bits reader signal - corr_i_out <= corr_amplitude[13:6]; - corr_q_out <= {corr_amplitude[5:0], after_hysteresis_prev_prev, after_hysteresis_prev}; - end - else if (minor_mode == `FPGA_HF_READER_MODE_SNIFF_IQ) - begin - - // Send 7 most significant bits of in phase tag signal (signed), plus 1 bit reader signal - if (corr_i_accum[13:11] == 3'b000 || corr_i_accum[13:11] == 3'b111) - corr_i_out <= {corr_i_accum[11:5], after_hysteresis_prev_prev}; - else // truncate to maximum value - if (corr_i_accum[13] == 1'b0) - corr_i_out <= {7'b0111111, after_hysteresis_prev_prev}; - else - corr_i_out <= {7'b1000000, after_hysteresis_prev_prev}; - - // Send 7 most significant bits of quadrature phase tag signal (signed), plus 1 bit reader signal - if (corr_q_accum[13:11] == 3'b000 || corr_q_accum[13:11] == 3'b111) - corr_q_out <= {corr_q_accum[11:5], after_hysteresis_prev}; - else // truncate to maximum value - if (corr_q_accum[13] == 1'b0) - corr_q_out <= {7'b0111111, after_hysteresis_prev}; - else - corr_q_out <= {7'b1000000, after_hysteresis_prev}; - end - else if (minor_mode == `FPGA_HF_READER_MODE_RECEIVE_AMPLITUDE) - begin - // send amplitude - corr_i_out <= {2'b00, corr_amplitude[13:8]}; - corr_q_out <= corr_amplitude[7:0]; - end - else if (minor_mode == `FPGA_HF_READER_MODE_RECEIVE_IQ) - begin - - // Send 8 bits of in phase tag signal - if (corr_i_accum[13:11] == 3'b000 || corr_i_accum[13:11] == 3'b111) - corr_i_out <= corr_i_accum[11:4]; - else // truncate to maximum value - if (corr_i_accum[13] == 1'b0) - corr_i_out <= 8'b01111111; - else - corr_i_out <= 8'b10000000; - - // Send 8 bits of quadrature phase tag signal - if (corr_q_accum[13:11] == 3'b000 || corr_q_accum[13:11] == 3'b111) - corr_q_out <= corr_q_accum[11:4]; - else // truncate to maximum value - if (corr_q_accum[13] == 1'b0) - corr_q_out <= 8'b01111111; - else - corr_q_out <= 8'b10000000; - end - - // for each Q/I pair report two reader signal samples when sniffing. Store the 1st. - after_hysteresis_prev_prev <= after_hysteresis; - - // Initialize next correlation. - // Both I and Q reference signals are high when corr_i_nct == 0. Therefore need to accumulate. - corr_i_accum <= $signed({1'b0, adc_d}); - corr_q_accum <= $signed({1'b0, adc_d}); - end - else - begin - if (subcarrier_I) - corr_i_accum <= corr_i_accum + $signed({1'b0, adc_d}); - else - corr_i_accum <= corr_i_accum - $signed({1'b0, adc_d}); - - if (subcarrier_Q) - corr_q_accum <= corr_q_accum + $signed({1'b0, adc_d}); - else - corr_q_accum <= corr_q_accum - $signed({1'b0, adc_d}); - end - - // for each Q/I pair report two reader signal samples when sniffing. Store the 2nd. - 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. - // We get one report each cycle, and each report is 16 bits, so the - // ssp_clk should be the adc_clk divided by 64/16 = 4. - // ssp_clk frequency = 13,56MHz / 4 = 3.39MHz - - if (corr_i_cnt[1:0] == 2'b00) - begin - // Don't shift if we just loaded new data, obviously. - if (corr_i_cnt != 6'd0) - begin - corr_i_out[7:0] <= {corr_i_out[6:0], corr_q_out[7]}; - corr_q_out[7:1] <= corr_q_out[6:0]; - end - end - -end - - -// ssp clock and frame signal for communication to and from ARM -// _____ _____ _____ _ -// ssp_clk | |_____| |_____| |_____| -// _____ -// ssp_frame ___| |____________________________ -// ___________ ___________ ___________ _ -// ssp_d_in X___________X___________X___________X_ -// -// corr_i_cnt 0 1 2 3 4 5 6 7 8 9 10 11 12 ... -// - -reg ssp_clk; -reg ssp_frame; - -always @(negedge adc_clk) -begin - if (corr_i_cnt[1:0] == 2'b00) - ssp_clk <= 1'b1; - - if (corr_i_cnt[1:0] == 2'b10) - ssp_clk <= 1'b0; - - // set ssp_frame signal for corr_i_cnt = 1..3 - // (send one frame with 16 Bits) - if (corr_i_cnt == 6'd1) - ssp_frame <= 1'b1; - - if (corr_i_cnt == 6'd3) - ssp_frame <= 1'b0; -end - - -assign ssp_din = corr_i_out[7]; - - -// a jamming signal -reg jam_signal; -reg [3:0] jam_counter; - -always @(negedge adc_clk) -begin - if (corr_i_cnt == 6'd0) - begin - jam_counter <= jam_counter + 1; - jam_signal <= jam_counter[1] ^ jam_counter[3]; - end -end - -// Antenna drivers -reg pwr_hi, pwr_oe4; - -always @(*) -begin - if (minor_mode == `FPGA_HF_READER_MODE_SEND_SHALLOW_MOD) - begin - pwr_hi = ck_1356meg; - pwr_oe4 = ssp_dout; - end - else if (minor_mode == `FPGA_HF_READER_MODE_SEND_FULL_MOD) - begin - pwr_hi = ck_1356meg & ~ssp_dout; - pwr_oe4 = 1'b0; - end - else if (minor_mode == `FPGA_HF_READER_MODE_SEND_JAM) - begin - pwr_hi = ck_1356meg & jam_signal; - pwr_oe4 = 1'b0; - end - else if (minor_mode == `FPGA_HF_READER_MODE_SNIFF_IQ - || minor_mode == `FPGA_HF_READER_MODE_SNIFF_AMPLITUDE - || minor_mode == `FPGA_HF_READER_MODE_SNIFF_PHASE) - begin // all off - pwr_hi = 1'b0; - pwr_oe4 = 1'b0; - end - else // receiving from tag - begin - pwr_hi = ck_1356meg; - pwr_oe4 = 1'b0; - end -end - -// always on -assign pwr_oe1 = 1'b0; -assign pwr_oe3 = 1'b0; - -// Unused. -assign pwr_lo = 1'b0; -assign pwr_oe2 = 1'b0; - -// Debug Output -assign dbg = corr_i_cnt[3]; - -endmodule diff --git a/fpga-xc3s100e/hi_simulate.v b/fpga-xc3s100e/hi_simulate.v deleted file mode 100644 index cf951279a..000000000 --- a/fpga-xc3s100e/hi_simulate.v +++ /dev/null @@ -1,152 +0,0 @@ -//----------------------------------------------------------------------------- -// Pretend to be an ISO 14443 tag. We will do this by alternately short- -// circuiting and open-circuiting the antenna coil, with the tri-state -// pins. -// -// We communicate over the SSP, as a bitstream (i.e., might as well be -// unframed, though we still generate the word sync signal). The output -// (ARM -> FPGA) tells us whether to modulate or not. The input (FPGA -// -> ARM) is us using the A/D as a fancy comparator; this is with -// (software-added) hysteresis, to undo the high-pass filter. -// -// At this point only Type A is implemented. This means that we are using a -// bit rate of 106 kbit/s, or fc/128. Oversample by 4, which ought to make -// things practical for the ARM (fc/32, 423.8 kbits/s, ~50 kbytes/s) -// -// Jonathan Westhues, October 2006 -//----------------------------------------------------------------------------- - -//For ISE 10.1 PROJ,IDE cannot apply definition to all files -`include "define.v" - - -module hi_simulate( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, - mod_type -); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [3:0] mod_type; - -// Power amp goes between LOW and tri-state, so pwr_hi (and pwr_lo) can -// always be low. -assign pwr_hi = 1'b0; // HF antenna connected to GND -assign pwr_lo = 1'b0; // LF antenna connected to GND - -// This one is all LF, so doesn't matter -assign pwr_oe2 = 1'b0; - -assign adc_clk = ck_1356meg; -assign dbg = ssp_frame; - -// The comparator with hysteresis on the output from the peak detector. -reg after_hysteresis; -reg [11:0] has_been_low_for; - -always @(negedge adc_clk) -begin - if (& adc_d[7:5]) after_hysteresis <= 1'b1; // if (adc_d >= 224) - else if (~(| adc_d[7:5])) after_hysteresis <= 1'b0; // if (adc_d <= 31) - - if (adc_d >= 224) - begin - has_been_low_for <= 12'd0; - end - else - begin - if (has_been_low_for == 12'd4095) - begin - has_been_low_for <= 12'd0; - after_hysteresis <= 1'b1; - end - else - begin - has_been_low_for <= has_been_low_for + 1; - end - end -end - - -// Divide 13.56 MHz to produce various frequencies for SSP_CLK -// and modulation. -reg [8:0] ssp_clk_divider; - -always @(negedge adc_clk) - ssp_clk_divider <= (ssp_clk_divider + 1); - -reg ssp_clk; - -always @(negedge adc_clk) -begin - if (mod_type == `FPGA_HF_SIMULATOR_MODULATE_424K_8BIT) - // Get bit every at 53KHz (every 8th carrier bit of 424kHz) - ssp_clk <= ~ssp_clk_divider[7]; - else if (mod_type == `FPGA_HF_SIMULATOR_MODULATE_212K) - // Get next bit at 212kHz - ssp_clk <= ~ssp_clk_divider[5]; - else - // Get next bit at 424kHz - ssp_clk <= ~ssp_clk_divider[4]; -end - - -// Produce the byte framing signal; the phase of this signal -// is arbitrary, because it's just a bit stream in this module. -reg ssp_frame; -always @(negedge adc_clk) -begin - if (mod_type == `FPGA_HF_SIMULATOR_MODULATE_212K) - begin - if (ssp_clk_divider[8:5] == 4'd1) - ssp_frame <= 1'b1; - if (ssp_clk_divider[8:5] == 4'd5) - ssp_frame <= 1'b0; - end - else - begin - if (ssp_clk_divider[7:4] == 4'd1) - ssp_frame <= 1'b1; - if (ssp_clk_divider[7:4] == 4'd5) - ssp_frame <= 1'b0; - end -end - - -// Synchronize up the after-hysteresis signal, to produce DIN. -reg ssp_din; -always @(posedge ssp_clk) - ssp_din = after_hysteresis; - -// Modulating carrier frequency is fc/64 (212kHz) to fc/16 (848kHz). Reuse ssp_clk divider for that. -reg modulating_carrier; -always @(*) - if(mod_type == `FPGA_HF_SIMULATOR_NO_MODULATION) - modulating_carrier <= 1'b0; // no modulation - else if(mod_type == `FPGA_HF_SIMULATOR_MODULATE_BPSK) - modulating_carrier <= ssp_dout ^ ssp_clk_divider[3]; // XOR means BPSK - else if(mod_type == `FPGA_HF_SIMULATOR_MODULATE_212K) - modulating_carrier <= ssp_dout & ssp_clk_divider[5]; // switch 212kHz subcarrier on/off - else if(mod_type == `FPGA_HF_SIMULATOR_MODULATE_424K || mod_type == `FPGA_HF_SIMULATOR_MODULATE_424K_8BIT) - modulating_carrier <= ssp_dout & ssp_clk_divider[4]; // switch 424kHz modulation on/off - else - modulating_carrier <= 1'b0; // yet unused - - - -// Load modulation. Toggle only one of these, since we are already producing much deeper -// modulation than a real tag would. -assign pwr_oe1 = 1'b0; // 33 Ohms Load -assign pwr_oe4 = modulating_carrier; // 33 Ohms Load -// This one is always on, so that we can watch the carrier. -assign pwr_oe3 = 1'b0; // 10k Load - -endmodule diff --git a/fpga-xc3s100e/hi_sniffer.v b/fpga-xc3s100e/hi_sniffer.v deleted file mode 100644 index c2dc844a7..000000000 --- a/fpga-xc3s100e/hi_sniffer.v +++ /dev/null @@ -1,50 +0,0 @@ -module hi_sniffer( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_clk -); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - output ssp_frame, ssp_din, ssp_clk; - -// We are only snooping, all off. -assign pwr_hi = 1'b0; -assign pwr_lo = 1'b0; -assign pwr_oe1 = 1'b0; -assign pwr_oe2 = 1'b0; -assign pwr_oe3 = 1'b0; -assign pwr_oe4 = 1'b0; - -reg ssp_frame; -reg [7:0] adc_d_out = 8'd0; -reg [2:0] ssp_cnt = 3'd0; - -assign adc_clk = ck_1356meg; -assign ssp_clk = ~ck_1356meg; - -always @(posedge ssp_clk) -begin - if(ssp_cnt[2:0] == 3'd7) - ssp_cnt[2:0] <= 3'd0; - else - ssp_cnt <= ssp_cnt + 1; - - if(ssp_cnt[2:0] == 3'b000) // set frame length - begin - adc_d_out[7:0] <= adc_d; - ssp_frame <= 1'b1; - end - else - begin - adc_d_out[7:0] <= {1'b0, adc_d_out[7:1]}; - ssp_frame <= 1'b0; - end - -end - -assign ssp_din = adc_d_out[0]; - -endmodule diff --git a/fpga-xc3s100e/iseproj/fpga_hf/fpga_hf.ise b/fpga-xc3s100e/iseproj/fpga_hf/fpga_hf.ise deleted file mode 100644 index 40e5eeffd..000000000 Binary files a/fpga-xc3s100e/iseproj/fpga_hf/fpga_hf.ise and /dev/null differ diff --git a/fpga-xc3s100e/iseproj/fpga_hf/fpga_hf.tcl b/fpga-xc3s100e/iseproj/fpga_hf/fpga_hf.tcl deleted file mode 100644 index 114f0df18..000000000 --- a/fpga-xc3s100e/iseproj/fpga_hf/fpga_hf.tcl +++ /dev/null @@ -1,479 +0,0 @@ -# -# Project automation script for fpga_hf -# -# Created for ISE version 10.1 -# -# This file contains several Tcl procedures (procs) that you can use to automate -# your project by running from xtclsh or the Project Navigator Tcl console. -# If you load this file (using the Tcl command: source fpga_hf.tcl, then you can -# run any of the procs included here. -# You may also edit any of these procs to customize them. See comments in each -# proc for more instructions. -# -# This file contains the following procedures: -# -# Top Level procs (meant to be called directly by the user): -# run_process: you can use this top-level procedure to run any processes -# that you choose to by adding and removing comments, or by -# adding new entries. -# rebuild_project: you can alternatively use this top-level procedure -# to recreate your entire project, and the run selected processes. -# -# Lower Level (helper) procs (called under in various cases by the top level procs): -# show_help: print some basic information describing how this script works -# add_source_files: adds the listed source files to your project. -# set_project_props: sets the project properties that were in effect when this -# script was generated. -# create_libraries: creates and adds file to VHDL libraries that were defined when -# this script was generated. -# create_partitions: adds any partitions that were defined when this script was generated. -# set_process_props: set the process properties as they were set for your project -# when this script was generated. -# - -set myProject "fpga_hf.ise" -set myScript "fpga_hf.tcl" - -# -# Main (top-level) routines -# - -# -# run_process -# This procedure is used to run processes on an existing project. You may comment or -# uncomment lines to control which processes are run. This routine is set up to run -# the Implement Design and Generate Programming File processes by default. This proc -# also sets process properties as specified in the "set_process_props" proc. Only -# those properties which have values different from their current settings in the project -# file will be modified in the project. -# -proc run_process {} { - - global myScript - global myProject - - ## put out a 'heartbeat' - so we know something's happening. - puts "\n$myScript: running ($myProject)...\n" - - if { ! [ open_project ] } { - return false - } - - set_process_props - # - # Remove the comment characters (#'s) to enable the following commands - # process run "Synthesize" - # process run "Translate" - # process run "Map" - # process run "Place & Route" - # - puts "Running 'Implement Design'" - if { ! [ process run "Implement Design" ] } { - puts "$myScript: Implementation run failed, check run output for details." - project close - return - } - puts "Running 'Generate Programming File'" - if { ! [ process run "Generate Programming File" ] } { - puts "$myScript: Generate Programming File run failed, check run output for details." - project close - return - } - - puts "Run completed." - project close - -} - -# -# rebuild_project -# -# This procedure renames the project file (if it exists) and recreates the project. -# It then sets project properties and adds project sources as specified by the -# set_project_props and add_source_files support procs. It recreates VHDL libraries -# and partitions as they existed at the time this script was generated. -# -# It then calls run_process to set process properties and run selected processes. -# -proc rebuild_project {} { - - global myScript - global myProject - - ## put out a 'heartbeat' - so we know something's happening. - puts "\n$myScript: rebuilding ($myProject)...\n" - - if { [ file exists $myProject ] } { - puts "$myScript: Removing existing project file." - file delete $myProject - } - - puts "$myScript: Rebuilding project $myProject" - project new $myProject - set_project_props - add_source_files - create_libraries - create_partitions - puts "$myScript: project rebuild completed." - - run_process - -} - -# -# Support Routines -# - -# -# show_help: print information to help users understand the options available when -# running this script. -# -proc show_help {} { - - global myScript - - puts "" - puts "usage: xtclsh $myScript " - puts " or you can run xtclsh and then enter 'source $myScript'." - puts "" - puts "options:" - puts " run_process - set properties and run processes." - puts " rebuild_project - rebuild the project from scratch and run processes." - puts " set_project_props - set project properties (device, speed, etc.)" - puts " add_source_files - add source files" - puts " create_libraries - create vhdl libraries" - puts " create_partitions - create partitions" - puts " set_process_props - set process property values" - puts " show_help - print this message" - puts "" -} - -proc open_project {} { - - global myScript - global myProject - - if { ! [ file exists $myProject ] } { - ## project file isn't there, rebuild it. - puts "Project $myProject not found. Use ${myProject}_rebuild to recreate it." - return false - } - - project open $myProject - - return true - -} -# -# set_project_props -# -# This procedure sets the project properties as they were set in the project -# at the time this script was generated. -# -proc set_project_props {} { - - global myScript - - if { ! [ open_project ] } { - return false - } - - puts "$myScript: Setting project properties..." - - project set family "Spartan3E" - project set device "xc3s100e" - project set package "vq100" - project set speed "-4" - project set top_level_module_type "HDL" - project set synthesis_tool "XST (VHDL/Verilog)" - project set simulator "ISE Simulator (VHDL/Verilog)" - project set "Preferred Language" "Verilog" - project set "Enable Message Filtering" "false" - project set "Display Incremental Messages" "false" - -} - - -# -# add_source_files -# -# This procedure add the source files that were known to the project at the -# time this script was generated. -# -proc add_source_files {} { - - global myScript - - if { ! [ open_project ] } { - return false - } - - puts "$myScript: Adding sources to project..." - - xfile add "../../clk_divider.v" - xfile add "../../define.v" - xfile add "../../fpga.ucf" - xfile add "../../fpga_allinone.v" - xfile add "../../fpga_hfmod.v" - xfile add "../../fpga_lfmod.v" - xfile add "../../hi_flite.v" - xfile add "../../hi_get_trace.v" - xfile add "../../hi_iso14443a.v" - xfile add "../../hi_reader.v" - xfile add "../../hi_simulate.v" - xfile add "../../hi_sniffer.v" - xfile add "../../lf_edge_detect.v" - xfile add "../../lo_adc.v" - xfile add "../../lo_edge_detect.v" - xfile add "../../lo_passthru.v" - xfile add "../../lo_read.v" - xfile add "../../lp20khz_1MSa_iir_filter.v" - xfile add "../../mux2_onein.v" - xfile add "../../mux2_oneout.v" - xfile add "../../util.v" - - # Set the Top Module as well... - project set top "fpga_hf" - - puts "$myScript: project sources reloaded." - -} ; # end add_source_files - -# -# create_libraries -# -# This procedure defines VHDL libraries and associates files with those libraries. -# It is expected to be used when recreating the project. Any libraries defined -# when this script was generated are recreated by this procedure. -# -proc create_libraries {} { - - global myScript - - if { ! [ open_project ] } { - return false - } - - puts "$myScript: Creating libraries..." - - - # must close the project or library definitions aren't saved. - project close - -} ; # end create_libraries - -# -# create_partitions -# -# This procedure creates partitions on instances in your project. -# It is expected to be used when recreating the project. Any partitions -# defined when this script was generated are recreated by this procedure. -# -proc create_partitions {} { - - global myScript - - if { ! [ open_project ] } { - return false - } - - puts "$myScript: Creating Partitions..." - - - # must close the project or partition definitions aren't saved. - project close - -} ; # end create_partitions - -# -# set_process_props -# -# This procedure sets properties as requested during script generation (either -# all of the properties, or only those modified from their defaults). -# -proc set_process_props {} { - - global myScript - - if { ! [ open_project ] } { - return false - } - - puts "$myScript: setting process properties..." - - project set "Compiled Library Directory" "\$XILINX//" - project set "Use SmartGuide" "false" - project set "SmartGuide Filename" "fpga_hf_guide.ncd" - project set "Multiplier Style" "Auto" -process "Synthesize - XST" - project set "Configuration Rate" "Default (1)" -process "Generate Programming File" - project set "Map to Input Functions" "4" -process "Map" - project set "Number of Clock Buffers" "24" -process "Synthesize - XST" - project set "Max Fanout" "500" -process "Synthesize - XST" - project set "Case Implementation Style" "None" -process "Synthesize - XST" - project set "Decoder Extraction" "true" -process "Synthesize - XST" - project set "Priority Encoder Extraction" "Yes" -process "Synthesize - XST" - project set "Mux Extraction" "Yes" -process "Synthesize - XST" - project set "RAM Extraction" "true" -process "Synthesize - XST" - project set "ROM Extraction" "true" -process "Synthesize - XST" - project set "FSM Encoding Algorithm" "Auto" -process "Synthesize - XST" - project set "Logical Shifter Extraction" "true" -process "Synthesize - XST" - project set "Optimization Goal" "Speed" -process "Synthesize - XST" - project set "Optimization Effort" "Normal" -process "Synthesize - XST" - project set "Resource Sharing" "true" -process "Synthesize - XST" - project set "Shift Register Extraction" "true" -process "Synthesize - XST" - project set "XOR Collapsing" "true" -process "Synthesize - XST" - project set "Other Bitgen Command Line Options" "" -process "Generate Programming File" - project set "Show All Models" "false" -process "Generate IBIS Model" - project set "Target UCF File Name" "" -process "Back-annotate Pin Locations" - project set "Ignore User Timing Constraints" "false" -process "Map" - project set "Use RLOC Constraints" "true" -process "Map" - project set "Other Map Command Line Options" "" -process "Map" - project set "Use LOC Constraints" "true" -process "Translate" - project set "Other Ngdbuild Command Line Options" "" -process "Translate" - project set "Ignore User Timing Constraints" "false" -process "Place & Route" - project set "Other Place & Route Command Line Options" "" -process "Place & Route" - project set "UserID Code (8 Digit Hexadecimal)" "0xFFFFFFFF" -process "Generate Programming File" - project set "Reset DCM if SHUTDOWN & AGHIGH performed" "false" -process "Generate Programming File" - project set "Configuration Pin Done" "Pull Up" -process "Generate Programming File" - project set "Create ASCII Configuration File" "false" -process "Generate Programming File" - project set "Create Binary Configuration File" "false" -process "Generate Programming File" - project set "Create Bit File" "true" -process "Generate Programming File" - project set "Enable BitStream Compression" "false" -process "Generate Programming File" - project set "Run Design Rules Checker (DRC)" "true" -process "Generate Programming File" - project set "Enable Cyclic Redundancy Checking (CRC)" "true" -process "Generate Programming File" - project set "Create IEEE 1532 Configuration File" "false" -process "Generate Programming File" - project set "Configuration Pin Program" "Pull Up" -process "Generate Programming File" - project set "JTAG Pin TCK" "Pull Up" -process "Generate Programming File" - project set "JTAG Pin TDI" "Pull Up" -process "Generate Programming File" - project set "JTAG Pin TDO" "Pull Up" -process "Generate Programming File" - project set "JTAG Pin TMS" "Pull Up" -process "Generate Programming File" - project set "Unused IOB Pins" "Pull Down" -process "Generate Programming File" - project set "Security" "Enable Readback and Reconfiguration" -process "Generate Programming File" - project set "FPGA Start-Up Clock" "CCLK" -process "Generate Programming File" - project set "Done (Output Events)" "Default (4)" -process "Generate Programming File" - project set "Drive Done Pin High" "false" -process "Generate Programming File" - project set "Enable Outputs (Output Events)" "Default (5)" -process "Generate Programming File" - project set "Release DLL (Output Events)" "Default (NoWait)" -process "Generate Programming File" - project set "Release Write Enable (Output Events)" "Default (6)" -process "Generate Programming File" - project set "Enable Internal Done Pipe" "false" -process "Generate Programming File" - project set "Allow Logic Optimization Across Hierarchy" "false" -process "Map" - project set "Optimization Strategy (Cover Mode)" "Area" -process "Map" - project set "Disable Register Ordering" "false" -process "Map" - project set "Pack I/O Registers/Latches into IOBs" "Off" -process "Map" - project set "Replicate Logic to Allow Logic Level Reduction" "true" -process "Map" - project set "Generate Detailed MAP Report" "false" -process "Map" - project set "Map Slice Logic into Unused Block RAMs" "false" -process "Map" - project set "Perform Timing-Driven Packing and Placement" "false" -process "Map" - project set "Trim Unconnected Signals" "true" -process "Map" - project set "Create I/O Pads from Ports" "false" -process "Translate" - project set "Macro Search Path" "" -process "Translate" - project set "Netlist Translation Type" "Timestamp" -process "Translate" - project set "User Rules File for Netlister Launcher" "" -process "Translate" - project set "Allow Unexpanded Blocks" "false" -process "Translate" - project set "Allow Unmatched LOC Constraints" "false" -process "Translate" - project set "Starting Placer Cost Table (1-100)" "1" -process "Place & Route" - project set "Placer Effort Level (Overrides Overall Level)" "None" -process "Place & Route" - project set "Router Effort Level (Overrides Overall Level)" "None" -process "Place & Route" - project set "Place And Route Mode" "Normal Place and Route" -process "Place & Route" - project set "Use Bonded I/Os" "false" -process "Place & Route" - project set "Add I/O Buffers" "true" -process "Synthesize - XST" - project set "Global Optimization Goal" "AllClockNets" -process "Synthesize - XST" - project set "Keep Hierarchy" "No" -process "Synthesize - XST" - project set "Register Balancing" "No" -process "Synthesize - XST" - project set "Register Duplication" "true" -process "Synthesize - XST" - project set "Asynchronous To Synchronous" "false" -process "Synthesize - XST" - project set "Automatic BRAM Packing" "false" -process "Synthesize - XST" - project set "BRAM Utilization Ratio" "100" -process "Synthesize - XST" - project set "Bus Delimiter" "<>" -process "Synthesize - XST" - project set "Case" "Maintain" -process "Synthesize - XST" - project set "Cores Search Directories" "" -process "Synthesize - XST" - project set "Cross Clock Analysis" "false" -process "Synthesize - XST" - project set "Equivalent Register Removal" "true" -process "Synthesize - XST" - project set "FSM Style" "LUT" -process "Synthesize - XST" - project set "Generate RTL Schematic" "Yes" -process "Synthesize - XST" - project set "Generics, Parameters" "" -process "Synthesize - XST" - project set "Hierarchy Separator" "/" -process "Synthesize - XST" - project set "HDL INI File" "" -process "Synthesize - XST" - project set "Library Search Order" "" -process "Synthesize - XST" - project set "Netlist Hierarchy" "As Optimized" -process "Synthesize - XST" - project set "Optimize Instantiated Primitives" "false" -process "Synthesize - XST" - project set "Pack I/O Registers into IOBs" "Auto" -process "Synthesize - XST" - project set "Read Cores" "true" -process "Synthesize - XST" - project set "Slice Packing" "true" -process "Synthesize - XST" - project set "Slice Utilization Ratio" "100" -process "Synthesize - XST" - project set "Use Clock Enable" "Yes" -process "Synthesize - XST" - project set "Use Synchronous Reset" "Yes" -process "Synthesize - XST" - project set "Use Synchronous Set" "Yes" -process "Synthesize - XST" - project set "Use Synthesis Constraints File" "true" -process "Synthesize - XST" - project set "Custom Compile File List" "" -process "Synthesize - XST" - project set "Verilog Include Directories" "" -process "Synthesize - XST" - project set "Verilog 2001" "true" -process "Synthesize - XST" - project set "Verilog Macros" "" -process "Synthesize - XST" - project set "Work Directory" "./xst" -process "Synthesize - XST" - project set "Write Timing Constraints" "false" -process "Synthesize - XST" - project set "Other XST Command Line Options" "" -process "Synthesize - XST" - project set "Map Effort Level" "Medium" -process "Map" - project set "Combinatorial Logic Optimization" "false" -process "Map" - project set "Starting Placer Cost Table (1-100)" "1" -process "Map" - project set "Power Reduction" "false" -process "Map" - project set "Register Duplication" "false" -process "Map" - project set "Synthesis Constraints File" "" -process "Synthesize - XST" - project set "Mux Style" "Auto" -process "Synthesize - XST" - project set "RAM Style" "Auto" -process "Synthesize - XST" - project set "Timing Mode" "Non Timing Driven" -process "Map" - project set "Generate Asynchronous Delay Report" "false" -process "Place & Route" - project set "Generate Clock Region Report" "false" -process "Place & Route" - project set "Generate Post-Place & Route Simulation Model" "false" -process "Place & Route" - project set "Generate Post-Place & Route Static Timing Report" "true" -process "Place & Route" - project set "Nodelist File (Unix Only)" "" -process "Place & Route" - project set "Number of PAR Iterations (0-100)" "3" -process "Place & Route" - project set "Save Results in Directory (.dir will be appended)" "" -process "Place & Route" - project set "Number of Results to Save (0-100)" "" -process "Place & Route" - project set "Power Reduction" "false" -process "Place & Route" - project set "Timing Mode" "Performance Evaluation" -process "Place & Route" - project set "Enable Debugging of Serial Mode BitStream" "false" -process "Generate Programming File" - project set "CLB Pack Factor Percentage" "100" -process "Map" - project set "Place & Route Effort Level (Overall)" "Standard" -process "Place & Route" - project set "Move First Flip-Flop Stage" "true" -process "Synthesize - XST" - project set "Move Last Flip-Flop Stage" "true" -process "Synthesize - XST" - project set "ROM Style" "Auto" -process "Synthesize - XST" - project set "Safe Implementation" "No" -process "Synthesize - XST" - project set "Extra Effort" "None" -process "Map" - project set "Power Activity File" "" -process "Map" - project set "Power Activity File" "" -process "Place & Route" - project set "Extra Effort (Highest PAR level only)" "None" -process "Place & Route" - - puts "$myScript: project property values set." - -} ; # end set_process_props - -proc main {} { - - if { [llength $::argv] == 0 } { - show_help - return true - } - - foreach option $::argv { - switch $option { - "show_help" { show_help } - "run_process" { run_process } - "rebuild_project" { rebuild_project } - "set_project_props" { set_project_props } - "add_source_files" { add_source_files } - "create_libraries" { create_libraries } - "create_partitions" { create_partitions } - "set_process_props" { set_process_props } - default { puts "unrecognized option: $option"; show_help } - } - } -} - -if { $tcl_interactive } { - show_help -} else { - if {[catch {main} result]} { - puts "$myScript failed: $result." - } -} - diff --git a/fpga-xc3s100e/lf_edge_detect.v b/fpga-xc3s100e/lf_edge_detect.v deleted file mode 100644 index d086f95fc..000000000 --- a/fpga-xc3s100e/lf_edge_detect.v +++ /dev/null @@ -1,77 +0,0 @@ -//----------------------------------------------------------------------------- -// Copyright (C) 2014 iZsh -// -// This code is licensed to you under the terms of the GNU GPL, version 2 or, -// at your option, any later version. See the LICENSE.txt file for the text of -// the license. -//----------------------------------------------------------------------------- -// input clk is 24MHz -`include "min_max_tracker.v" - -module lf_edge_detect(input clk, input [7:0] adc_d, input [7:0] lf_ed_threshold, - output [7:0] max, output [7:0] min, - output [7:0] high_threshold, output [7:0] highz_threshold, - output [7:0] lowz_threshold, output [7:0] low_threshold, - output edge_state, output edge_toggle); - - min_max_tracker tracker(clk, adc_d, lf_ed_threshold, min, max); - - // auto-tune - assign high_threshold = (max + min) / 2 + (max - min) / 4; - assign highz_threshold = (max + min) / 2 + (max - min) / 8; - assign lowz_threshold = (max + min) / 2 - (max - min) / 8; - assign low_threshold = (max + min) / 2 - (max - min) / 4; - - // heuristic to see if it makes sense to try to detect an edge - wire enabled = - (high_threshold > highz_threshold) - & (highz_threshold > lowz_threshold) - & (lowz_threshold > low_threshold) - & ((high_threshold - highz_threshold) > 8) - & ((highz_threshold - lowz_threshold) > 16) - & ((lowz_threshold - low_threshold) > 8); - - // Toggle the output with hysteresis - // Set to high if the ADC value is above the threshold - // Set to low if the ADC value is below the threshold - reg is_high = 0; - reg is_low = 0; - reg is_zero = 0; - reg trigger_enabled = 1; - reg output_edge = 0; - reg output_state; - - always @(posedge clk) - begin - is_high <= (adc_d >= high_threshold); - is_low <= (adc_d <= low_threshold); - is_zero <= ((adc_d > lowz_threshold) & (adc_d < highz_threshold)); - end - - // all edges detection - always @(posedge clk) - if (enabled) begin - // To enable detecting two consecutive peaks at the same level - // (low or high) we check whether or not we went back near 0 in-between. - // This extra check is necessary to prevent from noise artifacts - // around the threshold values. - if (trigger_enabled & (is_high | is_low)) begin - output_edge <= ~output_edge; - trigger_enabled <= 0; - end else - trigger_enabled <= trigger_enabled | is_zero; - end - - // edge states - always @(posedge clk) - if (enabled) begin - if (is_high) - output_state <= 1'd1; - else if (is_low) - output_state <= 1'd0; - end - - assign edge_state = output_state; - assign edge_toggle = output_edge; - -endmodule diff --git a/fpga-xc3s100e/lo_adc.v b/fpga-xc3s100e/lo_adc.v deleted file mode 100644 index bba090afb..000000000 --- a/fpga-xc3s100e/lo_adc.v +++ /dev/null @@ -1,91 +0,0 @@ -//----------------------------------------------------------------------------- -// The way that we connect things in low-frequency simulation mode. In this -// case just pass everything through to the ARM, which can bit-bang this -// (because it is so slow). -// -// Jonathan Westhues, April 2006 -//----------------------------------------------------------------------------- - -module lo_adc( - pck0, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, divisor, - lf_field -); - input pck0; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [7:0] divisor; - input lf_field; - -reg [7:0] to_arm_shiftreg; -reg [7:0] pck_divider; -reg clk_state; - -// Antenna logic, depending on "lf_field" (in arm defined as FPGA_LF_READER_FIELD) -wire tag_modulation = ssp_dout & !lf_field; -wire reader_modulation = !ssp_dout & lf_field & clk_state; - -// always on (High Frequency outputs, unused) -assign pwr_oe1 = 1'b0; -assign pwr_hi = 1'b0; - -// low frequency outputs -assign pwr_lo = reader_modulation; -assign pwr_oe2 = 1'b0; // 33 Ohms -assign pwr_oe3 = tag_modulation; // base antenna load = 33 Ohms -assign pwr_oe4 = 1'b0; // 10k Ohms - -// Debug Output ADC clock -assign dbg = adc_clk; - -// ADC clock out of phase with antenna driver -assign adc_clk = ~clk_state; - -// serialized SSP data is gated by clk_state to suppress unwanted signal -assign ssp_din = to_arm_shiftreg[7] && !clk_state; - -// SSP clock always runs at 24MHz -assign ssp_clk = pck0; - -// SSP frame is gated by clk_state and goes high when pck_divider=8..15 -assign ssp_frame = (pck_divider[7:3] == 5'd1) && !clk_state; - -// divide 24mhz down to 3mhz -always @(posedge pck0) -begin - if (pck_divider == divisor[7:0]) - begin - pck_divider <= 8'd0; - clk_state = !clk_state; - end - else - begin - pck_divider <= pck_divider + 1; - end -end - -// this task also runs at pck0 frequency (24Mhz) and is used to serialize -// the ADC output which is then clocked into the ARM SSP. -always @(posedge pck0) -begin - if ((pck_divider == 8'd7) && !clk_state) - to_arm_shiftreg <= adc_d; - else begin - to_arm_shiftreg[7:1] <= to_arm_shiftreg[6:0]; - // simulation showed a glitch occurring due to the LSB of the shifter - // not being set as we shift bits out - // this ensures the ssp_din remains low after a transfer and suppresses - // the glitch that would occur when the last data shifted out ended in - // a 1 bit and the next data shifted out started with a 0 bit - to_arm_shiftreg[0] <= 1'b0; - end -end - -endmodule diff --git a/fpga-xc3s100e/lo_edge_detect.v b/fpga-xc3s100e/lo_edge_detect.v deleted file mode 100644 index d91bf3845..000000000 --- a/fpga-xc3s100e/lo_edge_detect.v +++ /dev/null @@ -1,70 +0,0 @@ -//----------------------------------------------------------------------------- -// Copyright (C) 2014 iZsh -// -// This code is licensed to you under the terms of the GNU GPL, version 2 or, -// at your option, any later version. See the LICENSE.txt file for the text of -// the license. -//----------------------------------------------------------------------------- -// -// There are two modes: -// - lf_ed_toggle_mode == 0: the output is set low (resp. high) when a low -// (resp. high) edge/peak is detected, with hysteresis -// - lf_ed_toggle_mode == 1: the output is toggling whenever an edge/peak -// is detected. -// That way you can detect two consecutive edges/peaks at the same level (L/H) -// -// Output: -// - ssp_frame (wired to TIOA1 on the arm) for the edge detection/state -// - ssp_clk: cross_lo - -//For ISE 10.1 PROJ,IDE auto include -//`include "lp20khz_1MSa_iir_filter.v" -//`include "lf_edge_detect.v" - -module lo_edge_detect( - input pck0, input pck_divclk, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, - output ssp_frame, input ssp_dout, output ssp_clk, - input cross_lo, - output dbg, - input lf_field, - input lf_ed_toggle_mode, input [7:0] lf_ed_threshold -); - -wire tag_modulation = ssp_dout & !lf_field; -wire reader_modulation = !ssp_dout & lf_field & pck_divclk; - -// No logic, straight through. -assign pwr_oe1 = 1'b0; // not used in LF mode -assign pwr_oe3 = 1'b0; // base antenna load = 33 Ohms -// when modulating, add another 33 Ohms and 10k Ohms in parallel: -assign pwr_oe2 = tag_modulation; -assign pwr_oe4 = tag_modulation; - -assign ssp_clk = cross_lo; -assign pwr_lo = reader_modulation; -assign pwr_hi = 1'b0; - -// filter the ADC values -wire data_rdy; -wire [7:0] adc_filtered; -assign adc_clk = pck0; -lp20khz_1MSa_iir_filter adc_filter(pck0, adc_d, data_rdy, adc_filtered); - -// detect edges -wire [7:0] high_threshold, highz_threshold, lowz_threshold, low_threshold; -wire [7:0] max, min; -wire edge_state, edge_toggle; -lf_edge_detect lf_ed(pck0, adc_filtered, lf_ed_threshold, - max, min, - high_threshold, highz_threshold, lowz_threshold, low_threshold, - edge_state, edge_toggle); - -assign dbg = lf_ed_toggle_mode ? edge_toggle : edge_state; - -assign ssp_frame = lf_ed_toggle_mode ? edge_toggle : edge_state; - -endmodule - diff --git a/fpga-xc3s100e/lo_passthru.v b/fpga-xc3s100e/lo_passthru.v deleted file mode 100644 index f0f2847a0..000000000 --- a/fpga-xc3s100e/lo_passthru.v +++ /dev/null @@ -1,29 +0,0 @@ -//----------------------------------------------------------------------------- -// For reading TI tags, we need to place the FPGA in pass through mode -// and pass everything through to the ARM -//----------------------------------------------------------------------------- -// iZsh , June 2014 - -module lo_passthru( - input pck_divclk, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - output adc_clk, - output ssp_din, input ssp_dout, - input cross_lo, - output dbg -); - -// the antenna is modulated when ssp_dout = 1, when 0 the -// antenna drivers stop modulating and go into listen mode -assign pwr_oe3 = 1'b0; -assign pwr_oe1 = ssp_dout; -assign pwr_oe2 = ssp_dout; -assign pwr_oe4 = ssp_dout; -assign pwr_lo = pck_divclk && ssp_dout; -assign pwr_hi = 1'b0; -assign adc_clk = 1'b0; -assign ssp_din = cross_lo; -assign dbg = cross_lo; - -endmodule diff --git a/fpga-xc3s100e/lo_read.v b/fpga-xc3s100e/lo_read.v deleted file mode 100644 index 8ac58721e..000000000 --- a/fpga-xc3s100e/lo_read.v +++ /dev/null @@ -1,74 +0,0 @@ -//----------------------------------------------------------------------------- -// The way that we connect things in low-frequency read mode. In this case -// we are generating the unmodulated low frequency carrier. -// The A/D samples at that same rate and the result is serialized. -// -// Jonathan Westhues, April 2006 -// iZsh , June 2014 -//----------------------------------------------------------------------------- - -module lo_read( - input pck0, input [7:0] pck_cnt, input pck_divclk, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, - output ssp_frame, output ssp_din, output ssp_clk, - output dbg, - input lf_field -); - -reg [7:0] to_arm_shiftreg; - -// this task also runs at pck0 frequency (24MHz) and is used to serialize -// the ADC output which is then clocked into the ARM SSP. - -// because pck_divclk always transitions when pck_cnt = 0 we use the -// pck_div counter to sync our other signals off it -// we read the ADC value when pck_cnt=7 and shift it out on counts 8..15 -always @(posedge pck0) -begin - if((pck_cnt == 8'd7) && !pck_divclk) - to_arm_shiftreg <= adc_d; - else begin - to_arm_shiftreg[7:1] <= to_arm_shiftreg[6:0]; - // simulation showed a glitch occurring due to the LSB of the shifter - // not being set as we shift bits out - // this ensures the ssp_din remains low after a transfer and suppresses - // the glitch that would occur when the last data shifted out ended in - // a 1 bit and the next data shifted out started with a 0 bit - to_arm_shiftreg[0] <= 1'b0; - end -end - -// ADC samples on falling edge of adc_clk, data available on the rising edge - -// example of ssp transfer of binary value 1100101 -// start of transfer is indicated by the rise of the ssp_frame signal -// ssp_din changes on the rising edge of the ssp_clk clock and is clocked into -// the ARM by the falling edge of ssp_clk -// _______________________________ -// ssp_frame__| |__ -// _______ ___ ___ -// ssp_din __| |_______| |___| |______ -// _ _ _ _ _ _ _ _ _ _ -// ssp_clk |_| |_| |_| |_| |_| |_| |_| |_| |_| |_ - -// serialized SSP data is gated by ant_lo to suppress unwanted signal -assign ssp_din = to_arm_shiftreg[7] && !pck_divclk; -// SSP clock always runs at 24MHz -assign ssp_clk = pck0; -// SSP frame is gated by ant_lo and goes high when pck_divider=8..15 -assign ssp_frame = (pck_cnt[7:3] == 5'd1) && !pck_divclk; -// unused signals tied low -assign pwr_hi = 1'b0; -assign pwr_oe1 = 1'b0; -assign pwr_oe2 = 1'b0; -assign pwr_oe3 = 1'b0; -assign pwr_oe4 = 1'b0; -// this is the antenna driver signal -assign pwr_lo = lf_field & pck_divclk; -// ADC clock out of phase with antenna driver -assign adc_clk = ~pck_divclk; -// ADC clock also routed to debug pin -assign dbg = adc_clk; -endmodule diff --git a/fpga-xc3s100e/lp20khz_1MSa_iir_filter.v b/fpga-xc3s100e/lp20khz_1MSa_iir_filter.v deleted file mode 100644 index 2dbfd6945..000000000 --- a/fpga-xc3s100e/lp20khz_1MSa_iir_filter.v +++ /dev/null @@ -1,81 +0,0 @@ -//----------------------------------------------------------------------------- -// Copyright (C) 2014 iZsh -// -// This code is licensed to you under the terms of the GNU GPL, version 2 or, -// at your option, any later version. See the LICENSE.txt file for the text of -// the license. -//----------------------------------------------------------------------------- -// Butterworth low pass IIR filter -// input: 8bit ADC signal, 1MS/s -// output: 8bit value, Fc=20khz -// -// coef: (using http://www-users.cs.york.ac.uk/~fisher/mkfilter/trad.html) -// Recurrence relation: -// y[n] = ( 1 * x[n- 2]) -// + ( 2 * x[n- 1]) -// + ( 1 * x[n- 0]) - -// + ( -0.8371816513 * y[n- 2]) -// + ( 1.8226949252 * y[n- 1]) -// -// therefore: -// a = [1,2,1] -// b = [-0.8371816513, 1.8226949252] -// b is approximated to b = [-0xd6/0x100, 0x1d3 / 0x100] (for optimization) -// gain = 2.761139367e2 -// -// See details about its design see -// https://fail0verflow.com/blog/2014/proxmark3-fpga-iir-filter.html -module lp20khz_1MSa_iir_filter(input clk, input [7:0] adc_d, output rdy, output [7:0] out); - - // clk is 24MHz, the IIR filter is designed for 1MS/s - // hence we need to divide it by 24 - // using a shift register takes less area than a counter - reg [23:0] cnt = 1; - assign rdy = cnt[0]; - always @(posedge clk) - cnt <= {cnt[22:0], cnt[23]}; - - reg [7:0] x0 = 0; - reg [7:0] x1 = 0; - reg [16:0] y0 = 0; - reg [16:0] y1 = 0; - - always @(posedge clk) - begin - if (rdy) - begin - x0 <= x1; - x1 <= adc_d; - y0 <= y1; - y1 <= - // center the signal: - // input range is [0; 255] - // We want "128" to be at the center of the 17bit register - // (128+z)*gain = 17bit center - // z = (1<<16)/gain - 128 = 109 - // We could use 9bit x registers for that, but that would be - // a waste, let's just add the constant during the computation - // (x0+109) + 2*(x1+109) + (x2+109) = x0 + 2*x1 + x2 + 436 - x0 + {x1, 1'b0} + adc_d + 436 - // we want "- y0 * 0xd6 / 0x100" using only shift and add - // 0xd6 == 0b11010110 - // so *0xd6/0x100 is equivalent to - // ((x << 1) + (x << 2) + (x << 4) + (x << 6) + (x << 7)) >> 8 - // which is also equivalent to - // (x >> 7) + (x >> 6) + (x >> 4) + (x >> 2) + (x >> 1) - - ((y0 >> 7) + (y0 >> 6) + (y0 >> 4) + (y0 >> 2) + (y0 >> 1)) // - y0 * 0xd6 / 0x100 - // we want "+ y1 * 0x1d3 / 0x100" - // 0x1d3 == 0b111010011 - // so this is equivalent to - // ((x << 0) + (x << 1) + (x << 4) + (x << 6) + (x << 7) + (x << 8)) >> 8 - // which is also equivalent to - // (x >> 8) + (x >> 7) + (x >> 4) + (x >> 2) + (x >> 1) + (x >> 0) - + ((y1 >> 8) + (y1 >> 7) + (y1 >> 4) + (y1 >> 2) + (y1 >> 1) + y1); - end - end - - // output: reduce to 8bit - assign out = y1[16:9]; - -endmodule diff --git a/fpga-xc3s100e/min_max_tracker.v b/fpga-xc3s100e/min_max_tracker.v deleted file mode 100644 index 5e8bbedf1..000000000 --- a/fpga-xc3s100e/min_max_tracker.v +++ /dev/null @@ -1,65 +0,0 @@ -//----------------------------------------------------------------------------- -// Copyright (C) 2014 iZsh -// -// This code is licensed to you under the terms of the GNU GPL, version 2 or, -// at your option, any later version. See the LICENSE.txt file for the text of -// the license. -//----------------------------------------------------------------------------- -// track min and max peak values (envelope follower) -// -// NB: the min value (resp. max value) is updated only when the next high peak -// (resp. low peak) is reached/detected, since you can't know it isn't a -// local minima (resp. maxima) until then. -// This also means the peaks are detected with an unpredictable delay. -// This algorithm therefore can't be used directly for realtime peak detections, -// but it can be used as a simple envelope follower. -module min_max_tracker(input clk, input [7:0] adc_d, input [7:0] threshold, - output [7:0] min, output [7:0] max); - - reg [7:0] min_val = 255; - reg [7:0] max_val = 0; - reg [7:0] cur_min_val = 255; - reg [7:0] cur_max_val = 0; - reg [1:0] state = 0; - - always @(posedge clk) - begin - case (state) - 0: // initialize - begin - if (cur_max_val >= ({1'b0, adc_d} + threshold)) - state <= 2; - else if (adc_d >= ({1'b0, cur_min_val} + threshold)) - state <= 1; - if (cur_max_val <= adc_d) - cur_max_val <= adc_d; - else if (adc_d <= cur_min_val) - cur_min_val <= adc_d; - end - 1: // high phase - begin - if (cur_max_val <= adc_d) - cur_max_val <= adc_d; - else if (({1'b0, adc_d} + threshold) <= cur_max_val) begin - state <= 2; - cur_min_val <= adc_d; - max_val <= cur_max_val; - end - end - 2: // low phase - begin - if (adc_d <= cur_min_val) - cur_min_val <= adc_d; - else if (adc_d >= ({1'b0, cur_min_val} + threshold)) begin - state <= 1; - cur_max_val <= adc_d; - min_val <= cur_min_val; - end - end - endcase - end - - assign min = min_val; - assign max = max_val; - -endmodule diff --git a/fpga-xc3s100e/util.v b/fpga-xc3s100e/util.v deleted file mode 100644 index 0842ac64f..000000000 --- a/fpga-xc3s100e/util.v +++ /dev/null @@ -1,27 +0,0 @@ -//----------------------------------------------------------------------------- -// General-purpose miscellany. -// -// Jonathan Westhues, April 2006. -//----------------------------------------------------------------------------- - -module mux8(sel, y, x0, x1, x2, x3, x4, x5, x6, x7); - input [2:0] sel; - input x0, x1, x2, x3, x4, x5, x6, x7; - output y; - reg y; - -always @(x0 or x1 or x2 or x3 or x4 or x5 or x6 or x7 or sel) -begin - case (sel) - 3'b000: y = x0; - 3'b001: y = x1; - 3'b010: y = x2; - 3'b011: y = x3; - 3'b100: y = x4; - 3'b101: y = x5; - 3'b110: y = x6; - 3'b111: y = x7; - endcase -end - -endmodule diff --git a/fpga/Makefile b/fpga/Makefile new file mode 100644 index 000000000..e5bca0dfb --- /dev/null +++ b/fpga/Makefile @@ -0,0 +1,221 @@ +# +# FPGA Makefile for all targets +# +# The top part of this Makefile is used to define custom options for a number of compilation targets +# To define an additional target simply look at the other defined targets and add a new TARGET entry with a unique number and the custom options required + +XILINX_TOOLS_PREFIX= + +# Copy update (only when destination is older or missing) +CP = cp -u + +# Make directory, no error if already existing +MKDIR = mkdir -p + +# Remove recursive, force +RMDIR = rm -rf + +# Path to make +MAKE = make + +# Custom prefix for build directories, each target is built into its own separate directory name formed by combining the PREFIX and TARGET names. +# This way the source is not polluted with build files and the build directories are left behind after compilation so logs and reports can be +# examined or can be easily deleted with "make clean" +PREFIX = __ + +# Options to be passed to XST +XST_OPTS_BASE = run +XST_OPTS_BASE += -ifn xst.prj +XST_OPTS_BASE += -ifmt mixed +XST_OPTS_BASE += -ofmt NGC +XST_OPTS_BASE += -lso xst.lso +XST_OPTS_BASE += -top fpga_top +XST_OPTS_BASE += -resource_sharing yes + +# Optimizations for speed (default) +XST_OPTS_SPEED = -opt_mode Speed +XST_OPTS_SPEED += -opt_level 1 +XST_OPTS_SPEED += -fsm_style lut +XST_OPTS_SPEED += -fsm_encoding auto + +# Optimization for reduced space +XST_OPTS_AREA = -opt_mode area +XST_OPTS_AREA += -opt_level 2 +XST_OPTS_AREA += -fsm_style bram +XST_OPTS_AREA += -fsm_encoding compact + +# Types of selective module compilation: +# WITH_LF Enables selection of LF modules (and disables all HF) + +# To enable these modules WITH_LF _MUST_ be defined +# WITH_LF0 enable LF reader (generic) +# WITH_LF1 enable LF edge detect (generic) +# WITH_LF2 enable LF passthrough +# WITH_LF3 enable LF ADC (read/write) + +# To enable these modules WITH_LF _MUST_NOT_ be defined +# WITH_HF0 enable HF reader (see also WITH_HF_15 below) +# WITH_HF_15 select "iso15 2sc mode" extensions instead of original +# WITH_HF1 enable HF simulated tag +# WITH_HF2 enable HF ISO14443-A +# WITH_HF3 enable sniff +# WITH_HF4 enable HF ISO18092 FeliCa +# WITH_HF5 enable HF get trace + +# RDV40/Generic - Enable LF and all the LF modules +TARGET1_OPTIONS = -define \{WITH_LF WITH_LF0 WITH_LF1 WITH_LF2 WITH_LF3\} +# RDV40/Generic - Enable all HF modules except Felica +TARGET2_OPTIONS = -define \{WITH_HF0 WITH_HF1 WITH_HF2 WITH_HF3 WITH_HF5\} +# RDV40/Generic - Enable all HF modules except Felica and ISO14443, select HF_15 instead of HF +TARGET3_OPTIONS = -define \{WITH_HF0 WITH_HF1 WITH_HF3 WITH_HF5 WITH_HF_15\} +# RDV40/Generic - Enable all HF modules except ISO14443 +TARGET4_OPTIONS = -define \{WITH_HF0 WITH_HF1 WITH_HF3 WITH_HF4 WITH_HF5\} +# ICOPYX +TARGET5_OPTIONS = -define {PM3ICOPYX} -rtlview Yes + +# Here we list the target names +TARGET1_NAME = fpga_pm3_lf +TARGET2_NAME = fpga_pm3_hf +TARGET3_NAME = fpga_pm3_hf_15 +TARGET4_NAME = fpga_pm3_felica +TARGET5_NAME = fpga_icopyx_hf + +# Targets can be compiled for different FPGA flavours +TARGET1_FPGA = xc2s30-5-vq100 +TARGET2_FPGA = $(TARGET1_FPGA) +TARGET3_FPGA = $(TARGET1_FPGA) +TARGET4_FPGA = $(TARGET1_FPGA) +TARGET5_FPGA = xc3s100e-4-vq100 + +# Assemble the final XST options for each target +TARGET1_XST_OPTS = $(XST_OPTS_BASE) $(XST_OPTS_AREA) -p $(TARGET1_FPGA) -ofn $(TARGET1_NAME) $(TARGET1_OPTIONS) +TARGET2_XST_OPTS = $(XST_OPTS_BASE) $(XST_OPTS_AREA) -p $(TARGET2_FPGA) -ofn $(TARGET2_NAME) $(TARGET2_OPTIONS) +TARGET3_XST_OPTS = $(XST_OPTS_BASE) $(XST_OPTS_AREA) -p $(TARGET3_FPGA) -ofn $(TARGET3_NAME) $(TARGET3_OPTIONS) +TARGET4_XST_OPTS = $(XST_OPTS_BASE) $(XST_OPTS_AREA) -p $(TARGET4_FPGA) -ofn $(TARGET4_NAME) $(TARGET4_OPTIONS) +TARGET5_XST_OPTS = $(XST_OPTS_BASE) $(XST_OPTS_SPEED) -p $(TARGET5_FPGA) -ofn $(TARGET5_NAME) $(TARGET5_OPTIONS) + +# these files are common for all targets +TARGET_COMMON_FILES = define.v +TARGET_COMMON_FILES += mux8.v +TARGET_COMMON_FILES += clk_divider.v +TARGET_COMMON_FILES += lp20khz_1MSa_iir_filter.v +TARGET_COMMON_FILES += min_max_tracker.v +TARGET_COMMON_FILES += hi_flite.v +TARGET_COMMON_FILES += hi_get_trace.v +TARGET_COMMON_FILES += hi_iso14443a.v +TARGET_COMMON_FILES += hi_reader.v +TARGET_COMMON_FILES += hi_reader_15.v +TARGET_COMMON_FILES += hi_simulate.v +TARGET_COMMON_FILES += hi_sniffer.v +TARGET_COMMON_FILES += lf_edge_detect.v +TARGET_COMMON_FILES += lo_adc.v +TARGET_COMMON_FILES += lo_edge_detect.v +TARGET_COMMON_FILES += lo_passthru.v +TARGET_COMMON_FILES += lo_read.v + +# Add the files that are unique per target and all the common files +TARGET1_FILES = $(TARGET_COMMON_FILES) fpga_pm3_top.v +TARGET2_FILES = $(TARGET1_FILES) +TARGET3_FILES = $(TARGET1_FILES) +TARGET4_FILES = $(TARGET1_FILES) +TARGET5_FILES = $(TARGET_COMMON_FILES) mux2_onein.v mux2_oneout.v fpga_icopyx_hf.v fpga_icopyx_lf.v fpga_icopyx_top.v + +# List of all valid target FPGA images to build +TARGETS = $(TARGET1_NAME) $(TARGET2_NAME) $(TARGET3_NAME) $(TARGET4_NAME) $(TARGET5_NAME) + +# Verbosity type for ISE tools ise|xflow|silent +VERBOSITY = -intstyle silent +# Echo (Q=) or not echo (Q=@) build commands to the terminal +Q=@ + +# Pass the custom variables to the lower make rules +$(TARGET1_NAME).bit: TARGET_FPGA = $(TARGET1_FPGA) +$(TARGET1_NAME).bit: TARGET_FILES = $(TARGET1_FILES) +$(TARGET1_NAME).bit: TARGET_XST_OPTS = $(TARGET1_XST_OPTS) + +$(TARGET2_NAME).bit: TARGET_FPGA = $(TARGET2_FPGA) +$(TARGET2_NAME).bit: TARGET_FILES = $(TARGET2_FILES) +$(TARGET2_NAME).bit: TARGET_XST_OPTS = $(TARGET2_XST_OPTS) + +$(TARGET3_NAME).bit: TARGET_FPGA = $(TARGET3_FPGA) +$(TARGET3_NAME).bit: TARGET_FILES = $(TARGET3_FILES) +$(TARGET3_NAME).bit: TARGET_XST_OPTS = $(TARGET3_XST_OPTS) + +$(TARGET4_NAME).bit: TARGET_FPGA = $(TARGET4_FPGA) +$(TARGET4_NAME).bit: TARGET_FILES = $(TARGET4_FILES) +$(TARGET4_NAME).bit: TARGET_XST_OPTS = $(TARGET4_XST_OPTS) + +$(TARGET5_NAME).bit: TARGET_FPGA = $(TARGET5_FPGA) +$(TARGET5_NAME).bit: TARGET_FILES = $(TARGET5_FILES) +$(TARGET5_NAME).bit: TARGET_XST_OPTS = $(TARGET5_XST_OPTS) + +$(TARGETS): + $(Q)$(MKDIR) $(PREFIX)build_$@ + $(Q)$(MAKE) -C $(PREFIX)build_$@ -f ../Makefile $(notdir $@).bit + +work: + $(Q)$(RM) xst.prj + $(Q)for item in $(TARGET_FILES); do echo verilog work ../$$item>>xst.prj; done + $(Q)echo work> xst.lso + +%.xst: work + $(Q)$(RM) $@ + $(Q)echo $(TARGET_XST_OPTS)> $@ + +%.ngc: %.xst + $(Q)$(RM) $@ + $(info [-] XST $@) + $(Q)$(XILINX_TOOLS_PREFIX)xst $(VERBOSITY) -ifn $< + +%.ngd: %.ngc + $(Q)$(RM) $@ + $(info [-] NGD $@) + $(Q)$(XILINX_TOOLS_PREFIX)ngdbuild $(VERBOSITY) -quiet -p $(TARGET_FPGA) -nt timestamp -uc ../$(TARGET_FPGA).ucf $< $@ + +%_map.ncd: %.ngd + $(Q)$(RM) $@ + $(info [-] MAP $@) + $(Q)$(XILINX_TOOLS_PREFIX)map $(VERBOSITY) -p $(TARGET_FPGA) -o $*_map $* + +%.ncd: %_map.ncd + $(Q)$(RM) $@ + $(info [-] PAR $@) + $(Q)$(XILINX_TOOLS_PREFIX)par $(VERBOSITY) -w $< $@ + +%.bit: %.ncd + # Hacky hack, make empty files for icopyx + if echo "$@" | grep -qi "icopyx"; then \ + truncate -s0 ../fpga_icopyx_lf.bit; \ + truncate -s0 ../fpga_icopyx_hf_15.bit; \ + truncate -s0 ../fpga_icopyx_felica.bit; \ + fi + $(Q)$(RM) $@ $*.drc $*.rbt + $(info [=] BITGEN $@) + $(Q)$(XILINX_TOOLS_PREFIX)bitgen $(VERBOSITY) -w $* $@ + $(Q)$(CP) $@ .. + +# Build all targets +all: $(TARGETS) + +# ALWAYS have some hardcoded text after $(PREFIX) to avoid rm -rf * or rm -rf /* situations if PREFIX is incorrectly set to empty "" or just "/" +clean: + $(Q)$(RMDIR) $(PREFIX)build_* + $(info [-] Build files deleted) + +.DEFAULT: + @if [ "$@" != "all" ] && [ ! "$(filter $@,$(TARGETS))" ]; then \ + make help; \ + else \ + make all; \ + fi + +.PHONY: all help clean + +help: + @echo "################################################################" + @echo "# Valid targets are: $(TARGETS)" + @echo "# - Builds only one of the above listed targets" + @echo "# all - Builds the FPGA bitstreams for all targets" + @echo "# clean - Keeps .bit files but cleans intermediate build files for all targets" + @echo "################################################################" + diff --git a/fpga-xc2s30/clk_divider.v b/fpga/clk_divider.v similarity index 91% rename from fpga-xc2s30/clk_divider.v rename to fpga/clk_divider.v index fbb3250f1..0bcc2e608 100644 --- a/fpga-xc2s30/clk_divider.v +++ b/fpga/clk_divider.v @@ -14,7 +14,12 @@ // See LICENSE.txt for the text of the license. //----------------------------------------------------------------------------- -module clk_divider(input clk, input [7:0] divisor, output [7:0] div_cnt, output div_clk); +module clk_divider( + input clk, + input [7:0] divisor, + output [7:0] div_cnt, + output div_clk +); reg [7:0] div_cnt_ = 0; reg div_clk_; diff --git a/fpga/define.v b/fpga/define.v new file mode 100644 index 000000000..b7423278b --- /dev/null +++ b/fpga/define.v @@ -0,0 +1,155 @@ +//----------------------------------------------------------------------------- +// Copyright (C) Proxmark3 contributors. See AUTHORS.md for details. +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// See LICENSE.txt for the text of the license. +//----------------------------------------------------------------------------- +// +// The FPGA is responsible for interfacing between the A/D, the coil drivers, +// and the ARM. In the low-frequency modes it passes the data straight +// through, so that the ARM gets raw A/D samples over the SSP. In the high- +// frequency modes, the FPGA might perform some demodulation first, to +// reduce the amount of data that we must send to the ARM. +//----------------------------------------------------------------------------- + +/* + Communication between ARM / FPGA is done inside armsrc/fpgaloader.c see: function FpgaSendCommand() + Send 16 bit command / data pair to FPGA with the bit format: + ++------ frame layout circa 2020 ------------------+ +| 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 | ++-------------------------------------------------+ +| C C C C M M M M P P P P P P P P | C = FPGA_CMD_SET_CONFREG, M = FPGA_MAJOR_MODE_*, P = FPGA_LF_* or FPGA_HF_* parameter +| C C C C D D D D D D D D | C = FPGA_CMD_SET_DIVISOR, D = divisor +| C C C C T T T T T T T T | C = FPGA_CMD_SET_EDGE_DETECT_THRESHOLD, T = threshold +| C C C C E | C = FPGA_CMD_TRACE_ENABLE, E=0 off, E=1 on ++-------------------------------------------------+ + ++------ frame layout current ---------------------+ +| 15 14 13 12 11 10 9 8 7 6 5 4 3 2 1 0 | ++-------------------------------------------------+ +| C C C C M M M P P P P P P | C = FPGA_CMD_SET_CONFREG, M = FPGA_MAJOR_MODE_*, P = FPGA_LF_* or FPGA_HF_* parameter +| C C C C D D D D D D D D | C = FPGA_CMD_SET_DIVISOR, D = divisor +| C C C C T T T T T T T T | C = FPGA_CMD_SET_EDGE_DETECT_THRESHOLD, T = threshold +| C C C C E | C = FPGA_CMD_TRACE_ENABLE, E=0 off, E=1 on ++-------------------------------------------------+ + + shift_reg receive this 16bit frame + + LF command + ---------- + shift_reg[15:12] == 4bit command + LF has three commands (FPGA_CMD_SET_CONFREG, FPGA_CMD_SET_DIVISOR, FPGA_CMD_SET_EDGE_DETECT_THRESHOLD) + Current commands uses only 2bits. We have room for up to 4bits of commands total (7). + + LF data + ------- + shift_reg[11:0] == 12bit data + lf data is divided into MAJOR MODES and configuration values. + + The major modes uses 3bits (0,1,2,3,7 | 000, 001, 010, 011, 111) + 000 FPGA_MAJOR_MODE_LF_READER = Act as LF reader (modulate) + 001 FPGA_MAJOR_MODE_LF_EDGE_DETECT = Simulate LF + 010 FPGA_MAJOR_MODE_LF_PASSTHRU = Passthrough mode, CROSS_LO line connected to SSP_DIN. SSP_DOUT logic level controls if we modulate / listening + 011 FPGA_MAJOR_MODE_LF_ADC = refactor hitag2, clear ADC sampling + 111 FPGA_MAJOR_MODE_OFF = turn off sampling. + + Each one of this major modes can have options. Currently these two major modes uses options. + - FPGA_MAJOR_MODE_LF_READER + - FPGA_MAJOR_MODE_LF_EDGE_DETECT + + FPGA_MAJOR_MODE_LF_READER + ------------------------------------- + lf_field = 1bit (FPGA_LF_ADC_READER_FIELD) + + You can send FPGA_CMD_SET_DIVISOR to set with FREQUENCY the fpga should sample at + divisor = 8bits shift_reg[7:0] + + FPGA_MAJOR_MODE_LF_EDGE_DETECT + ------------------------------------------ + lf_ed_toggle_mode = 1bits + lf_ed_threshold = 8bits threshold defaults to 127 + + You can send FPGA_CMD_SET_EDGE_DETECT_THRESHOLD to set a custom threshold + lf_ed_threshold = 8bits threshold value. + + conf_word 12bits + conf_word[7:5] = 3bit major mode. + conf_word[0] = 1bit lf_field + conf_word[1] = 1bit lf_ed_toggle_mode + conf_word[7:0] = 8bit divisor + conf_word[7:0] = 8bit threshold + +*/ +// Defining commands, modes and options. This must be aligned to the definitions in armsrc/fpgaloader.h +// Note: the definitions here are without shifts + +// Definitions for the FPGA commands. +`define FPGA_CMD_SET_CONFREG 1 +`define FPGA_CMD_SET_DIVISOR 2 +`define FPGA_CMD_SET_EDGE_DETECT_THRESHOLD 3 +`define FPGA_CMD_TRACE_ENABLE 2 + +// Major modes +`define FPGA_MAJOR_MODE_LF_READER 0 +`define FPGA_MAJOR_MODE_LF_EDGE_DETECT 1 +`define FPGA_MAJOR_MODE_LF_PASSTHRU 2 +`define FPGA_MAJOR_MODE_LF_ADC 3 +`define FPGA_MAJOR_MODE_HF_READER 0 +`define FPGA_MAJOR_MODE_HF_SIMULATOR 1 +`define FPGA_MAJOR_MODE_HF_ISO14443A 2 +`define FPGA_MAJOR_MODE_HF_SNIFF 3 +`define FPGA_MAJOR_MODE_HF_ISO18092 4 +`define FPGA_MAJOR_MODE_HF_GET_TRACE 5 +`define FPGA_MAJOR_MODE_OFF 7 + +// Options for LF_READER +`define FPGA_LF_ADC_READER_FIELD 1 + +// Options for LF_EDGE_DETECT +`define FPGA_LF_EDGE_DETECT_READER_FIELD 1 +`define FPGA_LF_EDGE_DETECT_TOGGLE_MODE 2 + +// Options for the generic HF reader +`define FPGA_HF_READER_MODE_RECEIVE_IQ 0 +`define FPGA_HF_READER_MODE_RECEIVE_AMPLITUDE 1 +`define FPGA_HF_READER_MODE_RECEIVE_PHASE 2 +`define FPGA_HF_READER_MODE_SEND_FULL_MOD 3 +`define FPGA_HF_READER_MODE_SEND_SHALLOW_MOD 4 +`define FPGA_HF_READER_MODE_SNIFF_IQ 5 +`define FPGA_HF_READER_MODE_SNIFF_AMPLITUDE 6 +`define FPGA_HF_READER_MODE_SNIFF_PHASE 7 +`define FPGA_HF_READER_MODE_SEND_JAM 8 + +`define FPGA_HF_READER_SUBCARRIER_848_KHZ 0 +`define FPGA_HF_READER_SUBCARRIER_424_KHZ 1 +`define FPGA_HF_READER_SUBCARRIER_212_KHZ 2 +`define FPGA_HF_READER_2SUBCARRIERS_424_484_KHZ 3 + +// Options for the HF simulated tag, how to modulate +`define FPGA_HF_SIMULATOR_NO_MODULATION 0 +`define FPGA_HF_SIMULATOR_MODULATE_BPSK 1 +`define FPGA_HF_SIMULATOR_MODULATE_212K 2 +`define FPGA_HF_SIMULATOR_MODULATE_424K 4 +`define FPGA_HF_SIMULATOR_MODULATE_424K_8BIT 5 + +// Options for ISO14443A +`define FPGA_HF_ISO14443A_SNIFFER 0 +`define FPGA_HF_ISO14443A_TAGSIM_LISTEN 1 +`define FPGA_HF_ISO14443A_TAGSIM_MOD 2 +`define FPGA_HF_ISO14443A_READER_LISTEN 3 +`define FPGA_HF_ISO14443A_READER_MOD 4 + +// Options for ISO18092 / Felica +`define FPGA_HF_ISO18092_FLAG_NOMOD 1 // 0001 disable modulation module +`define FPGA_HF_ISO18092_FLAG_424K 2 // 0010 should enable 414k mode (untested). No autodetect +`define FPGA_HF_ISO18092_FLAG_READER 4 // 0100 enables antenna power, to act as a reader instead of tag diff --git a/fpga-xc3s100e/fpga_felica.bit b/fpga/fpga_icopyx_felica.bit similarity index 100% rename from fpga-xc3s100e/fpga_felica.bit rename to fpga/fpga_icopyx_felica.bit diff --git a/fpga/fpga_icopyx_hf.bit b/fpga/fpga_icopyx_hf.bit new file mode 100644 index 000000000..b62cdace6 Binary files /dev/null and b/fpga/fpga_icopyx_hf.bit differ diff --git a/fpga/fpga_icopyx_hf.v b/fpga/fpga_icopyx_hf.v new file mode 100644 index 000000000..b7730875d --- /dev/null +++ b/fpga/fpga_icopyx_hf.v @@ -0,0 +1,227 @@ +//----------------------------------------------------------------------------- +// Copyright (C) Proxmark3 contributors. See AUTHORS.md for details. +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// See LICENSE.txt for the text of the license. +//----------------------------------------------------------------------------- +// +// The FPGA is responsible for interfacing between the A/D, the coil drivers, +// and the ARM. In the low-frequency modes it passes the data straight +// through, so that the ARM gets raw A/D samples over the SSP. In the high- +// frequency modes, the FPGA might perform some demodulation first, to +// reduce the amount of data that we must send to the ARM. +//----------------------------------------------------------------------------- +//`include "define.v" + +//`include "hi_reader.v" +//`include "hi_simulate.v" +//`include "hi_iso14443a.v" +//`include "hi_flite.v" +//`include "hi_sniffer.v" +//`include "hi_get_trace.v" + +module fpga_hf( + input spck, + output miso, + input mosi, + input ncs, + input pck0, + input ck_1356meg, + input ck_1356megb, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + input [7:0] adc_d, + output adc_clk, + output adc_noe, + output ssp_frame, + output ssp_din, + input ssp_dout, + output ssp_clk, + input cross_hi, + input cross_lo, + output debug +); + +//----------------------------------------------------------------------------- +// The SPI receiver. This sets up the configuration word, which the rest of +// the logic looks at to determine how to connect the A/D and the coil +// drivers (i.e., which section gets it). Also assign some symbolic names +// to the configuration bits, for use below. +//----------------------------------------------------------------------------- + +// Receive 16bits of data from ARM here. +reg [15:0] shift_reg; +always @(posedge spck) if (~ncs) shift_reg <= {shift_reg[14:0], mosi}; + +reg [8:0] conf_word; +reg trace_enable; + +// select module (outputs) based on major mode +wire [2:0] major_mode = conf_word[8:6]; +// parameter to be passed to modules +wire [3:0] minor_mode = conf_word[3:0]; + +// configuring the HF reader +wire [1:0] subcarrier_frequency = conf_word[5:4]; + +// We switch modes between transmitting to the 13.56 MHz tag and receiving +// from it, which means that we must make sure that we can do so without +// glitching, or else we will glitch the transmitted carrier. +always @(posedge ncs) +begin + // 4 bit command + case (shift_reg[15:12]) + `FPGA_CMD_SET_CONFREG: conf_word <= shift_reg[8:0]; + `FPGA_CMD_TRACE_ENABLE: trace_enable <= shift_reg[0]; + endcase +end + +//----------------------------------------------------------------------------- +// And then we instantiate the modules corresponding to each of the FPGA's +// major modes, and use muxes to connect the outputs of the active mode to +// the output pins. +//----------------------------------------------------------------------------- + +// 0 - HF reader +hi_reader hr( + .ck_1356meg (ck_1356megb), + .pwr_lo (hr_pwr_lo), + .pwr_hi (hr_pwr_hi), + .pwr_oe1 (hr_pwr_oe1), + .pwr_oe2 (hr_pwr_oe2), + .pwr_oe3 (hr_pwr_oe3), + .pwr_oe4 (hr_pwr_oe4), + .adc_d (adc_d), + .adc_clk (hr_adc_clk), + .ssp_frame (hr_ssp_frame), + .ssp_din (hr_ssp_din), + .ssp_dout (ssp_dout), + .ssp_clk (hr_ssp_clk), + .debug (hr_debug), + .subcarrier_frequency (subcarrier_frequency), + .minor_mode (minor_mode) +); + +// 1 - HF simulated tag +hi_simulate hs( + .ck_1356meg (ck_1356meg), + .pwr_lo (hs_pwr_lo), + .pwr_hi (hs_pwr_hi), + .pwr_oe1 (hs_pwr_oe1), + .pwr_oe2 (hs_pwr_oe2), + .pwr_oe3 (hs_pwr_oe3), + .pwr_oe4 (hs_pwr_oe4), + .adc_d (adc_d), + .adc_clk (hs_adc_clk), + .ssp_frame (hs_ssp_frame), + .ssp_din (hs_ssp_din), + .ssp_dout (ssp_dout), + .ssp_clk (hs_ssp_clk), + .debug (hs_debug), + .mod_type (minor_mode) +); + +// 2 - HF ISO14443-A +hi_iso14443a hisn( + .ck_1356meg (ck_1356meg), + .pwr_lo (hisn_pwr_lo), + .pwr_hi (hisn_pwr_hi), + .pwr_oe1 (hisn_pwr_oe1), + .pwr_oe2 (hisn_pwr_oe2), + .pwr_oe3 (hisn_pwr_oe3), + .pwr_oe4 (hisn_pwr_oe4), + .adc_d (adc_d), + .adc_clk (hisn_adc_clk), + .ssp_frame (hisn_ssp_frame), + .ssp_din (hisn_ssp_din), + .ssp_dout (ssp_dout), + .ssp_clk (hisn_ssp_clk), + .debug (hisn_debug), + .mod_type (minor_mode) +); + +// 3 - HF sniff +hi_sniffer he( + .ck_1356meg (ck_1356megb), + .pwr_lo (he_pwr_lo), + .pwr_hi (he_pwr_hi), + .pwr_oe1 (he_pwr_oe1), + .pwr_oe2 (he_pwr_oe2), + .pwr_oe3 (he_pwr_oe3), + .pwr_oe4 (he_pwr_oe4), + .adc_d (adc_d), + .adc_clk (he_adc_clk), + .ssp_frame (he_ssp_frame), + .ssp_din (he_ssp_din), + .ssp_clk (he_ssp_clk) +); + +// 4 - HF ISO18092 FeliCa +hi_flite hfl( + .ck_1356meg (ck_1356megb), + .pwr_lo (hfl_pwr_lo), + .pwr_hi (hfl_pwr_hi), + .pwr_oe1 (hfl_pwr_oe1), + .pwr_oe2 (hfl_pwr_oe2), + .pwr_oe3 (hfl_pwr_oe3), + .pwr_oe4 (hfl_pwr_oe4), + .adc_d (adc_d), + .adc_clk (hfl_adc_clk), + .ssp_frame (hfl_ssp_frame), + .ssp_din (hfl_ssp_din), + .ssp_dout (ssp_dout), + .ssp_clk (hfl_ssp_clk), + .debug (hfl_debug), + .mod_type (minor_mode) +); + +// 5 - HF get trace +hi_get_trace gt( + .ck_1356megb (ck_1356megb), + .adc_d (adc_d), + .trace_enable (trace_enable), + .major_mode (major_mode), + .ssp_frame (gt_ssp_frame), + .ssp_din (gt_ssp_din), + .ssp_clk (gt_ssp_clk) +); + +// Major modes: +// x0 = HF reader +// x1 = HF simulated tag +// x2 = HF ISO14443-A +// x3 = HF sniff +// x4 = HF ISO18092 FeliCa +// x5 = HF get trace +// x6 = unused +// x7 = FPGA_MAJOR_MODE_OFF + +mux8 mux_ssp_clk (.sel(major_mode), .y(ssp_clk ), .x0(hr_ssp_clk ), .x1(hs_ssp_clk ), .x2(hisn_ssp_clk ), .x3(he_ssp_clk ), .x4(hfl_ssp_clk ), .x5(gt_ssp_clk ), .x6(1'b0), .x7(1'b0) ); +mux8 mux_ssp_din (.sel(major_mode), .y(ssp_din ), .x0(hr_ssp_din ), .x1(hs_ssp_din ), .x2(hisn_ssp_din ), .x3(he_ssp_din ), .x4(hfl_ssp_din ), .x5(gt_ssp_din ), .x6(1'b0), .x7(1'b0) ); +mux8 mux_ssp_frame (.sel(major_mode), .y(ssp_frame), .x0(hr_ssp_frame ), .x1(hs_ssp_frame), .x2(hisn_ssp_frame), .x3(he_ssp_frame), .x4(hfl_ssp_frame), .x5(gt_ssp_frame), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_oe1 (.sel(major_mode), .y(pwr_oe1 ), .x0(hr_pwr_oe1 ), .x1(hs_pwr_oe1 ), .x2(hisn_pwr_oe1 ), .x3(he_pwr_oe1 ), .x4(hfl_pwr_oe1 ), .x5(1'b0 ), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_oe2 (.sel(major_mode), .y(pwr_oe2 ), .x0(hr_pwr_oe2 ), .x1(hs_pwr_oe2 ), .x2(hisn_pwr_oe2 ), .x3(he_pwr_oe2 ), .x4(hfl_pwr_oe2 ), .x5(1'b0 ), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_oe3 (.sel(major_mode), .y(pwr_oe3 ), .x0(hr_pwr_oe3 ), .x1(hs_pwr_oe3 ), .x2(hisn_pwr_oe3 ), .x3(he_pwr_oe3 ), .x4(hfl_pwr_oe3 ), .x5(1'b0 ), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_oe4 (.sel(major_mode), .y(pwr_oe4 ), .x0(hr_pwr_oe4 ), .x1(hs_pwr_oe4 ), .x2(hisn_pwr_oe4 ), .x3(he_pwr_oe4 ), .x4(hfl_pwr_oe4 ), .x5(1'b0 ), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_lo (.sel(major_mode), .y(pwr_lo ), .x0(hr_pwr_lo ), .x1(hs_pwr_lo ), .x2(hisn_pwr_lo ), .x3(he_pwr_lo ), .x4(hfl_pwr_lo ), .x5(1'b0 ), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_hi (.sel(major_mode), .y(pwr_hi ), .x0(hr_pwr_hi ), .x1(hs_pwr_hi ), .x2(hisn_pwr_hi ), .x3(he_pwr_hi ), .x4(hfl_pwr_hi ), .x5(1'b0 ), .x6(1'b0), .x7(1'b0) ); +mux8 mux_adc_clk (.sel(major_mode), .y(adc_clk ), .x0(hr_adc_clk ), .x1(hs_adc_clk ), .x2(hisn_adc_clk ), .x3(he_adc_clk ), .x4(hfl_adc_clk ), .x5(1'b0 ), .x6(1'b0), .x7(1'b0) ); +mux8 mux_dbg (.sel(major_mode), .y(debug ), .x0(hr_debug ), .x1(hs_debug ), .x2(hisn_debug ), .x3(he_debug ), .x4(hfl_debug ), .x5(1'b0 ), .x6(1'b0), .x7(1'b0) ); + +// In all modes, let the ADC's outputs be enabled. +assign adc_noe = 1'b0; + +endmodule diff --git a/fpga-xc3s100e/fpga_lf.bit b/fpga/fpga_icopyx_hf_15.bit similarity index 100% rename from fpga-xc3s100e/fpga_lf.bit rename to fpga/fpga_icopyx_hf_15.bit diff --git a/fpga/fpga_icopyx_lf.bit b/fpga/fpga_icopyx_lf.bit new file mode 100644 index 000000000..e69de29bb diff --git a/fpga/fpga_icopyx_lf.v b/fpga/fpga_icopyx_lf.v new file mode 100644 index 000000000..0ca4739b7 --- /dev/null +++ b/fpga/fpga_icopyx_lf.v @@ -0,0 +1,218 @@ +//----------------------------------------------------------------------------- +// Copyright (C) Proxmark3 contributors. See AUTHORS.md for details. +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// See LICENSE.txt for the text of the license. +//----------------------------------------------------------------------------- +// +// The FPGA is responsible for interfacing between the A/D, the coil drivers, +// and the ARM. In the low-frequency modes it passes the data straight +// through, so that the ARM gets raw A/D samples over the SSP. In the high- +// frequency modes, the FPGA might perform some demodulation first, to +// reduce the amount of data that we must send to the ARM. +//----------------------------------------------------------------------------- +//`include "define.v" + +//`include "lo_read.v" +//`include "lo_passthru.v" +//`include "lo_edge_detect.v" +//`include "lo_adc.v" +//`include "clk_divider.v" + +module fpga_lf( + input spck, + output miso, + input mosi, + input ncs, + input pck0, + input ck_1356meg, + input ck_1356megb, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + input [7:0] adc_d, + output adc_clk, + output adc_noe, + output ssp_frame, + output ssp_din, + input ssp_dout, + output ssp_clk, + input cross_hi, + input cross_lo, + output debug, + output PWR_LO_EN +); + +//----------------------------------------------------------------------------- +// The SPI receiver. This sets up the configuration word, which the rest of +// the logic looks at to determine how to connect the A/D and the coil +// drivers (i.e., which section gets it). Also assign some symbolic names +// to the configuration bits, for use below. +//----------------------------------------------------------------------------- + +// Receive 16bits of data from ARM here. +reg [15:0] shift_reg; +always @(posedge spck) if (~ncs) shift_reg <= {shift_reg[14:0], mosi}; + +reg [11:0] conf_word; + +// select module (outputs) based on major mode +wire [2:0] major_mode = conf_word[8:6]; +// parameter to be passed to modules +wire lf_field = conf_word[0]; +wire lf_ed_toggle_mode = conf_word[1]; +reg [7:0] lf_ed_threshold; + +wire [7:0] pck_cnt; +wire pck_divclk; +reg [7:0] divisor; +clk_divider div_clk(pck0, divisor, pck_cnt, pck_divclk); + +// We switch modes between transmitting to the 13.56 MHz tag and receiving +// from it, which means that we must make sure that we can do so without +// glitching, or else we will glitch the transmitted carrier. +always @(posedge ncs) +begin + // 4 bit command + case (shift_reg[15:12]) + `FPGA_CMD_SET_CONFREG: + begin + // 12 bit data + conf_word <= shift_reg[11:0]; + if (shift_reg[8:6] == `FPGA_MAJOR_MODE_LF_EDGE_DETECT) + begin + lf_ed_threshold <= 127; // default threshold + end + end + + `FPGA_CMD_SET_DIVISOR: + divisor <= shift_reg[7:0]; // 8bits + + `FPGA_CMD_SET_EDGE_DETECT_THRESHOLD: + lf_ed_threshold <= shift_reg[7:0]; // 8 bits + endcase +end + +//----------------------------------------------------------------------------- +// And then we instantiate the modules corresponding to each of the FPGA's +// major modes, and use muxes to connect the outputs of the active mode to +// the output pins. +//----------------------------------------------------------------------------- + +// 0 -- LF reader (generic) +lo_read lr( + .pck0 (pck0), + .pck_cnt (pck_cnt), + .pck_divclk (pck_divclk), + .pwr_lo (lr_pwr_lo), + .pwr_hi (lr_pwr_hi), + .pwr_oe1 (lr_pwr_oe1), + .pwr_oe2 (lr_pwr_oe2), + .pwr_oe3 (lr_pwr_oe3), + .pwr_oe4 (lr_pwr_oe4), + .adc_d (adc_d), + .adc_clk (lr_adc_clk), + .ssp_frame (lr_ssp_frame), + .ssp_din (lr_ssp_din), + .ssp_clk (lr_ssp_clk), + .debug (lr_debug), + .lf_field (lf_field) +); + +// 1 -- LF edge detect (generic) +lo_edge_detect le( + .pck0 (pck0), + .pck_divclk (pck_divclk), + .pwr_lo (le_pwr_lo), + .pwr_hi (le_pwr_hi), + .pwr_oe1 (le_pwr_oe1), + .pwr_oe2 (le_pwr_oe2), + .pwr_oe3 (le_pwr_oe3), + .pwr_oe4 (le_pwr_oe4), + .adc_d (adc_d), + .adc_clk (le_adc_clk), + .ssp_frame (le_ssp_frame), + .ssp_dout (ssp_dout), + .ssp_clk (le_ssp_clk), + .cross_lo (cross_lo), + .debug (le_debug), + .lf_field (lf_field), + .lf_ed_toggle_mode (lf_ed_toggle_mode), + .lf_ed_threshold (lf_ed_threshold) +); + +// 2 -- LF passthrough +lo_passthru lp( + .pck_divclk (pck_divclk), + .pwr_lo (lp_pwr_lo), + .pwr_hi (lp_pwr_hi), + .pwr_oe1 (lp_pwr_oe1), + .pwr_oe2 (lp_pwr_oe2), + .pwr_oe3 (lp_pwr_oe3), + .pwr_oe4 (lp_pwr_oe4), + .adc_clk (lp_adc_clk), + .ssp_din (lp_ssp_din), + .ssp_dout (ssp_dout), + .cross_lo (cross_lo), + .debug (lp_debug) +); + +// 3 -- LF ADC (read/write) +lo_adc la( + .pck0 (pck0), + .pwr_lo (la_pwr_lo ), + .pwr_hi (la_pwr_hi ), + .pwr_oe1 (la_pwr_oe1), + .pwr_oe2 (la_pwr_oe2), + .pwr_oe3 (la_pwr_oe3), + .pwr_oe4 (la_pwr_oe4), + .adc_d (adc_d), + .adc_clk (la_adc_clk), + .ssp_frame (la_ssp_frame), + .ssp_din (la_ssp_din), + .ssp_dout (ssp_dout), + .ssp_clk (la_ssp_clk), + .debug (la_debug), + .divisor (divisor), + .lf_field (lf_field) +); + +// Major modes: +// x0 = LF reader (generic) +// x1 = LF edge detect (generic) +// x2 = LF passthrough +// x3 = LF ADC (read/write) +// x4 = SPARE +// x5 = SPARE +// x6 = SPARE +// x7 = FPGA_MAJOR_MODE_OFF + +mux8 mux_ssp_clk (.sel(major_mode), .y(ssp_clk ), .x0(lr_ssp_clk ), .x1(le_ssp_clk ), .x2(1'b0 ), .x3(la_ssp_clk ), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); +mux8 mux_ssp_din (.sel(major_mode), .y(ssp_din ), .x0(lr_ssp_din ), .x1(1'b0 ), .x2(lp_ssp_din), .x3(la_ssp_din ), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); +mux8 mux_ssp_frame (.sel(major_mode), .y(ssp_frame), .x0(lr_ssp_frame), .x1(le_ssp_frame), .x2(1'b0 ), .x3(la_ssp_frame), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_oe1 (.sel(major_mode), .y(pwr_oe1 ), .x0(lr_pwr_oe1 ), .x1(le_pwr_oe1 ), .x2(lp_pwr_oe1), .x3(la_pwr_oe1 ), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_oe2 (.sel(major_mode), .y(pwr_oe2 ), .x0(lr_pwr_oe2 ), .x1(le_pwr_oe2 ), .x2(lp_pwr_oe2), .x3(la_pwr_oe2 ), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_oe3 (.sel(major_mode), .y(pwr_oe3 ), .x0(lr_pwr_oe3 ), .x1(le_pwr_oe3 ), .x2(lp_pwr_oe3), .x3(la_pwr_oe3 ), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_oe4 (.sel(major_mode), .y(pwr_oe4 ), .x0(lr_pwr_oe4 ), .x1(le_pwr_oe4 ), .x2(lp_pwr_oe4), .x3(la_pwr_oe4 ), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); +mux8 mux_pwr_lo (.sel(major_mode), .y(pwr_lo ), .x0(lr_pwr_lo ), .x1(le_pwr_lo ), .x2(lp_pwr_lo ), .x3(la_pwr_lo ), .x4(1'b0), .x5(1'b0), .x6(1'b1), .x7(1'b0) ); +mux8 mux_pwr_hi (.sel(major_mode), .y(pwr_hi ), .x0(lr_pwr_hi ), .x1(le_pwr_hi ), .x2(lp_pwr_hi ), .x3(la_pwr_hi ), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); +mux8 mux_adc_clk (.sel(major_mode), .y(adc_clk ), .x0(lr_adc_clk ), .x1(le_adc_clk ), .x2(lp_adc_clk), .x3(la_adc_clk ), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); +mux8 mux_dbg (.sel(major_mode), .y(debug ), .x0(lr_debug ), .x1(le_debug ), .x2(lp_debug ), .x3(la_debug ), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); +mux8 mux_ant (.sel(major_mode), .y(PWR_LO_EN), .x0(1'b1 ), .x1(1'b1 ), .x2(1'b1 ), .x3(1'b1 ), .x4(1'b0), .x5(1'b0), .x6(1'b0), .x7(1'b0) ); + +// In all modes, let the ADC's outputs be enabled. +assign adc_noe = 1'b0; + +endmodule diff --git a/fpga-xc3s100e/fpga_allinone.v b/fpga/fpga_icopyx_top.v similarity index 61% rename from fpga-xc3s100e/fpga_allinone.v rename to fpga/fpga_icopyx_top.v index e766181f2..81aacb73c 100644 --- a/fpga-xc3s100e/fpga_allinone.v +++ b/fpga/fpga_icopyx_top.v @@ -1,37 +1,61 @@ -////////////////////////////////////////////////////////////////////////////////// -// Company: -// Engineer: +//----------------------------------------------------------------------------- +// Copyright (C) Proxmark3 contributors. See AUTHORS.md for details. // -// Create Date: 16:09:14 05/13/2020 -// Design Name: -// Module Name: fpga_all_in_one -// Project Name: -// Target Devices: -// Tool versions: -// Description: +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. // -// Dependencies: +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. // -// Revision: -// Revision 0.01 - File Created -// Additional Comments: +// See LICENSE.txt for the text of the license. +//----------------------------------------------------------------------------- // -////////////////////////////////////////////////////////////////////////////////// -module fpga_hf( - input spck, output miso, input mosi, input ncs, - input pck0, input ck_1356meg, input ck_1356megb, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, output adc_noe, - output ssp_frame, output ssp_din, input ssp_dout, output ssp_clk, - input cross_hi, input cross_lo, +// The FPGA is responsible for interfacing between the A/D, the coil drivers, +// and the ARM. In the low-frequency modes it passes the data straight +// through, so that the ARM gets raw A/D samples over the SSP. In the high- +// frequency modes, the FPGA might perform some demodulation first, to +// reduce the amount of data that we must send to the ARM. +//----------------------------------------------------------------------------- +//`include "fpga_lf.v" +//`include "fpga_hf.v" +//`include "mux2_onein.v" +//`include "mux2_oneout.v" +//`include "util.v" + +module fpga_top( + input spck, + output miso, + input mosi, + input ncs, + input pck0, + input ck_1356meg, + input ck_1356megb, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + input [7:0] adc_d, + output adc_clk, + output adc_noe, + output ssp_frame, + output ssp_din, + input ssp_dout, + output ssp_clk, + input cross_hi, + input cross_lo, output dbg, output PWR_LO_EN, input FPGA_SWITCH ); -fpga_hfmod hfmod( +fpga_hf hfmod( hfspck, hfmiso, hfmosi, hfncs, hfpck0, hfck_1356meg, hfck_1356megb, hfpwr_lo, hfpwr_hi, @@ -39,10 +63,10 @@ fpga_hfmod hfmod( adc_d, hfadc_clk, hfadc_noe, hfssp_frame, hfssp_din, hfssp_dout, hfssp_clk, hfcross_hi, hfcross_lo, - hfdbg + hfdebug ); -fpga_lfmod lfmod( +fpga_lf lfmod( lfspck, lfmiso, lfmosi, lfncs, lfpck0, lfck_1356meg, lfck_1356megb, lfpwr_lo, lfpwr_hi, @@ -50,7 +74,7 @@ fpga_lfmod lfmod( adc_d, lfadc_clk, lfadc_noe, lfssp_frame, lfssp_din, lfssp_dout, lfssp_clk, lfcross_hi, lfcross_lo, - lfdbg, + lfdebug, lfPWR_LO_EN ); @@ -75,7 +99,7 @@ mux2_oneout mux_ssp_dout_all (FPGA_SWITCH, ssp_dout, hfss mux2_one mux_ssp_clk_all (FPGA_SWITCH, ssp_clk, hfssp_clk, lfssp_clk); mux2_oneout mux_cross_hi_all (FPGA_SWITCH, cross_hi, hfcross_hi, lfcross_hi); mux2_oneout mux_cross_lo_all (FPGA_SWITCH, cross_lo, hfcross_lo, lfcross_lo); -mux2_one mux_dbg_all (FPGA_SWITCH, dbg, hfdbg, lfdbg); +mux2_one mux_dbg_all (FPGA_SWITCH, dbg, hfdebug, lfdebug); mux2_one mux_PWR_LO_EN_all (FPGA_SWITCH, PWR_LO_EN, 1'b0, lfPWR_LO_EN); endmodule diff --git a/fpga/fpga_pm3_felica.bit b/fpga/fpga_pm3_felica.bit new file mode 100644 index 000000000..a903f180e Binary files /dev/null and b/fpga/fpga_pm3_felica.bit differ diff --git a/fpga/fpga_pm3_hf.bit b/fpga/fpga_pm3_hf.bit new file mode 100644 index 000000000..76dcb8d98 Binary files /dev/null and b/fpga/fpga_pm3_hf.bit differ diff --git a/fpga/fpga_pm3_hf_15.bit b/fpga/fpga_pm3_hf_15.bit new file mode 100644 index 000000000..92a00a357 Binary files /dev/null and b/fpga/fpga_pm3_hf_15.bit differ diff --git a/fpga/fpga_pm3_lf.bit b/fpga/fpga_pm3_lf.bit new file mode 100644 index 000000000..593a9031f Binary files /dev/null and b/fpga/fpga_pm3_lf.bit differ diff --git a/fpga/fpga_pm3_top.v b/fpga/fpga_pm3_top.v new file mode 100644 index 000000000..89bd2e56b --- /dev/null +++ b/fpga/fpga_pm3_top.v @@ -0,0 +1,438 @@ +//----------------------------------------------------------------------------- +// Copyright (C) Proxmark3 contributors. See AUTHORS.md for details. +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// See LICENSE.txt for the text of the license. +//----------------------------------------------------------------------------- +// +// The FPGA is responsible for interfacing between the A/D, the coil drivers, +// and the ARM. In the low-frequency modes it passes the data straight +// through, so that the ARM gets raw A/D samples over the SSP. In the high- +// frequency modes, the FPGA might perform some demodulation first, to +// reduce the amount of data that we must send to the ARM. +//----------------------------------------------------------------------------- +/* +Once upon a time the FPGA had a 16 input mux so we could have all LF and HF modules enabled and selectable +As the functionality grew, we run out of space in the FPGA and we had to split into an "LF only" and an "HF only" FPGA bitstream +But even then after a while it was not possible to fit all the HF functions at the same time so now we have multiple "HF only" bitstreams +For example "Felica but without ISO14443", or "ISO14443 but without Felica" or "HF_15 but without Felica and ISO14443" + +Because of all of the above, you can not enable both HF and LF modes at the same time, because some LF modules outputs +map to the same mux inputs as some HF modules outputs (thanks to reducing the mux from 16 to 8 inputs) and you can not have +multiple outputs connected together therefore leading to a failed compilation +*/ + +// These defines are meant to be passed by the Makefile so do not uncomment them here +// Proxmark3 RDV4 target +//`define PM3RDV4 +// Proxmark3 generic target +//`define PM3GENERIC +// iCopy-X with XC3S100E +//`define PM3ICOPYX + +// Pass desired defines to compiler to enable required modules +// WITH_LF enables Low Frequency mode when defined else HF is enabled +//`define WITH_LF +// WITH_LF0 enables module reader +//`define WITH_LF0 +// WITH_LF1 enables module edge detect +//`define WITH_LF1 +// WITH_LF2 enables module passthrough +//`define WITH_LF2 +// WITH_LF3 enables module ADC +//`define WITH_LF3 + +// WITH_HF0 enables module HF reader +//`define WITH_HF0 +// WITH_HF1 enables module simulated tag +//`define WITH_HF1 +// WITH_HF2 enables module ISO14443-A +//`define WITH_HF2 +// WITH_HF3 enables module sniff +//`define WITH_HF3 +// WITH_HF4 enables module ISO18092 FeliCa +//`define WITH_HF4 +// WITH_HF5 enables module get trace +//`define WITH_HF5 + +//`include "define.v" +//`include "util.v" +// +//`ifdef WITH_LF `include "clk_divider.v" `endif +//`ifdef WITH_LF0 `include "lo_read.v" `endif +//`ifdef WITH_LF1 `include "lo_edge_detect.v" `endif +//`ifdef WITH_LF2 `include "lo_passthru.v" `endif +//`ifdef WITH_LF3 `include "lo_adc.v" `endif +// +//`ifdef WITH_HF_15 +//`ifdef WITH_HF0 `include "hi_reader_15.v" `endif +//`else +//`ifdef WITH_HF0 `include "hi_reader.v" `endif +//`endif +//`ifdef WITH_HF1 `include "hi_simulate.v" `endif +//`ifdef WITH_HF2 `include "hi_iso14443a.v" `endif +//`ifdef WITH_HF3 `include "hi_sniffer.v" `endif +//`ifdef WITH_HF4 `include "hi_flite.v" `endif +//`ifdef WITH_HF5 `include "hi_get_trace.v" `endif + +module fpga_top( + input ck_1356meg, + input ck_1356megb, + input spck, + input pck0, + input ncs, + input [7:0] adc_d, + input cross_hi, + input cross_lo, + input mosi, + input ssp_dout, + + output ssp_din, + output ssp_frame, + output ssp_clk, + output adc_clk, + output adc_noe, + output miso, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + output dbg +); + +// In all modes, let the ADC's outputs be enabled. +assign adc_noe = 1'b0; + +//----------------------------------------------------------------------------- +// The SPI receiver. This sets up the configuration word, which the rest of +// the logic looks at to determine how to connect the A/D and the coil +// drivers (i.e., which section gets it). Also assign some symbolic names +// to the configuration bits, for use below. +//----------------------------------------------------------------------------- + +// Receive 16bits of data from ARM here. +reg [15:0] shift_reg; +always @(posedge spck) if (~ncs) shift_reg <= {shift_reg[14:0], mosi}; + +reg trace_enable; + +reg [7:0] lf_ed_threshold; + +// adjustable frequency clock +wire [7:0] pck_cnt; +wire pck_divclk; +reg [7:0] divisor; +clk_divider div_clk(pck0, divisor, pck_cnt, pck_divclk); + +`ifdef WITH_LF +reg [11:0] conf_word; +`else +reg [8:0] conf_word; +`endif + +// We switch modes between transmitting to the 13.56 MHz tag and receiving +// from it, which means that we must make sure that we can do so without +// glitching, or else we will glitch the transmitted carrier. +always @(posedge ncs) +begin + // 4 bit command + case (shift_reg[15:12]) +`ifdef WITH_LF + `FPGA_CMD_SET_CONFREG: + begin + // 12 bit data + conf_word <= shift_reg[11:0]; + if (shift_reg[8:6] == `FPGA_MAJOR_MODE_LF_EDGE_DETECT) lf_ed_threshold <= 127; // default threshold + end + + `FPGA_CMD_SET_DIVISOR: + divisor <= shift_reg[7:0]; // 8bits + + `FPGA_CMD_SET_EDGE_DETECT_THRESHOLD: + lf_ed_threshold <= shift_reg[7:0]; // 8 bits +`else + `FPGA_CMD_SET_CONFREG: conf_word <= shift_reg[8:0]; + `FPGA_CMD_TRACE_ENABLE: trace_enable <= shift_reg[0]; +`endif + endcase +end + +//----------------------------------------------------------------------------- +// And then we instantiate the modules corresponding to each of the FPGA's +// major modes, and use muxes to connect the outputs of the active mode to +// the output pins. +//----------------------------------------------------------------------------- + +// ############################################################################ +// # Enable Low Frequency Modules +`ifdef WITH_LF + +// LF reader (generic) +`ifdef WITH_LF0 +lo_read lr( + .pck0 (pck0), + .pck_divclk (pck_divclk), + .pck_cnt (pck_cnt), + .adc_d (adc_d), + .lf_field (conf_word[0]), + + .ssp_din (mux0_ssp_din), + .ssp_frame (mux0_ssp_frame), + .ssp_clk (mux0_ssp_clk), + .adc_clk (mux0_adc_clk), + .pwr_lo (mux0_pwr_lo), + .pwr_hi (mux0_pwr_hi), + .pwr_oe1 (mux0_pwr_oe1), + .pwr_oe2 (mux0_pwr_oe2), + .pwr_oe3 (mux0_pwr_oe3), + .pwr_oe4 (mux0_pwr_oe4), + .debug (mux0_debug) +); +`endif + +// LF edge detect (generic) +`ifdef WITH_LF1 +lo_edge_detect le( + .pck0 (pck0), + .pck_divclk (pck_divclk), + .adc_d (adc_d), + .cross_lo (cross_lo), + .lf_field (conf_word[0]), + .lf_ed_toggle_mode (conf_word[1]), + .lf_ed_threshold (lf_ed_threshold), + .ssp_dout (ssp_dout), + + .ssp_frame (mux1_ssp_frame), + .ssp_clk (mux1_ssp_clk), + .adc_clk (mux1_adc_clk), + .pwr_lo (mux1_pwr_lo), + .pwr_hi (mux1_pwr_hi), + .pwr_oe1 (mux1_pwr_oe1), + .pwr_oe2 (mux1_pwr_oe2), + .pwr_oe3 (mux1_pwr_oe3), + .pwr_oe4 (mux1_pwr_oe4), + .debug (mux1_debug) +); +`endif + +// LF passthrough +`ifdef WITH_LF2 +lo_passthru lp( + .pck_divclk (pck_divclk), + .cross_lo (cross_lo), + .ssp_dout (ssp_dout), + + .ssp_din (mux2_ssp_din), + .adc_clk (mux2_adc_clk), + .pwr_lo (mux2_pwr_lo), + .pwr_hi (mux2_pwr_hi), + .pwr_oe1 (mux2_pwr_oe1), + .pwr_oe2 (mux2_pwr_oe2), + .pwr_oe3 (mux2_pwr_oe3), + .pwr_oe4 (mux2_pwr_oe4), + .debug (mux2_debug) +); +`endif + +// LF ADC (read/write) +`ifdef WITH_LF3 +lo_adc la( + .pck0 (pck0), + .adc_d (adc_d), + .divisor (divisor), + .lf_field (conf_word[0]), + .ssp_dout (ssp_dout), + + .ssp_din (mux3_ssp_din), + .ssp_frame (mux3_ssp_frame), + .ssp_clk (mux3_ssp_clk), + .adc_clk (mux3_adc_clk), + .pwr_lo (mux3_pwr_lo ), + .pwr_hi (mux3_pwr_hi ), + .pwr_oe1 (mux3_pwr_oe1), + .pwr_oe2 (mux3_pwr_oe2), + .pwr_oe3 (mux3_pwr_oe3), + .pwr_oe4 (mux3_pwr_oe4), + .debug (mux3_debug) +); +`endif // WITH_LF3 + +assign mux6_pwr_lo = 1'b1; +// 7 -- SPARE + +`else // if WITH_LF not defined +// ############################################################################ +// # Enable High Frequency Modules + +// HF reader +`ifdef WITH_HF0 +`ifdef WITH_HF_15 +hi_reader_15 hr( +`else +hi_reader hr( +`endif + .ck_1356meg (ck_1356megb), + .adc_d (adc_d), + .subcarrier_frequency (conf_word[5:4]), + .minor_mode (conf_word[3:0]), + .ssp_dout (ssp_dout), + + .ssp_din (mux0_ssp_din), + .ssp_frame (mux0_ssp_frame), + .ssp_clk (mux0_ssp_clk), + .adc_clk (mux0_adc_clk), + .pwr_lo (mux0_pwr_lo), + .pwr_hi (mux0_pwr_hi), + .pwr_oe1 (mux0_pwr_oe1), + .pwr_oe2 (mux0_pwr_oe2), + .pwr_oe3 (mux0_pwr_oe3), + .pwr_oe4 (mux0_pwr_oe4), + .debug (mux0_debug) +); +`endif // WITH_HF0 + +// HF simulated tag +`ifdef WITH_HF1 +hi_simulate hs( + .ck_1356meg (ck_1356meg), + .adc_d (adc_d), + .mod_type (conf_word[3:0]), + .ssp_dout (ssp_dout), + + .ssp_din (mux1_ssp_din), + .ssp_frame (mux1_ssp_frame), + .ssp_clk (mux1_ssp_clk), + .adc_clk (mux1_adc_clk), + .pwr_lo (mux1_pwr_lo), + .pwr_hi (mux1_pwr_hi), + .pwr_oe1 (mux1_pwr_oe1), + .pwr_oe2 (mux1_pwr_oe2), + .pwr_oe3 (mux1_pwr_oe3), + .pwr_oe4 (mux1_pwr_oe4), + .debug (mux1_debug) +); +`endif // WITH_HF1 + +// HF ISO14443-A +`ifdef WITH_HF2 +hi_iso14443a hisn( + .ck_1356meg (ck_1356meg), + .adc_d (adc_d), + .mod_type (conf_word[3:0]), + .ssp_dout (ssp_dout), + + .ssp_din (mux2_ssp_din), + .ssp_frame (mux2_ssp_frame), + .ssp_clk (mux2_ssp_clk), + .adc_clk (mux2_adc_clk), + .pwr_lo (mux2_pwr_lo), + .pwr_hi (mux2_pwr_hi), + .pwr_oe1 (mux2_pwr_oe1), + .pwr_oe2 (mux2_pwr_oe2), + .pwr_oe3 (mux2_pwr_oe3), + .pwr_oe4 (mux2_pwr_oe4), + .debug (mux2_debug) +); +`endif // WITH_HF2 + +// HF sniff +`ifdef WITH_HF3 +hi_sniffer he( + .ck_1356meg (ck_1356megb), + .adc_d (adc_d), + + .ssp_din (mux3_ssp_din), + .ssp_frame (mux3_ssp_frame), + .ssp_clk (mux3_ssp_clk), + .adc_clk (mux3_adc_clk), + .pwr_lo (mux3_pwr_lo), + .pwr_hi (mux3_pwr_hi), + .pwr_oe1 (mux3_pwr_oe1), + .pwr_oe2 (mux3_pwr_oe2), + .pwr_oe3 (mux3_pwr_oe3), + .pwr_oe4 (mux3_pwr_oe4) +); +`endif //WITH_HF3 + +// HF ISO18092 FeliCa +`ifdef WITH_HF4 +hi_flite hfl( + .ck_1356meg (ck_1356megb), + .adc_d (adc_d), + .mod_type (conf_word[3:0]), + .ssp_dout (ssp_dout), + + .ssp_din (mux4_ssp_din), + .ssp_frame (mux4_ssp_frame), + .ssp_clk (mux4_ssp_clk), + .adc_clk (mux4_adc_clk), + .pwr_lo (mux4_pwr_lo), + .pwr_hi (mux4_pwr_hi), + .pwr_oe1 (mux4_pwr_oe1), + .pwr_oe2 (mux4_pwr_oe2), + .pwr_oe3 (mux4_pwr_oe3), + .pwr_oe4 (mux4_pwr_oe4), + .debug (mux4_debug) +); +`endif // WITH_HF4 + +// HF get trace +`ifdef WITH_HF5 +hi_get_trace gt( + .ck_1356megb (ck_1356megb), + .adc_d (adc_d), + .trace_enable (trace_enable), + .major_mode (conf_word[8:6]), + .ssp_din (mux5_ssp_din), + .ssp_frame (mux5_ssp_frame), + .ssp_clk (mux5_ssp_clk) +); +`endif // WITH_HF5 + +`endif // WITH_LF + +// These assignments must agree with the defines in fpgaloader.h +// Major modes Low Frequency +// mux0 = LF reader (generic) +// mux1 = LF edge detect (generic) +// mux2 = LF passthrough +// mux3 = LF ADC (read/write) +// mux4 = SPARE +// mux5 = SPARE +// mux6 = SPARE +// mux7 = FPGA_MAJOR_MODE_OFF + +// Major modes High Frequency +// mux0 = HF reader +// mux1 = HF simulated tag +// mux2 = HF ISO14443-A +// mux3 = HF sniff +// mux4 = HF ISO18092 FeliCa +// mux5 = HF get trace +// mux6 = unused +// mux7 = FPGA_MAJOR_MODE_OFF + +mux8 mux_ssp_clk (.sel(conf_word[8:6]), .y(ssp_clk ), .x0(mux0_ssp_clk ), .x1(mux1_ssp_clk ), .x2(mux2_ssp_clk ), .x3(mux3_ssp_clk ), .x4(mux4_ssp_clk ), .x5(mux5_ssp_clk ), .x6(mux6_ssp_clk ), .x7(mux7_ssp_clk ) ); +mux8 mux_ssp_din (.sel(conf_word[8:6]), .y(ssp_din ), .x0(mux0_ssp_din ), .x1(mux1_ssp_din ), .x2(mux2_ssp_din ), .x3(mux3_ssp_din ), .x4(mux4_ssp_din ), .x5(mux5_ssp_din ), .x6(mux6_ssp_din ), .x7(mux7_ssp_din ) ); +mux8 mux_ssp_frame (.sel(conf_word[8:6]), .y(ssp_frame), .x0(mux0_ssp_frame), .x1(mux1_ssp_frame), .x2(mux2_ssp_frame), .x3(mux3_ssp_frame), .x4(mux4_ssp_frame), .x5(mux5_ssp_frame), .x6(mux6_ssp_frame), .x7(mux7_ssp_frame) ); +mux8 mux_pwr_oe1 (.sel(conf_word[8:6]), .y(pwr_oe1 ), .x0(mux0_pwr_oe1 ), .x1(mux1_pwr_oe1 ), .x2(mux2_pwr_oe1 ), .x3(mux3_pwr_oe1 ), .x4(mux4_pwr_oe1 ), .x5(mux5_pwr_oe1 ), .x6(mux6_pwr_oe1 ), .x7(mux7_pwr_oe1 ) ); +mux8 mux_pwr_oe2 (.sel(conf_word[8:6]), .y(pwr_oe2 ), .x0(mux0_pwr_oe2 ), .x1(mux1_pwr_oe2 ), .x2(mux2_pwr_oe2 ), .x3(mux3_pwr_oe2 ), .x4(mux4_pwr_oe2 ), .x5(mux5_pwr_oe2 ), .x6(mux6_pwr_oe2 ), .x7(mux7_pwr_oe2 ) ); +mux8 mux_pwr_oe3 (.sel(conf_word[8:6]), .y(pwr_oe3 ), .x0(mux0_pwr_oe3 ), .x1(mux1_pwr_oe3 ), .x2(mux2_pwr_oe3 ), .x3(mux3_pwr_oe3 ), .x4(mux4_pwr_oe3 ), .x5(mux5_pwr_oe3 ), .x6(mux6_pwr_oe3 ), .x7(mux7_pwr_oe3 ) ); +mux8 mux_pwr_oe4 (.sel(conf_word[8:6]), .y(pwr_oe4 ), .x0(mux0_pwr_oe4 ), .x1(mux1_pwr_oe4 ), .x2(mux2_pwr_oe4 ), .x3(mux3_pwr_oe4 ), .x4(mux4_pwr_oe4 ), .x5(mux5_pwr_oe4 ), .x6(mux6_pwr_oe4 ), .x7(mux7_pwr_oe4 ) ); +mux8 mux_pwr_lo (.sel(conf_word[8:6]), .y(pwr_lo ), .x0(mux0_pwr_lo ), .x1(mux1_pwr_lo ), .x2(mux2_pwr_lo ), .x3(mux3_pwr_lo ), .x4(mux4_pwr_lo ), .x5(mux5_pwr_lo ), .x6(mux6_pwr_lo ), .x7(mux7_pwr_lo ) ); +mux8 mux_pwr_hi (.sel(conf_word[8:6]), .y(pwr_hi ), .x0(mux0_pwr_hi ), .x1(mux1_pwr_hi ), .x2(mux2_pwr_hi ), .x3(mux3_pwr_hi ), .x4(mux4_pwr_hi ), .x5(mux5_pwr_hi ), .x6(mux6_pwr_hi ), .x7(mux7_pwr_hi ) ); +mux8 mux_adc_clk (.sel(conf_word[8:6]), .y(adc_clk ), .x0(mux0_adc_clk ), .x1(mux1_adc_clk ), .x2(mux2_adc_clk ), .x3(mux3_adc_clk ), .x4(mux4_adc_clk ), .x5(mux5_adc_clk ), .x6(mux6_adc_clk ), .x7(mux7_adc_clk ) ); +mux8 mux_dbg (.sel(conf_word[8:6]), .y(dbg ), .x0(mux0_debug ), .x1(mux1_debug ), .x2(mux2_debug ), .x3(mux3_debug ), .x4(mux4_debug ), .x5(mux5_debug ), .x6(mux6_debug ), .x7(mux7_debug ) ); + +endmodule diff --git a/fpga-xc2s30/hi_flite.v b/fpga/hi_flite.v similarity index 92% rename from fpga-xc2s30/hi_flite.v rename to fpga/hi_flite.v index 75ffbc9e5..ac9e7e069 100644 --- a/fpga-xc2s30/hi_flite.v +++ b/fpga/hi_flite.v @@ -30,33 +30,30 @@ */ module hi_flite( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, - mod_type + input ck_1356meg, + input [7:0] adc_d, + input [3:0] mod_type, + input ssp_dout, + + output reg ssp_din, + output reg ssp_frame, + output reg ssp_clk, + output adc_clk, + output reg pwr_lo, + output reg pwr_hi, + output reg pwr_oe1, + output reg pwr_oe2, + output reg pwr_oe3, + output reg pwr_oe4, + output debug ); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [3:0] mod_type; -assign dbg = 0; +assign debug = 0; -wire power = mod_type[2]; -wire speed = mod_type[1]; +wire power = mod_type[2]; +wire speed = mod_type[1]; wire disabl = mod_type[0]; -// Most off, oe4 for modulation; -// Trying reader emulation (would presumably just require switching power on, but I am not sure) -assign pwr_lo = 1'b0; -assign pwr_oe2 = 1'b0; - // 512x64/fc -wait before ts0, 32768 ticks // tslot: 256*64/fc assign adc_clk = ck_1356meg; @@ -95,10 +92,6 @@ reg did_sync=0; wire [7:0] bithalf = speed ? `bithalf_424 : `bithalf_212; wire [7:0] bitmlen = speed ? `bitmlen_424 : `bitmlen_212; - -//ssp clock and current values -reg ssp_clk; -reg ssp_frame; reg curbit = 1'b0; reg [7:0] fccount = 8'd0; // in-bit tick counter. Counts carrier cycles from the first lower edge detected, reset on every manchester bit detected @@ -107,6 +100,7 @@ reg [7:0] tsinceedge = 8'd0;// ticks from last edge, desync if the valye is too reg zero = 1'b0; // Manchester first halfbit low second high corresponds to this value. It has been known to change. SYNC is used to set it +//ssp clock and current values //ssp counter for transfer and framing reg [8:0] ssp_cnt = 9'd0; @@ -122,6 +116,7 @@ begin if( ((~speed) && (ssp_cnt[5:0] == 6'b000000)) || (speed && (ssp_cnt[4:0] == 5'b00000))) begin ssp_clk <= 1'b1; + //send current bit (detected in SNIFF mode or the one being modulated in MOD mode, 0 otherwise) ssp_din <= curbit; end if( ( (~speed) && (ssp_cnt[5:0] == 6'b100000)) ||(speed && ssp_cnt[4:0] == 5'b10000)) @@ -138,9 +133,6 @@ begin end end -//send current bit (detected in SNIFF mode or the one being modulated in MOD mode, 0 otherwise) -reg ssp_din; - //previous signal value, mostly to detect SYNC reg prv = 1'b1; @@ -353,11 +345,8 @@ begin end // sending <= 0; end + //put modulation here to maintain the correct clock. Seems that some readers are sensitive to that -reg pwr_hi; -reg pwr_oe1; -reg pwr_oe3; -reg pwr_oe4; wire mod = ((fccount >= bithalf) ^ dlay) & (~disabl); @@ -365,21 +354,22 @@ always @(ck_1356meg or ssp_dout or power or disabl or mod) begin if (power) begin - pwr_hi <= ck_1356meg; + pwr_hi <= ck_1356meg; + pwr_lo <= 1'b0; pwr_oe1 <= 1'b0;//mod; + pwr_oe2 <= 1'b0;//mod; pwr_oe3 <= 1'b0;//mod; pwr_oe4 <= mod;//1'b0; end else begin - pwr_hi <= 1'b0; + pwr_hi <= 1'b0; + pwr_lo <= 1'b0; pwr_oe1 <= 1'b0; + pwr_oe2 <= 1'b0; pwr_oe3 <= 1'b0; pwr_oe4 <= mod; end end - - - endmodule diff --git a/fpga-xc2s30/hi_get_trace.v b/fpga/hi_get_trace.v similarity index 86% rename from fpga-xc2s30/hi_get_trace.v rename to fpga/hi_get_trace.v index 6e4369e14..9bf32bc64 100644 --- a/fpga-xc2s30/hi_get_trace.v +++ b/fpga/hi_get_trace.v @@ -13,17 +13,18 @@ // // See LICENSE.txt for the text of the license. //----------------------------------------------------------------------------- +//`include "define.v" module hi_get_trace( - ck_1356megb, - adc_d, trace_enable, major_mode, - ssp_frame, ssp_din, ssp_clk + input ck_1356megb, + input [7:0] adc_d, + input trace_enable, + input [2:0] major_mode, + + output ssp_din, + output reg ssp_frame, + output reg ssp_clk ); - input ck_1356megb; - input [7:0] adc_d; - input trace_enable; - input [2:0] major_mode; - output ssp_frame, ssp_din, ssp_clk; // clock divider reg [6:0] clock_cnt; @@ -88,9 +89,9 @@ begin write_enable2 <= 1'b0; end else - begin + begin addr <= addr + 1; - end + end end end else @@ -136,9 +137,6 @@ begin end -// SSC communication to ARM -reg ssp_clk; -reg ssp_frame; reg [7:0] shift_out; always @(negedge ck_1356megb) @@ -147,16 +145,16 @@ begin begin if (clock_cnt[6:4] == 3'd0) // either load new value begin - if (addr[11] == 1'b0) - shift_out <= D_out1; - else - shift_out <= D_out2; + if (addr[11] == 1'b0) + shift_out <= D_out1; + else + shift_out <= D_out2; end else - begin - // or shift left - shift_out[7:1] <= shift_out[6:0]; - end + begin + // or shift left + shift_out[7:1] <= shift_out[6:0]; + end end ssp_clk <= ~clock_cnt[3]; // ssp_clk frequency = 13,56MHz / 16 = 847,5 kHz diff --git a/fpga-xc2s30/hi_iso14443a.v b/fpga/hi_iso14443a.v similarity index 97% rename from fpga-xc2s30/hi_iso14443a.v rename to fpga/hi_iso14443a.v index d52ab4000..7ccd7f610 100644 --- a/fpga-xc2s30/hi_iso14443a.v +++ b/fpga/hi_iso14443a.v @@ -14,29 +14,28 @@ // See LICENSE.txt for the text of the license. //----------------------------------------------------------------------------- // ISO14443-A support for the Proxmark III -// +//`include "define.v" module hi_iso14443a( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, - mod_type + input ck_1356meg, + input [7:0] adc_d, + input [3:0] mod_type, + input ssp_dout, + + output ssp_din, + output reg ssp_frame, + output reg ssp_clk, + output adc_clk, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + output debug ); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [3:0] mod_type; - - -wire adc_clk = ck_1356meg; - +assign adc_clk = ck_1356meg; //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // Reader -> PM3: @@ -76,8 +75,6 @@ begin end - - //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // Reader -> PM3 // detect when a reader is active (modulating). We assume that the reader is active, if we see the carrier off for at least 8 @@ -137,7 +134,6 @@ wire [9:0] tmp2 = adc_d_times_2 + input_prev_1; wire signed [10:0] adc_d_filtered = {1'b0, tmp1} - {1'b0, tmp2}; - //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // internal FPGA timing. Maximum required period is 128 carrier clock cycles for a full 8 Bit transfer to ARM. (i.e. we need a // 7 bit counter). Adjust its frequency to external reader's clock when simulating a tag or sniffing. @@ -222,7 +218,11 @@ reg signed [10:0] rx_mod_falling_edge_max; reg signed [10:0] rx_mod_rising_edge_max; reg curbit; +`ifdef PM3ICOPYX +`define EDGE_DETECT_THRESHOLD 3 +`else `define EDGE_DETECT_THRESHOLD 5 +`endif `define EDGE_DETECT_THRESHOLDHIGH 20 always @(negedge adc_clk) @@ -266,7 +266,6 @@ begin end - //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // Tag+Reader -> PM3 // sample 4 bits reader data and 4 bits tag data for sniffing @@ -283,7 +282,6 @@ begin end - //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // PM3 -> Reader: // a delay line to ensure that we send the (emulated) tag's answer at the correct time according to ISO14443-3 @@ -307,7 +305,6 @@ begin end - //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // PM3 -> Reader, internal timing: // a timer for the 1172 cycles fdt (Frame Delay Time). Start the timer with a rising edge of the reader's signal. @@ -400,7 +397,6 @@ begin end - //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // PM3 -> Reader // determine the required delay in the mod_sig_buf (set mod_sig_ptr). @@ -444,7 +440,6 @@ begin end - //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // FPGA -> ARM communication: // buffer 8 bits data to be sent to ARM. Shift them out bit by bit. @@ -495,8 +490,6 @@ end //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // FPGA <-> ARM communication: // generate a ssp clock and ssp frame signal for the synchronous transfer from/to the ARM -reg ssp_clk; -reg ssp_frame; always @(negedge adc_clk) begin @@ -529,7 +522,6 @@ begin end - //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// // FPGA -> ARM communication: // select the data to be sent to ARM @@ -553,7 +545,6 @@ begin sendbit = 1'b0; end - if(mod_type == `FPGA_HF_ISO14443A_SNIFFER) // send sampled reader and tag data: bit_to_arm = to_arm[7]; @@ -589,6 +580,6 @@ assign pwr_oe4 = mod_sig_coil & sub_carrier & (mod_type == `FPGA_HF_ISO14443A_TA assign pwr_oe2 = 1'b0; assign pwr_lo = 1'b0; -assign dbg = negedge_cnt[3]; +assign debug = negedge_cnt[3]; endmodule diff --git a/fpga-xc2s30/hi_reader.v b/fpga/hi_reader.v similarity index 95% rename from fpga-xc2s30/hi_reader.v rename to fpga/hi_reader.v index dbc38a8a7..ffa2634d8 100644 --- a/fpga-xc2s30/hi_reader.v +++ b/fpga/hi_reader.v @@ -13,24 +13,27 @@ // // See LICENSE.txt for the text of the license. //----------------------------------------------------------------------------- +//`include "define.v" module hi_reader( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, - subcarrier_frequency, minor_mode + input ck_1356meg, + input [7:0] adc_d, + input [1:0] subcarrier_frequency, + input [3:0] minor_mode, + input ssp_dout, + + output ssp_din, + output reg ssp_frame, + output reg ssp_clk, + output adc_clk, + output pwr_lo, + output reg pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output reg pwr_oe4, + output debug ); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [1:0] subcarrier_frequency; - input [3:0] minor_mode; assign adc_clk = ck_1356meg; // sample frequency is 13,56 MHz @@ -160,7 +163,6 @@ begin end else if (minor_mode == `FPGA_HF_READER_MODE_SNIFF_IQ) begin - // Send 7 most significant bits of in phase tag signal (signed), plus 1 bit reader signal if (corr_i_accum[13:11] == 3'b000 || corr_i_accum[13:11] == 3'b111) corr_i_out <= {corr_i_accum[11:5], after_hysteresis_prev_prev}; @@ -261,9 +263,6 @@ end // corr_i_cnt 0 1 2 3 4 5 6 7 8 9 10 11 12 ... // -reg ssp_clk; -reg ssp_frame; - always @(negedge adc_clk) begin if (corr_i_cnt[1:0] == 2'b00) @@ -298,9 +297,6 @@ begin end end -// Antenna drivers -reg pwr_hi, pwr_oe4; - always @(*) begin if (minor_mode == `FPGA_HF_READER_MODE_SEND_SHALLOW_MOD) @@ -341,6 +337,6 @@ assign pwr_lo = 1'b0; assign pwr_oe2 = 1'b0; // Debug Output -assign dbg = corr_i_cnt[3]; +assign debug = corr_i_cnt[3]; endmodule diff --git a/fpga-xc2s30/hi_reader_15.v b/fpga/hi_reader_15.v similarity index 96% rename from fpga-xc2s30/hi_reader_15.v rename to fpga/hi_reader_15.v index 0db4fe2a3..ad41e771c 100644 --- a/fpga-xc2s30/hi_reader_15.v +++ b/fpga/hi_reader_15.v @@ -14,25 +14,26 @@ // See LICENSE.txt for the text of the license. //----------------------------------------------------------------------------- // modified to add support for iso15 2sc mode -// -module hi_15_reader( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, - subcarrier_frequency, minor_mode +module hi_reader_15( + input ck_1356meg, + input [7:0] adc_d, + input [1:0] subcarrier_frequency, + input [3:0] minor_mode, + input ssp_dout, + + output ssp_din, + output reg ssp_frame, + output reg ssp_clk, + output adc_clk, + output pwr_lo, + output reg pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output reg pwr_oe4, + output debug ); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [1:0] subcarrier_frequency; - input [3:0] minor_mode; assign adc_clk = ck_1356meg; // sample frequency is 13,56 MHz @@ -379,9 +380,6 @@ end // corr_i_cnt 0 1 2 3 4 5 6 7 8 9 10 11 12 ... // -reg ssp_clk; -reg ssp_frame; - always @(negedge adc_clk) begin if (corr_i_cnt[1:0] == 2'b00) @@ -416,9 +414,6 @@ begin end end -// Antenna drivers -reg pwr_hi, pwr_oe4; - always @(*) begin if (minor_mode == `FPGA_HF_READER_MODE_SEND_SHALLOW_MOD) @@ -459,6 +454,6 @@ assign pwr_lo = 1'b0; assign pwr_oe2 = 1'b0; // Debug Output -assign dbg = corr_i_cnt[3]; +assign debug = corr_i_cnt[3]; endmodule diff --git a/fpga-xc2s30/hi_simulate.v b/fpga/hi_simulate.v similarity index 91% rename from fpga-xc2s30/hi_simulate.v rename to fpga/hi_simulate.v index 2232aedd9..97346eb9b 100644 --- a/fpga-xc2s30/hi_simulate.v +++ b/fpga/hi_simulate.v @@ -30,23 +30,26 @@ // // Jonathan Westhues, October 2006 //----------------------------------------------------------------------------- +//`include "define.v" module hi_simulate( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, - mod_type + input ck_1356meg, + input [7:0] adc_d, + input [3:0] mod_type, + input ssp_dout, + + output reg ssp_din, + output reg ssp_frame, + output reg ssp_clk, + output adc_clk, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + output debug ); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [3:0] mod_type; // Power amp goes between LOW and tri-state, so pwr_hi (and pwr_lo) can // always be low. @@ -57,7 +60,7 @@ assign pwr_lo = 1'b0; // LF antenna connected to GND assign pwr_oe2 = 1'b0; assign adc_clk = ck_1356meg; -assign dbg = ssp_frame; +assign debug = ssp_frame; // The comparator with hysteresis on the output from the peak detector. reg after_hysteresis; @@ -94,8 +97,6 @@ reg [8:0] ssp_clk_divider; always @(negedge adc_clk) ssp_clk_divider <= (ssp_clk_divider + 1); -reg ssp_clk; - always @(negedge adc_clk) begin if (mod_type == `FPGA_HF_SIMULATOR_MODULATE_424K_8BIT) @@ -112,7 +113,6 @@ end // Produce the byte framing signal; the phase of this signal // is arbitrary, because it's just a bit stream in this module. -reg ssp_frame; always @(negedge adc_clk) begin if (mod_type == `FPGA_HF_SIMULATOR_MODULATE_212K) @@ -133,7 +133,6 @@ end // Synchronize up the after-hysteresis signal, to produce DIN. -reg ssp_din; always @(posedge ssp_clk) ssp_din = after_hysteresis; diff --git a/fpga-xc2s30/hi_sniffer.v b/fpga/hi_sniffer.v similarity index 69% rename from fpga-xc2s30/hi_sniffer.v rename to fpga/hi_sniffer.v index ed62191f1..11781ca5a 100644 --- a/fpga-xc2s30/hi_sniffer.v +++ b/fpga/hi_sniffer.v @@ -15,16 +15,20 @@ //----------------------------------------------------------------------------- module hi_sniffer( - ck_1356meg, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_clk + input ck_1356meg, + input [7:0] adc_d, + + output ssp_din, + output reg ssp_frame, + output ssp_clk, + output adc_clk, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4 ); - input ck_1356meg; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - output ssp_frame, ssp_din, ssp_clk; // We are only snooping, all off. assign pwr_hi = 1'b0; @@ -34,12 +38,13 @@ assign pwr_oe2 = 1'b0; assign pwr_oe3 = 1'b0; assign pwr_oe4 = 1'b0; -reg ssp_frame; +//reg ssp_frame; reg [7:0] adc_d_out = 8'd0; -reg [2:0] ssp_cnt = 3'd0; +reg [2:0] ssp_cnt = 3'd0; -assign adc_clk = ck_1356meg; +assign adc_clk = ck_1356meg; assign ssp_clk = ~ck_1356meg; +assign ssp_din = adc_d_out[0]; always @(posedge ssp_clk) begin @@ -49,18 +54,16 @@ begin ssp_cnt <= ssp_cnt + 1; if(ssp_cnt[2:0] == 3'b000) // set frame length - begin - adc_d_out[7:0] <= adc_d; - ssp_frame <= 1'b1; - end + begin + adc_d_out[7:0] <= adc_d; + ssp_frame <= 1'b1; + end else - begin - adc_d_out[7:0] <= {1'b0, adc_d_out[7:1]}; - ssp_frame <= 1'b0; - end + begin + // shift value right one bit + adc_d_out[7:0] <= {1'b0, adc_d_out[7:1]}; + ssp_frame <= 1'b0; + end end - -assign ssp_din = adc_d_out[0]; - endmodule diff --git a/fpga-xc2s30/lf_edge_detect.v b/fpga/lf_edge_detect.v similarity index 72% rename from fpga-xc2s30/lf_edge_detect.v rename to fpga/lf_edge_detect.v index 4b6c0ac01..2a58331d1 100644 --- a/fpga-xc2s30/lf_edge_detect.v +++ b/fpga/lf_edge_detect.v @@ -15,23 +15,37 @@ // See LICENSE.txt for the text of the license. //----------------------------------------------------------------------------- - // input clk is 24MHz -`include "min_max_tracker.v" +//`include "min_max_tracker.v" -module lf_edge_detect(input clk, input [7:0] adc_d, input [7:0] lf_ed_threshold, - output [7:0] max, output [7:0] min, - output [7:0] high_threshold, output [7:0] highz_threshold, - output [7:0] lowz_threshold, output [7:0] low_threshold, - output edge_state, output edge_toggle); +module lf_edge_detect( + input clk, + input [7:0] adc_d, + input [7:0] lf_ed_threshold, - min_max_tracker tracker(clk, adc_d, lf_ed_threshold, min, max); + output [7:0] max, + output [7:0] min, + output [7:0] low_threshold, + output [7:0] high_threshold, + output [7:0] lowz_threshold, + output [7:0] highz_threshold, + output edge_state, + output edge_toggle +); + + min_max_tracker tracker( + .clk (clk), + .adc_d (adc_d), + .threshold (lf_ed_threshold), + .min (min), + .max (max) +); // auto-tune - assign high_threshold = (max + min) / 2 + (max - min) / 4; + assign high_threshold = (max + min) / 2 + (max - min) / 4; assign highz_threshold = (max + min) / 2 + (max - min) / 8; - assign lowz_threshold = (max + min) / 2 - (max - min) / 8; - assign low_threshold = (max + min) / 2 - (max - min) / 4; + assign lowz_threshold = (max + min) / 2 - (max - min) / 8; + assign low_threshold = (max + min) / 2 - (max - min) / 4; // heuristic to see if it makes sense to try to detect an edge wire enabled = @@ -55,18 +69,20 @@ module lf_edge_detect(input clk, input [7:0] adc_d, input [7:0] lf_ed_threshold, always @(posedge clk) begin is_high <= (adc_d >= high_threshold); - is_low <= (adc_d <= low_threshold); + is_low <= (adc_d <= low_threshold); is_zero <= ((adc_d > lowz_threshold) & (adc_d < highz_threshold)); end // all edges detection always @(posedge clk) - if (enabled) begin + if (enabled) + begin // To enable detecting two consecutive peaks at the same level // (low or high) we check whether or not we went back near 0 in-between. // This extra check is necessary to prevent from noise artifacts // around the threshold values. - if (trigger_enabled & (is_high | is_low)) begin + if (trigger_enabled & (is_high | is_low)) + begin output_edge <= ~output_edge; trigger_enabled <= 0; end else @@ -75,14 +91,15 @@ module lf_edge_detect(input clk, input [7:0] adc_d, input [7:0] lf_ed_threshold, // edge states always @(posedge clk) - if (enabled) begin + if (enabled) + begin if (is_high) output_state <= 1'd1; else if (is_low) output_state <= 1'd0; end - assign edge_state = output_state; + assign edge_state = output_state; assign edge_toggle = output_edge; endmodule diff --git a/fpga-xc2s30/lo_adc.v b/fpga/lo_adc.v similarity index 74% rename from fpga-xc2s30/lo_adc.v rename to fpga/lo_adc.v index 808ec96ed..475cc869f 100644 --- a/fpga-xc2s30/lo_adc.v +++ b/fpga/lo_adc.v @@ -22,22 +22,24 @@ //----------------------------------------------------------------------------- module lo_adc( - pck0, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - dbg, divisor, - lf_field + input pck0, + input [7:0] adc_d, + input [7:0] divisor, + input lf_field, + input ssp_dout, + + output ssp_din, + output ssp_frame, + output ssp_clk, + output adc_clk, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + output debug ); - input pck0; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - output dbg; - input [7:0] divisor; - input lf_field; reg [7:0] to_arm_shiftreg; reg [7:0] pck_divider; @@ -49,16 +51,16 @@ wire reader_modulation = !ssp_dout & lf_field & clk_state; // always on (High Frequency outputs, unused) assign pwr_oe1 = 1'b0; -assign pwr_hi = 1'b0; +assign pwr_hi = 1'b0; // low frequency outputs -assign pwr_lo = reader_modulation; +assign pwr_lo = reader_modulation; assign pwr_oe2 = 1'b0; // 33 Ohms assign pwr_oe3 = tag_modulation; // base antenna load = 33 Ohms assign pwr_oe4 = 1'b0; // 10k Ohms // Debug Output ADC clock -assign dbg = adc_clk; +assign debug = adc_clk; // ADC clock out of phase with antenna driver assign adc_clk = ~clk_state; @@ -76,10 +78,10 @@ assign ssp_frame = (pck_divider[7:3] == 5'd1) && !clk_state; always @(posedge pck0) begin if (pck_divider == divisor[7:0]) - begin + begin pck_divider <= 8'd0; clk_state = !clk_state; - end + end else begin pck_divider <= pck_divider + 1; @@ -92,13 +94,9 @@ always @(posedge pck0) begin if ((pck_divider == 8'd7) && !clk_state) to_arm_shiftreg <= adc_d; - else begin + else + begin to_arm_shiftreg[7:1] <= to_arm_shiftreg[6:0]; - // simulation showed a glitch occurring due to the LSB of the shifter - // not being set as we shift bits out - // this ensures the ssp_din remains low after a transfer and suppresses - // the glitch that would occur when the last data shifted out ended in - // a 1 bit and the next data shifted out started with a 0 bit to_arm_shiftreg[0] <= 1'b0; end end diff --git a/fpga-xc2s30/lo_edge_detect.v b/fpga/lo_edge_detect.v similarity index 67% rename from fpga-xc2s30/lo_edge_detect.v rename to fpga/lo_edge_detect.v index 462dfcc46..c820466f7 100644 --- a/fpga-xc2s30/lo_edge_detect.v +++ b/fpga/lo_edge_detect.v @@ -25,19 +25,29 @@ // - ssp_frame (wired to TIOA1 on the arm) for the edge detection/state // - ssp_clk: cross_lo -`include "lp20khz_1MSa_iir_filter.v" -`include "lf_edge_detect.v" +//`include "lp20khz_1MSa_iir_filter.v" +//`include "lf_edge_detect.v" module lo_edge_detect( - input pck0, input pck_divclk, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, - output ssp_frame, input ssp_dout, output ssp_clk, + input pck0, + input pck_divclk, + input [7:0] adc_d, input cross_lo, - output dbg, input lf_field, - input lf_ed_toggle_mode, input [7:0] lf_ed_threshold + input lf_ed_toggle_mode, + input [7:0] lf_ed_threshold, + input ssp_dout, + + output ssp_frame, + output ssp_clk, + output adc_clk, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + output debug ); wire tag_modulation = ssp_dout & !lf_field; @@ -58,18 +68,34 @@ assign pwr_hi = 1'b0; wire data_rdy; wire [7:0] adc_filtered; assign adc_clk = pck0; -lp20khz_1MSa_iir_filter adc_filter(pck0, adc_d, data_rdy, adc_filtered); + +lp20khz_1MSa_iir_filter adc_filter( + .clk (pck0), + .adc_d (adc_d), + .rdy (data_rdy), + .out (adc_filtered) +); // detect edges wire [7:0] high_threshold, highz_threshold, lowz_threshold, low_threshold; wire [7:0] max, min; wire edge_state, edge_toggle; -lf_edge_detect lf_ed(pck0, adc_filtered, lf_ed_threshold, - max, min, - high_threshold, highz_threshold, lowz_threshold, low_threshold, - edge_state, edge_toggle); -assign dbg = lf_ed_toggle_mode ? edge_toggle : edge_state; +lf_edge_detect lf_ed( + .clk (pck0), + .adc_d (adc_filtered), + .lf_ed_threshold (lf_ed_threshold), + .max (max), + .min (min), + .high_threshold (high_threshold), + .highz_threshold (highz_threshold), + .lowz_threshold (lowz_threshold), + .low_threshold (low_threshold), + .edge_state (edge_state), + .edge_toggle (edge_toggle) +); + +assign debug = lf_ed_toggle_mode ? edge_toggle : edge_state; assign ssp_frame = lf_ed_toggle_mode ? edge_toggle : edge_state; diff --git a/fpga-xc2s30/lo_passthru.v b/fpga/lo_passthru.v similarity index 82% rename from fpga-xc2s30/lo_passthru.v rename to fpga/lo_passthru.v index 52e56d4c5..a5ae1d4e2 100644 --- a/fpga-xc2s30/lo_passthru.v +++ b/fpga/lo_passthru.v @@ -17,27 +17,32 @@ // For reading TI tags, we need to place the FPGA in pass through mode // and pass everything through to the ARM - module lo_passthru( input pck_divclk, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - output adc_clk, - output ssp_din, input ssp_dout, input cross_lo, - output dbg + input ssp_dout, + + output ssp_din, + output adc_clk, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + output debug ); // the antenna is modulated when ssp_dout = 1, when 0 the // antenna drivers stop modulating and go into listen mode -assign pwr_oe3 = 1'b0; +assign ssp_din = cross_lo; +assign adc_clk = 1'b0; +assign pwr_lo = pck_divclk && ssp_dout; +assign pwr_hi = 1'b0; assign pwr_oe1 = ssp_dout; assign pwr_oe2 = ssp_dout; +assign pwr_oe3 = 1'b0; assign pwr_oe4 = ssp_dout; -assign pwr_lo = pck_divclk && ssp_dout; -assign pwr_hi = 1'b0; -assign adc_clk = 1'b0; -assign ssp_din = cross_lo; -assign dbg = cross_lo; +assign debug = cross_lo; endmodule diff --git a/fpga-xc2s30/lo_read.v b/fpga/lo_read.v similarity index 80% rename from fpga-xc2s30/lo_read.v rename to fpga/lo_read.v index a7e481654..06bd0ae5a 100644 --- a/fpga-xc2s30/lo_read.v +++ b/fpga/lo_read.v @@ -22,13 +22,23 @@ //----------------------------------------------------------------------------- module lo_read( - input pck0, input [7:0] pck_cnt, input pck_divclk, - output pwr_lo, output pwr_hi, - output pwr_oe1, output pwr_oe2, output pwr_oe3, output pwr_oe4, - input [7:0] adc_d, output adc_clk, - output ssp_frame, output ssp_din, output ssp_clk, - output dbg, - input lf_field + input pck0, + input pck_divclk, + input [7:0] pck_cnt, + input [7:0] adc_d, + input lf_field, + + output ssp_din, + output ssp_frame, + output ssp_clk, + output adc_clk, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + output debug ); reg [7:0] to_arm_shiftreg; @@ -43,13 +53,9 @@ always @(posedge pck0) begin if((pck_cnt == 8'd7) && !pck_divclk) to_arm_shiftreg <= adc_d; - else begin + else + begin to_arm_shiftreg[7:1] <= to_arm_shiftreg[6:0]; - // simulation showed a glitch occurring due to the LSB of the shifter - // not being set as we shift bits out - // this ensures the ssp_din remains low after a transfer and suppresses - // the glitch that would occur when the last data shifted out ended in - // a 1 bit and the next data shifted out started with a 0 bit to_arm_shiftreg[0] <= 1'b0; end end @@ -74,7 +80,7 @@ assign ssp_clk = pck0; // SSP frame is gated by ant_lo and goes high when pck_divider=8..15 assign ssp_frame = (pck_cnt[7:3] == 5'd1) && !pck_divclk; // unused signals tied low -assign pwr_hi = 1'b0; +assign pwr_hi = 1'b0; assign pwr_oe1 = 1'b0; assign pwr_oe2 = 1'b0; assign pwr_oe3 = 1'b0; @@ -84,5 +90,5 @@ assign pwr_lo = lf_field & pck_divclk; // ADC clock out of phase with antenna driver assign adc_clk = ~pck_divclk; // ADC clock also routed to debug pin -assign dbg = adc_clk; +assign debug = adc_clk; endmodule diff --git a/fpga-xc2s30/lo_simulate.v b/fpga/lo_simulate.v similarity index 79% rename from fpga-xc2s30/lo_simulate.v rename to fpga/lo_simulate.v index 89b548c73..c3f819cd7 100644 --- a/fpga-xc2s30/lo_simulate.v +++ b/fpga/lo_simulate.v @@ -22,23 +22,27 @@ //----------------------------------------------------------------------------- module lo_simulate( - pck0, ck_1356meg, ck_1356megb, - pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4, - adc_d, adc_clk, - ssp_frame, ssp_din, ssp_dout, ssp_clk, - cross_hi, cross_lo, - dbg, - divisor + input pck0, + input ck_1356meg, + input ck_1356megb, + input [7:0] adc_d, + input [7:0] divisor, + input cross_hi, + input cross_lo, + input ssp_dout, + + output ssp_din, + output ssp_frame, + output ssp_clk, + output adc_clk, + output pwr_lo, + output pwr_hi, + output pwr_oe1, + output pwr_oe2, + output pwr_oe3, + output pwr_oe4, + output debug ); - input pck0, ck_1356meg, ck_1356megb; - output pwr_lo, pwr_hi, pwr_oe1, pwr_oe2, pwr_oe3, pwr_oe4; - input [7:0] adc_d; - output adc_clk; - input ssp_dout; - output ssp_frame, ssp_din, ssp_clk; - input cross_hi, cross_lo; - output dbg; - input [7:0] divisor; // No logic, straight through. assign pwr_oe3 = 1'b0; @@ -46,9 +50,9 @@ assign pwr_oe1 = ssp_dout; assign pwr_oe2 = ssp_dout; assign pwr_oe4 = ssp_dout; assign ssp_clk = cross_lo; -assign pwr_lo = 1'b0; -assign pwr_hi = 1'b0; -assign dbg = ssp_frame; +assign pwr_lo = 1'b0; +assign pwr_hi = 1'b0; +assign debug = ssp_frame; // Divide the clock to be used for the ADC reg [7:0] pck_divider; diff --git a/fpga-xc2s30/lp20khz_1MSa_iir_filter.v b/fpga/lp20khz_1MSa_iir_filter.v similarity index 96% rename from fpga-xc2s30/lp20khz_1MSa_iir_filter.v rename to fpga/lp20khz_1MSa_iir_filter.v index 8bc6cca4f..d4a16cde1 100644 --- a/fpga-xc2s30/lp20khz_1MSa_iir_filter.v +++ b/fpga/lp20khz_1MSa_iir_filter.v @@ -36,7 +36,12 @@ // See details about its design see // https://fail0verflow.com/blog/2014/proxmark3-fpga-iir-filter.html -module lp20khz_1MSa_iir_filter(input clk, input [7:0] adc_d, output rdy, output [7:0] out); +module lp20khz_1MSa_iir_filter( + input clk, + input [7:0] adc_d, + output rdy, + output [7:0] out +); // clk is 24MHz, the IIR filter is designed for 1MS/s // hence we need to divide it by 24 diff --git a/fpga-xc2s30/min_max_tracker.v b/fpga/min_max_tracker.v similarity index 95% rename from fpga-xc2s30/min_max_tracker.v rename to fpga/min_max_tracker.v index 210d3c666..2f6e06017 100644 --- a/fpga-xc2s30/min_max_tracker.v +++ b/fpga/min_max_tracker.v @@ -23,8 +23,13 @@ // This algorithm therefore can't be used directly for realtime peak detections, // but it can be used as a simple envelope follower. -module min_max_tracker(input clk, input [7:0] adc_d, input [7:0] threshold, - output [7:0] min, output [7:0] max); +module min_max_tracker( + input clk, + input [7:0] adc_d, + input [7:0] threshold, + output [7:0] min, + output [7:0] max +); reg [7:0] min_val = 255; reg [7:0] max_val = 0; diff --git a/fpga/mux16.v b/fpga/mux16.v new file mode 100644 index 000000000..1d9777706 --- /dev/null +++ b/fpga/mux16.v @@ -0,0 +1,50 @@ +//----------------------------------------------------------------------------- +// Copyright (C) Proxmark3 contributors. See AUTHORS.md for details. +// +// This program is free software: you can redistribute it and/or modify +// it under the terms of the GNU General Public License as published by +// the Free Software Foundation, either version 3 of the License, or +// (at your option) any later version. +// +// This program is distributed in the hope that it will be useful, +// but WITHOUT ANY WARRANTY; without even the implied warranty of +// MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the +// GNU General Public License for more details. +// +// See LICENSE.txt for the text of the license. +//----------------------------------------------------------------------------- +// +// General-purpose miscellany. +// + +// 16 inputs to 1 output multiplexer +module mux16( + input [3:0] sel, + output reg y, + input x0, x1, x2, x3, x4, x5, x6, x7, x8, x9, x10, x11, x12, x13, x14, x15 +); + +always @(*) +begin + // y = x[sel]; + case (sel) + 4'd0: y = x0; + 4'd1: y = x1; + 4'd2: y = x2; + 4'd3: y = x3; + 4'd4: y = x4; + 4'd5: y = x5; + 4'd6: y = x6; + 4'd7: y = x7; + 4'd8: y = x8; + 4'd9: y = x9; + 4'd10: y = x10; + 4'd11: y = x11; + 4'd12: y = x12; + 4'd13: y = x13; + 4'd14: y = x14; + 4'd15: y = x15; + endcase +end + +endmodule diff --git a/fpga-xc3s100e/mux2_onein.v b/fpga/mux2_onein.v similarity index 70% rename from fpga-xc3s100e/mux2_onein.v rename to fpga/mux2_onein.v index 86f17a553..baefa72c8 100644 --- a/fpga-xc3s100e/mux2_onein.v +++ b/fpga/mux2_onein.v @@ -4,13 +4,14 @@ // kombi, 2020.05 //----------------------------------------------------------------------------- -module mux2_one(sel, y, x0, x1); - input [1:0] sel; - input x0, x1; - output y; - reg y; +module mux2_one( + input [1:0] sel, + output reg y, + input x0, + input x1 +); -always @(x0 or x1 or sel) +always @(*) begin case (sel) 1'b0: y = x1; diff --git a/fpga-xc3s100e/mux2_oneout.v b/fpga/mux2_oneout.v similarity index 68% rename from fpga-xc3s100e/mux2_oneout.v rename to fpga/mux2_oneout.v index 3cbc0fd6b..fa61205a2 100644 --- a/fpga-xc3s100e/mux2_oneout.v +++ b/fpga/mux2_oneout.v @@ -4,13 +4,14 @@ // kombi, 2020.05 //----------------------------------------------------------------------------- -module mux2_oneout(sel, y, x0, x1); - input [1:0] sel; - output x0, x1; - input y; - reg x0, x1; +module mux2_oneout( + input [1:0] sel, + input y, + output reg x0, + output reg x1 +); -always @(x0 or x1 or sel) +always @(*) begin case (sel) 1'b0: x1 = y; diff --git a/fpga-xc2s30/util.v b/fpga/mux8.v similarity index 68% rename from fpga-xc2s30/util.v rename to fpga/mux8.v index 66361ca59..d9118d243 100644 --- a/fpga-xc2s30/util.v +++ b/fpga/mux8.v @@ -17,23 +17,25 @@ // General-purpose miscellany. // -module mux8(sel, y, x0, x1, x2, x3, x4, x5, x6, x7); - input [2:0] sel; - input x0, x1, x2, x3, x4, x5, x6, x7; - output y; - reg y; +// 8 inputs to 1 output multiplexer +module mux8( + input [2:0] sel, + output reg y, + input x0, x1, x2, x3, x4, x5, x6, x7 +); -always @(x0 or x1 or x2 or x3 or x4 or x5 or x6 or x7 or sel) +always @(*) begin + // y = x[sel]; case (sel) - 3'b000: y = x0; - 3'b001: y = x1; - 3'b010: y = x2; - 3'b011: y = x3; - 3'b100: y = x4; - 3'b101: y = x5; - 3'b110: y = x6; - 3'b111: y = x7; + 3'd0: y = x0; + 3'd1: y = x1; + 3'd2: y = x2; + 3'd3: y = x3; + 3'd4: y = x4; + 3'd5: y = x5; + 3'd6: y = x6; + 3'd7: y = x7; endcase end diff --git a/fpga-xc2s30/tests/Makefile b/fpga/tests/Makefile similarity index 100% rename from fpga-xc2s30/tests/Makefile rename to fpga/tests/Makefile diff --git a/fpga-xc2s30/tests/plot_edgedetect.py b/fpga/tests/plot_edgedetect.py old mode 100755 new mode 100644 similarity index 100% rename from fpga-xc2s30/tests/plot_edgedetect.py rename to fpga/tests/plot_edgedetect.py diff --git a/fpga-xc2s30/sim.tcl b/fpga/tests/sim.tcl similarity index 100% rename from fpga-xc2s30/sim.tcl rename to fpga/tests/sim.tcl diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.filtered.gold b/fpga/tests/tb_data/pcf7931_read_1MSA_data.filtered.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.filtered.gold rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.filtered.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.high.gold b/fpga/tests/tb_data/pcf7931_read_1MSA_data.high.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.high.gold rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.high.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.highz.gold b/fpga/tests/tb_data/pcf7931_read_1MSA_data.highz.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.highz.gold rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.highz.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.in b/fpga/tests/tb_data/pcf7931_read_1MSA_data.in similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.in rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.in diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.low.gold b/fpga/tests/tb_data/pcf7931_read_1MSA_data.low.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.low.gold rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.low.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.lowz.gold b/fpga/tests/tb_data/pcf7931_read_1MSA_data.lowz.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.lowz.gold rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.lowz.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.max.gold b/fpga/tests/tb_data/pcf7931_read_1MSA_data.max.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.max.gold rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.max.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.min.gold b/fpga/tests/tb_data/pcf7931_read_1MSA_data.min.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.min.gold rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.min.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.state.gold b/fpga/tests/tb_data/pcf7931_read_1MSA_data.state.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.state.gold rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.state.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.time b/fpga/tests/tb_data/pcf7931_read_1MSA_data.time similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.time rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.time diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.toggle.gold b/fpga/tests/tb_data/pcf7931_read_1MSA_data.toggle.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_read_1MSA_data.toggle.gold rename to fpga/tests/tb_data/pcf7931_read_1MSA_data.toggle.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.filtered.gold b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.filtered.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.filtered.gold rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.filtered.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.high.gold b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.high.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.high.gold rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.high.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.highz.gold b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.highz.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.highz.gold rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.highz.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.in b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.in similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.in rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.in diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.low.gold b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.low.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.low.gold rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.low.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.lowz.gold b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.lowz.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.lowz.gold rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.lowz.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.max.gold b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.max.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.max.gold rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.max.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.min.gold b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.min.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.min.gold rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.min.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.state.gold b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.state.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.state.gold rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.state.gold diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.time b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.time similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.time rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.time diff --git a/fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.toggle.gold b/fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.toggle.gold similarity index 100% rename from fpga-xc2s30/tests/tb_data/pcf7931_write1byte_1MSA_data.toggle.gold rename to fpga/tests/tb_data/pcf7931_write1byte_1MSA_data.toggle.gold diff --git a/fpga-xc2s30/tests/tb_lf_edge_detect.v b/fpga/tests/tb_lf_edge_detect.v similarity index 100% rename from fpga-xc2s30/tests/tb_lf_edge_detect.v rename to fpga/tests/tb_lf_edge_detect.v diff --git a/fpga-xc2s30/tests/tb_lp20khz_1MSa_iir_filter.v b/fpga/tests/tb_lp20khz_1MSa_iir_filter.v similarity index 100% rename from fpga-xc2s30/tests/tb_lp20khz_1MSa_iir_filter.v rename to fpga/tests/tb_lp20khz_1MSa_iir_filter.v diff --git a/fpga-xc2s30/tests/tb_min_max_tracker.v b/fpga/tests/tb_min_max_tracker.v similarity index 100% rename from fpga-xc2s30/tests/tb_min_max_tracker.v rename to fpga/tests/tb_min_max_tracker.v diff --git a/fpga-xc2s30/testbed_fpga.v b/fpga/tests/testbed_fpga.v similarity index 100% rename from fpga-xc2s30/testbed_fpga.v rename to fpga/tests/testbed_fpga.v diff --git a/fpga-xc2s30/testbed_hi_read_tx.v b/fpga/tests/testbed_hi_read_tx.v similarity index 100% rename from fpga-xc2s30/testbed_hi_read_tx.v rename to fpga/tests/testbed_hi_read_tx.v diff --git a/fpga-xc2s30/testbed_hi_simulate.v b/fpga/tests/testbed_hi_simulate.v similarity index 100% rename from fpga-xc2s30/testbed_hi_simulate.v rename to fpga/tests/testbed_hi_simulate.v diff --git a/fpga-xc2s30/testbed_lo_read.v b/fpga/tests/testbed_lo_read.v similarity index 100% rename from fpga-xc2s30/testbed_lo_read.v rename to fpga/tests/testbed_lo_read.v diff --git a/fpga-xc2s30/testbed_lo_simulate.v b/fpga/tests/testbed_lo_simulate.v similarity index 100% rename from fpga-xc2s30/testbed_lo_simulate.v rename to fpga/tests/testbed_lo_simulate.v diff --git a/fpga/xc2s30-5-vq100.ucf b/fpga/xc2s30-5-vq100.ucf new file mode 100644 index 000000000..e42ce0d88 --- /dev/null +++ b/fpga/xc2s30-5-vq100.ucf @@ -0,0 +1,45 @@ +# See the schematic for the pin assignment. + +NET "adc_d<0>" LOC = "P62" ; +NET "adc_d<1>" LOC = "P60" ; +NET "adc_d<2>" LOC = "P58" ; +NET "adc_d<3>" LOC = "P57" ; +NET "adc_d<4>" LOC = "P56" ; +NET "adc_d<5>" LOC = "P55" ; +NET "adc_d<6>" LOC = "P54" ; +NET "adc_d<7>" LOC = "P53" ; +#NET "cross_hi" LOC = "P88" ; +#NET "miso" LOC = "P40" ; +NET "adc_clk" LOC = "P46" ; +NET "adc_noe" LOC = "P47" ; +NET "ck_1356meg" LOC = "P91" ; +NET "ck_1356megb" LOC = "P93" ; +NET "cross_lo" LOC = "P87" ; +NET "dbg" LOC = "P22" ; +NET "mosi" LOC = "P43" ; +NET "ncs" LOC = "P44" ; +NET "pck0" LOC = "P36" ; +NET "pwr_hi" LOC = "P80" ; +NET "pwr_lo" LOC = "P81" ; +NET "pwr_oe1" LOC = "P82" ; +NET "pwr_oe2" LOC = "P83" ; +NET "pwr_oe3" LOC = "P84" ; +NET "pwr_oe4" LOC = "P86" ; +NET "spck" LOC = "P39" ; +NET "ssp_clk" LOC = "P71" ; +NET "ssp_din" LOC = "P32" ; +NET "ssp_dout" LOC = "P34" ; +NET "ssp_frame" LOC = "P31" ; + +# definition of Clock nets: +NET "ck_1356meg" TNM_NET = "clk_net_1356" ; +NET "ck_1356megb" TNM_NET = "clk_net_1356b"; +NET "pck0" TNM_NET = "clk_net_pck0" ; +NET "spck" TNM_NET = "clk_net_spck" ; + +# Timing specs of clock nets: +TIMEGRP "clk_net_1356_all" = "clk_net_1356" "clk_net_1356b" ; +TIMESPEC "TS_1356MHz" = PERIOD "clk_net_1356_all" 74 ns HIGH 37 ns ; +TIMESPEC "TS_24MHz" = PERIOD "clk_net_pck0" 42 ns HIGH 21 ns ; +TIMESPEC "TS_4MHz" = PERIOD "clk_net_spck" 250 ns HIGH 125 ns ; + diff --git a/fpga/xc3s100e-4-vq100.ucf b/fpga/xc3s100e-4-vq100.ucf new file mode 100644 index 000000000..b259af2ed --- /dev/null +++ b/fpga/xc3s100e-4-vq100.ucf @@ -0,0 +1,48 @@ +# See the schematic for the pin assignment. + +NET "adc_d<0>" LOC = "P79" ; +NET "adc_d<1>" LOC = "P78" ; +NET "adc_d<2>" LOC = "P71" ; +NET "adc_d<3>" LOC = "P70" ; +NET "adc_d<4>" LOC = "P69" ; +NET "adc_d<5>" LOC = "P68" ; +NET "adc_d<6>" LOC = "P67" ; +NET "adc_d<7>" LOC = "P66" ; +#NET "cross_hi" LOC = "P88" ; +#NET "miso" LOC = "P40" ; +NET "adc_clk" LOC = "P65" ; +NET "adc_noe" LOC = "P62" ; +NET "ck_1356meg" LOC = "P88" ; +NET "ck_1356megb" LOC = "P89" ; +NET "cross_lo" LOC = "P90" ; +NET "dbg" LOC = "P22" ; +NET "mosi" LOC = "P43" ; +NET "ncs" LOC = "P40" ; +NET "pck0" LOC = "P36" ; +NET "pwr_hi" LOC = "P85" ; +NET "pwr_lo" LOC = "P83" ; +NET "pwr_oe1" LOC = "P84" ; +NET "pwr_oe2" LOC = "P91" ; +NET "pwr_oe3" LOC = "P92" ; +NET "pwr_oe4" LOC = "P86" ; +NET "spck" LOC = "P39" ; +NET "ssp_clk" LOC = "P33" ; +NET "ssp_din" LOC = "P32" ; +NET "ssp_dout" LOC = "P34" ; +NET "ssp_frame" LOC = "P27" ; +NET "FPGA_SWITCH" LOC = "P38" ; +NET "PWR_LO_EN" LOC = "P94" ; + +# definition of Clock nets: +NET "ck_1356meg" TNM_NET = "clk_net_1356" ; +NET "ck_1356megb" TNM_NET = "clk_net_1356b"; +NET "pck0" TNM_NET = "clk_net_pck0" ; +NET "spck" TNM_NET = "clk_net_spck" ; +NET "FPGA_SWITCH" CLOCK_DEDICATED_ROUTE = FALSE ; + +# Timing specs of clock nets: +TIMEGRP "clk_net_1356_all" = "clk_net_1356" "clk_net_1356b" ; +TIMESPEC "TS_1356MHz" = PERIOD "clk_net_1356_all" 74 ns HIGH 37 ns ; +TIMESPEC "TS_24MHz" = PERIOD "clk_net_pck0" 42 ns HIGH 21 ns ; +TIMESPEC "TS_4MHz" = PERIOD "clk_net_spck" 250 ns HIGH 125 ns ; + diff --git a/tools/fpga_compress/fpga_compress.c b/tools/fpga_compress/fpga_compress.c index 58b3a2162..0a66142ac 100644 --- a/tools/fpga_compress/fpga_compress.c +++ b/tools/fpga_compress/fpga_compress.c @@ -282,7 +282,8 @@ static int bitparse_find_section(FILE *infile, char section_name, unsigned int * /* Four byte length field */ for (int i = 0; i < 4; i++) { tmp = fgetc(infile); - if (tmp < 0) { + /* image length sanity check, should be under 300KB */ + if ( (tmp < 0) || (tmp > 300*1024) ) { break; } current_length += tmp << (24 - (i * 8)); @@ -292,7 +293,8 @@ static int bitparse_find_section(FILE *infile, char section_name, unsigned int * default: /* Fall through, two byte length field */ for (int i = 0; i < 2; i++) { tmp = fgetc(infile); - if (tmp < 0) { + /* if name, date or time fields are too long, we probably shouldn't parse them */ + if ( (tmp < 0) || (tmp > 64) ){ break; } current_length += tmp << (8 - (i * 8)); @@ -334,14 +336,16 @@ static int FpgaGatherVersion(FILE *infile, char *infile_name, char *dst, int len } } - if (!memcmp("fpga_lf", basename(infile_name), 7)) - strncat(dst, "LF", len - strlen(dst) - 1); - else if (!memcmp("fpga_hf_15", basename(infile_name), 10)) - strncat(dst, "HF 15", len - strlen(dst) - 1); - else if (!memcmp("fpga_hf.", basename(infile_name), 8)) - strncat(dst, "HF", len - strlen(dst) - 1); - else if (!memcmp("fpga_felica", basename(infile_name), 7)) - strncat(dst, "HF FeliCa", len - strlen(dst) - 1); + if (bitparse_find_section(infile, 'a', &fpga_info_len)) { + for (uint32_t i = 0; i < fpga_info_len; i++) { + char c = (char)fgetc(infile); + if (i < sizeof(tempstr)) { + tempstr[i] = c; + } + } + + strncat(dst, tempstr, len - strlen(dst) - 1); + } strncat(dst, " image ", len - strlen(dst) - 1); if (bitparse_find_section(infile, 'b', &fpga_info_len)) {