我正在尝试从FPGA到Arduino实现自己的SPI通信,其中我的FPGA充当MASTER并生成芯片使能和通信时钟。 FPGA在其上升沿发送数据,并在其下降沿接收数据,我的FPGA代码正常工作。
在Arduino端,我在中断时捕获该主时钟,并在其上升沿接收数据并在其下降沿发送,但如果我将时钟速度从10 KHz提高,则通信无法正常工作。
根据我的理解,Arduino Due工作在84 MHz,处理1 MHz中断不是一个大问题。你能告诉我如何用Arduino Due来处理这个高速时钟吗?
下面的Arduino代码:
void ISR1();
// this constant won't change
const int S_CLK = 19; // slow clock in this case FPGA is master
const int MOSI_C = 51; // Master out slave in in this case arduino
//receive data from FPGA
const int MISO_C = 50; // Master in slave out in this case arduino
//transmit data from FPGA
const int SS_C = 53; // the pin that the pushbutton is attached to
const int TRANS_INDEX = 32; //index that is used to transmit data in this
cas 32 bits are transmitted
const int REC_INDEX = 48;
#define CLK_MAIN 84000000UL
//Variables will change
int ss_check = 0; //used for reading of slave select
int mosi_data[REC_INDEX + 2]; //delcare receiving data array length
int count = 0; //used for convertion of bits to bytes
int index_r_stat = 0; //give us a value of status that
how much bits are received
int flag = 0; //used for stop reading s
int miso_out[TRANS_INDEX] = {
1, 0, 1, 0, 1, 0, 1, 1, 1, 0, 1, 1, 0, 1, 0, 0, 1, 1, 1, 0, 0, 0, 1, 0, 1, 1, 0, 1, 1, 0, 1, 0
};
int miso_index = 0; //used for above array
int last_clk_state = 1; //used for the detection of rising and
falling edge
int check_clk;
void setup() {
// initialize the button pin as a input
pinMode(S_CLK , INPUT);
pinMode(MOSI_C , INPUT);
pinMode(MISO_C , OUTPUT);
pinMode(SS_C , INPUT);
// initialize serial communication
Serial.begin(9600);
}
void loop() {
// read the pushbutton input pin
ss_check = digitalRead(SS_C);
//Serial.println(ss_check);
//WAIT until slave select is not read
if (ss_check == 0) {
//attach interrupt so that data is
attachInterrupt(digitalPinToInterrupt(S_CLK), ISR1, CHANGE);
}
if ((index_r_stat == (REC_INDEX + 1)) && (flag == 0)) {
for (int i = 1; i < (REC_INDEX + 1); i = i + 1) {
Serial.print(mosi_data[i]);
flag = 1;
if (count < 7) {
count = count + 1;
} else {
count = 0;
Serial.println();
}
}
}
}
void ISR1() {
if ((last_clk_state == 1) && (digitalRead(S_CLK) == 0)) {
check_clk = 0;
//this code is used to transmit data to FPGA
if (miso_index < TRANS_INDEX - 1) {
digitalWrite(MISO_C, miso_out[miso_index]);
miso_index = miso_index + 1;
} else {
miso_index = miso_index;
}
} else {
check_clk = 1;
//this code is used for reading data from FPGA
if (index_r_stat < (REC_INDEX + 1)) {
mosi_data[index_r_stat] = digitalRead( MOSI_C);
index_r_stat = index_r_stat + 1;
} else {
detachInterrupt(S_CLK);
index_r_stat = index_r_stat;
}
}
last_clk_state = digitalRead(S_CLK);
}