利用artix-7 100t读取microsd卡数据,现在遇到的问题是,我利用的源代码是mit 2015秋季的assiment,如下图
问题在于这个代码是jonathan matthews根据sandisk 2gb microsd1.1版本写的,我现在sd卡版本是32gb uhs-1版本已经是3.01
这个代码能够兼容新的32gb uhs-1吗?
mit 代码 http://web.mit.edu/6.111/volume2/www/f2019/tools/sd_controller.v
显示课件ppt http://web.mit.edu/6.111/volume2/www/f2019/tools/sd_audio.pdf
mit
/* SD Card controller module. Allows reading from and writing to a microSD card
through SPI mode. */
`timescale 1ns / 1ps
module sd_controller(
output reg cs, // Connect to SD_DAT[3].
output mosi, // Connect to SD_CMD.
input miso, // Connect to SD_DAT[0].
output sclk, // Connect to SD_SCK.
// For SPI mode, SD_DAT[2] and SD_DAT[1] should be held HIGH.
// SD_RESET should be held LOW.
input rd, // Read-enable. When [ready] is HIGH, asseting [rd] will
// begin a 512-byte READ operation at [address].
// [byte_available] will transition HIGH as a new byte has been
// read from the SD card. The byte is presented on [dout].
output reg [7:0] dout, // Data output for READ operation.
output reg byte_available, // A new byte has been presented on [dout].
input wr, // Write-enable. When [ready] is HIGH, asserting [wr] will
// begin a 512-byte WRITE operation at [address].
// [ready_for_next_byte] will transition HIGH to request that
// the next byte to be written should be presentaed on [din].
input [7:0] din, // Data input for WRITE operation.
output reg ready_for_next_byte, // A new byte should be presented on [din].
input reset, // Resets controller on assertion.
output ready, // HIGH if the SD card is ready for a read or write operation.
input [31:0] address, // Memory address for read/write operation. This MUST
// be a multiple of 512 bytes, due to SD sectoring.
input clk, // 25 MHz clock.
output [4:0] status // For debug purposes: Current state of controller.
);
parameter RST = 0;
parameter INIT = 1;
parameter CMD0 = 2;
parameter CMD55 = 3;
parameter CMD41 = 4;
parameter POLL_CMD = 5;
parameter IDLE = 6;
parameter READ_BLOCK = 7;
parameter READ_BLOCK_WAIT = 8;
parameter READ_BLOCK_DATA = 9;
parameter READ_BLOCK_CRC = 10;
parameter SEND_CMD = 11;
parameter RECEIVE_BYTE_WAIT = 12;
parameter RECEIVE_BYTE = 13;
parameter WRITE_BLOCK_CMD = 14;
parameter WRITE_BLOCK_INIT = 15;
parameter WRITE_BLOCK_DATA = 16;
parameter WRITE_BLOCK_BYTE = 17;
parameter WRITE_BLOCK_WAIT = 18;
parameter WRITE_DATA_SIZE = 515;
reg [4:0] state = RST;
assign status = state;
reg [4:0] return_state;
reg sclk_sig = 0;
reg [55:0] cmd_out;
reg [7:0] recv_data;
reg cmd_mode = 1;
reg [7:0] data_sig = 8'hFF;
reg [9:0] byte_counter;
reg [9:0] bit_counter;
reg [26:0] boot_counter = 27'd100_000_000;
always @(posedge clk) begin
if(reset == 1) begin
state <= RST;
sclk_sig <= 0;
boot_counter <= 27'd100_000_000;
end
else begin
case(state)
RST: begin
if(boot_counter == 0) begin
sclk_sig <= 0;
cmd_out <= {56{1'b1}};
byte_counter <= 0;
byte_available <= 0;
ready_for_next_byte <= 0;
cmd_mode <= 1;
bit_counter <= 160;
cs <= 1;
state <= INIT;
end
else begin
boot_counter <= boot_counter - 1;
end
end
INIT: begin
if(bit_counter == 0) begin
cs <= 0;
state <= CMD0;
end
else begin
bit_counter <= bit_counter - 1;
sclk_sig <= ~sclk_sig;
end
end
CMD0: begin
cmd_out <= 56'hFF_40_00_00_00_00_95;
bit_counter <= 55;
return_state <= CMD55;
state <= SEND_CMD;
end
CMD55: begin
cmd_out <= 56'hFF_77_00_00_00_00_01;
bit_counter <= 55;
return_state <= CMD41;
state <= SEND_CMD;
end
CMD41: begin
cmd_out <= 56'hFF_69_00_00_00_00_01;
bit_counter <= 55;
return_state <= POLL_CMD;
state <= SEND_CMD;
end
POLL_CMD: begin
if(recv_data[0] == 0) begin
state <= IDLE;
end
else begin
state <= CMD55;
end
end
IDLE: begin
if(rd == 1) begin
state <= READ_BLOCK;
end
else if(wr == 1) begin
state <= WRITE_BLOCK_CMD;
end
else begin
state <= IDLE;
end
end
READ_BLOCK: begin
cmd_out <= {16'hFF_51, address, 8'hFF};
bit_counter <= 55;
return_state <= READ_BLOCK_WAIT;
state <= SEND_CMD;
end
READ_BLOCK_WAIT: begin
if(sclk_sig == 1 && miso == 0) begin
byte_counter <= 511;
bit_counter <= 7;
return_state <= READ_BLOCK_DATA;
state <= RECEIVE_BYTE;
end
sclk_sig <= ~sclk_sig;
end
READ_BLOCK_DATA: begin
dout <= recv_data;
byte_available <= 1;
if (byte_counter == 0) begin
bit_counter <= 7;
return_state <= READ_BLOCK_CRC;
state <= RECEIVE_BYTE;
end
else begin
byte_counter <= byte_counter - 1;
return_state <= READ_BLOCK_DATA;
bit_counter <= 7;
state <= RECEIVE_BYTE;
end
end
READ_BLOCK_CRC: begin
bit_counter <= 7;
return_state <= IDLE;
state <= RECEIVE_BYTE;
end
SEND_CMD: begin
if (sclk_sig == 1) begin
if (bit_counter == 0) begin
state <= RECEIVE_BYTE_WAIT;
end
else begin
bit_counter <= bit_counter - 1;
cmd_out <= {cmd_out[54:0], 1'b1};
end
end
sclk_sig <= ~sclk_sig;
end
RECEIVE_BYTE_WAIT: begin
if (sclk_sig == 1) begin
if (miso == 0) begin
recv_data <= 0;
bit_counter <= 6;
state <= RECEIVE_BYTE;
end
end
sclk_sig <= ~sclk_sig;
end
RECEIVE_BYTE: begin
byte_available <= 0;
if (sclk_sig == 1) begin
recv_data <= {recv_data[6:0], miso};
if (bit_counter == 0) begin
state <= return_state;
end
else begin
bit_counter <= bit_counter - 1;
end
end
sclk_sig <= ~sclk_sig;
end
WRITE_BLOCK_CMD: begin
cmd_out <= {16'hFF_58, address, 8'hFF};
bit_counter <= 55;
return_state <= WRITE_BLOCK_INIT;
state <= SEND_CMD;
ready_for_next_byte <= 1;
end
WRITE_BLOCK_INIT: begin
cmd_mode <= 0;
byte_counter <= WRITE_DATA_SIZE;
state <= WRITE_BLOCK_DATA;
ready_for_next_byte <= 0;
end
WRITE_BLOCK_DATA: begin
if (byte_counter == 0) begin
state <= RECEIVE_BYTE_WAIT;
return_state <= WRITE_BLOCK_WAIT;
end
else begin
if ((byte_counter == 2) || (byte_counter == 1)) begin
data_sig <= 8'hFF;
end
else if (byte_counter == WRITE_DATA_SIZE) begin
data_sig <= 8'hFE;
end
else begin
data_sig <= din;
ready_for_next_byte <= 1;
end
bit_counter <= 7;
state <= WRITE_BLOCK_BYTE;
byte_counter <= byte_counter - 1;
end
end
WRITE_BLOCK_BYTE: begin
if (sclk_sig == 1) begin
if (bit_counter == 0) begin
state <= WRITE_BLOCK_DATA;
ready_for_next_byte <= 0;
end
else begin
data_sig <= {data_sig[6:0], 1'b1};
bit_counter <= bit_counter - 1;
end;
end;
sclk_sig <= ~sclk_sig;
end
WRITE_BLOCK_WAIT: begin
if (sclk_sig == 1) begin
if (miso == 1) begin
state <= IDLE;
cmd_mode <= 1;
end
end
sclk_sig = ~sclk_sig;
end
endcase
end
end
assign sclk = sclk_sig;
assign mosi = cmd_mode ? cmd_out[55] : data_sig[7];
assign ready = (state == IDLE);
endmodule