Compare commits

..

2 Commits

Author SHA1 Message Date
9af830daa0 comment clean up 2025-06-10 02:51:18 -07:00
53b48c0bce comment clean up for segment_display folder 2025-06-10 01:38:52 -07:00
10 changed files with 98 additions and 66 deletions

View File

@ -6,6 +6,9 @@
* @date: 6/12/2025 * @date: 6/12/2025
* *
* */ * */
//define used here because verilator needs it but vivado is smart enough
//not to.
`ifdef VERILATOR `ifdef VERILATOR
`include "sdvd_defs.sv" `include "sdvd_defs.sv"
`endif `endif
@ -72,8 +75,6 @@ always_ff @(posedge clk) begin
// This will overflow to the correct value always // This will overflow to the correct value always
address <= address + speed; address <= address + speed;
enb <= 1; enb <= 1;
// NOTE: I really don't know a good way to generate the load
// signal. It maybe could be an inverted 48khz clock?
if (delay == 0) begin if (delay == 0) begin
sample <= doutb; sample <= doutb;
end end
@ -86,59 +87,56 @@ always_ff @(posedge clk) begin
end end
end end
//xpm_memory_sdpram #( //vivado block ram xpm macro
// .WRITE_DATA_WIDTH_A(16)
//) buffer ();
xpm_memory_sdpram #( xpm_memory_sdpram #(
.ADDR_WIDTH_A(11), // DECIMAL .ADDR_WIDTH_A(11), // DECIMAL
.ADDR_WIDTH_B(10), // DECIMAL .ADDR_WIDTH_B(10), // DECIMAL
.AUTO_SLEEP_TIME(0), // DECIMAL .AUTO_SLEEP_TIME(0), // DECIMAL
.BYTE_WRITE_WIDTH_A(8), // DECIMAL .BYTE_WRITE_WIDTH_A(8), // DECIMAL
.CASCADE_HEIGHT(0), // DECIMAL .CASCADE_HEIGHT(0), // DECIMAL
.CLOCKING_MODE("independent_clock"), // String .CLOCKING_MODE("independent_clock"), // String
.ECC_BIT_RANGE("7:0"), // String .ECC_BIT_RANGE("7:0"), // String
.ECC_MODE("no_ecc"), // String .ECC_MODE("no_ecc"), // String
.ECC_TYPE("none"), // String .ECC_TYPE("none"), // String
.IGNORE_INIT_SYNTH(0), // DECIMAL .IGNORE_INIT_SYNTH(0), // DECIMAL
.MEMORY_INIT_FILE("none"), // String .MEMORY_INIT_FILE("none"), // String
.MEMORY_INIT_PARAM("0"), // String .MEMORY_INIT_PARAM("0"), // String
.MEMORY_OPTIMIZATION("true"), // String .MEMORY_OPTIMIZATION("true"), // String
.MEMORY_PRIMITIVE("auto"), // String .MEMORY_PRIMITIVE("auto"), // String
.MEMORY_SIZE(16*1024), // DECIMAL .MEMORY_SIZE(16*1024), // DECIMAL
.MESSAGE_CONTROL(0), // DECIMAL .MESSAGE_CONTROL(0), // DECIMAL
.RAM_DECOMP("auto"), // String .RAM_DECOMP("auto"), // String
.READ_DATA_WIDTH_B(16), // DECIMAL .READ_DATA_WIDTH_B(16), // DECIMAL
.READ_LATENCY_B(1), // DECIMAL .READ_LATENCY_B(1), // DECIMAL
.READ_RESET_VALUE_B("0"), // String .READ_RESET_VALUE_B("0"), // String
.RST_MODE_A("SYNC"), // String .RST_MODE_A("SYNC"), // String
.RST_MODE_B("SYNC"), // String .RST_MODE_B("SYNC"), // String
.SIM_ASSERT_CHK(0), // DECIMAL; 0=disable simulation messages, 1=enable simulation messages .SIM_ASSERT_CHK(0), // DECIMAL; 0=disable simulation messages, 1=enable simulation messages
.USE_EMBEDDED_CONSTRAINT(0), // DECIMAL .USE_EMBEDDED_CONSTRAINT(0), // DECIMAL
.USE_MEM_INIT(1), // DECIMAL .USE_MEM_INIT(1), // DECIMAL
.USE_MEM_INIT_MMI(0), // DECIMAL .USE_MEM_INIT_MMI(0), // DECIMAL
.WAKEUP_TIME("disable_sleep"), // String .WAKEUP_TIME("disable_sleep"), // String
.WRITE_DATA_WIDTH_A(8), // DECIMAL .WRITE_DATA_WIDTH_A(8), // DECIMAL
.WRITE_MODE_B("no_change"), // String .WRITE_MODE_B("no_change"), // String
.WRITE_PROTECT(1) // DECIMAL .WRITE_PROTECT(1) // DECIMAL
) )
buffer ( buffer (
.doutb(doutb), // READ_DATA_WIDTH_B-bit output: Data output for port B read operations. .doutb(doutb), // READ_DATA_WIDTH_B-bit output: Data output for port B read operations.
.addra(driver.addra), // ADDR_WIDTH_A-bit input: Address for port A write operations. .addra(driver.addra), // ADDR_WIDTH_A-bit input: Address for port A write operations.
.addrb(address), // ADDR_WIDTH_B-bit input: Address for port B read operations. .addrb(address), // ADDR_WIDTH_B-bit input: Address for port B read operations.
.clka(driver.clka), // 1-bit input: Clock signal for port A. Also clocks port B when .clka(driver.clka), // 1-bit input: Clock signal for port A. Also clocks port B when
// parameter CLOCKING_MODE is "common_clock". // parameter CLOCKING_MODE is "common_clock".
.clkb(clk), // 1-bit input: Clock signal for port B when parameter CLOCKING_MODE is .clkb(clk), // 1-bit input: Clock signal for port B when parameter CLOCKING_MODE is
// "independent_clock". Unused when parameter CLOCKING_MODE is // "independent_clock". Unused when parameter CLOCKING_MODE is
// "common_clock". // "common_clock".
.dina(driver.dina), // WRITE_DATA_WIDTH_A-bit input: Data input for port A write operations. .dina(driver.dina), // WRITE_DATA_WIDTH_A-bit input: Data input for port A write operations.
.ena(driver.ena), // 1-bit input: Memory enable signal for port A. Must be high on clock .ena(driver.ena), // 1-bit input: Memory enable signal for port A. Must be high on clock
// cycles when write operations are initiated. Pipelined internally. // cycles when write operations are initiated. Pipelined internally.
.enb(enb), // 1-bit input: Memory enable signal for port B. Must be high on clock .enb(enb), // 1-bit input: Memory enable signal for port B. Must be high on clock
// cycles when read operations are initiated. Pipelined internally. // cycles when read operations are initiated. Pipelined internally.
//active high reset .rstb(reset), // 1-bit input: Reset signal for the final port B output register stage.
.rstb(reset), // 1-bit input: Reset signal for the final port B output register stage.
// Synchronously resets output port doutb to the value specified by // Synchronously resets output port doutb to the value specified by
// parameter READ_RESET_VALUE_B. // parameter READ_RESET_VALUE_B.
.wea(driver.ena), // WRITE_DATA_WIDTH_A/BYTE_WRITE_WIDTH_A-bit input: Write enable vector .wea(driver.ena), // WRITE_DATA_WIDTH_A/BYTE_WRITE_WIDTH_A-bit input: Write enable vector
@ -147,11 +145,10 @@ buffer (
// writing one byte of dina to address addra. For example, to // writing one byte of dina to address addra. For example, to
// synchronously write only bits [15-8] of dina when WRITE_DATA_WIDTH_A // synchronously write only bits [15-8] of dina when WRITE_DATA_WIDTH_A
// is 32, wea would be 4'b0010. // is 32, wea would be 4'b0010.
// Extra inputs that I guess I need
.sleep(0), .sleep(0), // The XPM macros say these can be removed, but when I did this the
.injectsbiterra(0), .injectsbiterra(0), // entire block memory got optimized out. These were readded in later
.injectdbiterra(0), .injectdbiterra(0),
// With a latency of 1 this surely does not matter
.regceb(enb) .regceb(enb)
); );

View File

@ -6,7 +6,7 @@
* @author: Waylon Cude, Dilanthi Prentice * @author: Waylon Cude, Dilanthi Prentice
* @date: 6/12/2025 * @date: 6/12/2025
* */ * */
//Define used because verilator needs it but vivado is samrt enough not to
`ifdef VERILATOR `ifdef VERILATOR
`include "sdvd_defs.sv" `include "sdvd_defs.sv"
`endif `endif
@ -19,7 +19,7 @@ module low_freq_clock_gen(
output logic clk1k, clk10h, seconds_pulse output logic clk1k, clk10h, seconds_pulse
); );
// Hardcoded to be 1,000,000/4,000 // Hardcoded to be 1,000,000/4,000 (25,000)
// Relying on constant maths makes it the wrong size // Relying on constant maths makes it the wrong size
localparam num_cycles = 25_000; localparam num_cycles = 25_000;

View File

@ -1,18 +1,21 @@
/****
* modular_clock_gen.sv - parameterizable clock divider.
*
* @author: Waylon Cude, Dilanthi Prentice
* @date: 6/12/2025
*
* */
module modular_clock_gen( module modular_clock_gen(
input clk, reset, input clk, reset,
output logic oclk output logic oclk
); );
//parameter has no default because the user should always set it
parameter DIVISOR; parameter DIVISOR;
logic [$clog2(DIVISOR)-1:0] counter; logic [$clog2(DIVISOR)-1:0] counter;
logic set; logic set;
// clock will be high for about half of the cycle, depending on integer
// rounding
// OOPS this makes it combinational
//assign oclk = counter < (DIVISOR/2);
always_ff @(posedge clk) begin always_ff @(posedge clk) begin
// modular clock has to keep ticking through reset // modular clock has to keep ticking through reset
// so everything with a synchronous reset actually works // so everything with a synchronous reset actually works

View File

@ -118,11 +118,13 @@ audio_buffer audioBuffer(
assign SD_DAT[3:1] = 'z; assign SD_DAT[3:1] = 'z;
logic clk_100khz; logic clk_100khz;
logic clk_25mhz; logic clk_25mhz;
// Actually 200khz now // We can clock this at around 200khz before things start breaking
// 200khz is slightly unstable?????? // Even at 200khz sometimes things break
modular_clock_gen #(1000) slowSdClock(CLK100MHZ, reset, clk_100khz); modular_clock_gen #(1000) slowSdClock(CLK100MHZ, reset, clk_100khz);
// Try clocking this slower than max speed // Try clocking this slower than max speed
// To see if that makes it actually work ... // To see if that makes it actually work
//
// NOTE: It did not make it work
modular_clock_gen #(1000) fastSdClock(CLK100MHZ, reset, clk_25mhz); modular_clock_gen #(1000) fastSdClock(CLK100MHZ, reset, clk_25mhz);
sd_controller realSdPlayer( sd_controller realSdPlayer(
clk_100khz, clk_100khz,

View File

@ -1,5 +1,11 @@
// parameterizable sequential crc generator /***
// This probably could be combinational logic too, though it would be way slow * crc_gen.sv - paramerizable sequential crc generator. This could probably be
* combinational logic too (but it would be way slower)
*
* @author: Waylon Cude, Dilanthi Prentice
* @date: 6/12/2025
*
* */
module crc_gen #( module crc_gen #(
parameter CRCBITS=7, parameter CRCBITS=7,
parameter COMMANDLEN=40, parameter COMMANDLEN=40,

View File

@ -1,3 +1,11 @@
/****
* read_command.sv - reads the sd command line and listens for sd command
* responses.
*
* @author: Waylon Cude, Dilanthi Prentice
* @date: 6/12/2025
*
* **/
module read_command( module read_command(
input logic clk, input logic clk,
input logic reset, input logic reset,
@ -19,8 +27,8 @@ logic received_reg;
logic [2:0] response_type_reg; logic [2:0] response_type_reg;
// oops this was set a cycle before the data was actually ready // recevied was set a cycle before the data was actually ready
// and if it's just a reg it holds for too long // and if it's just a register it holds for too long
// use both for maximum reactivity // use both for maximum reactivity
assign received = received_reg && !listen; assign received = received_reg && !listen;

View File

@ -1,6 +1,12 @@
// Whenever we receive a data block, start spitting bytes out into the audio /***
// buffer bram. This could always be clocked at the 25MHz default speed clock, * read_data.sv - whenever we receive a data block, start spitting bytes out
// or it could switch over like the writer has to * into the audio buffer block ram. This could be clocked at
* 25MHz default speed clock, or it could swtich over like the
* writer has to.
* @author: Waylon Cude, Dilanthi Prentice
* @date: 6/12/2025
*
***/
module read_data( module read_data(
input clk, input clk,
input reset, input reset,

View File

@ -1,3 +1,11 @@
/***
* send_command.sv - sends sd card commands. It takes in a command and an
* argument and will figure out the necessary crc.
*
* @author: Waylon Cude, Dilanthi Prentice
* @date: 6/12/2025
*
* */
module send_command( module send_command(
input clk, input clk,
// The crc should be clocked way faster than the sender // The crc should be clocked way faster than the sender

View File

@ -1,5 +1,7 @@
/*** /***
* seconds_display.sv - converts a five bit seconds counter to its seven segement display equivalent. * sixty_display.sv - converts a binary digit from zero to fifty-nine to its
* ones and tens digits and then gets the seven segment
* display equivalents of them.
* *
* @author: Dilanthi Prentice, Waylon Cude * @author: Dilanthi Prentice, Waylon Cude
* @date: 6/12/25 * @date: 6/12/25
@ -16,14 +18,14 @@ module seconds_display
logic [4:0] ones_digit; logic [4:0] ones_digit;
logic [4:0] tens_digit; logic [4:0] tens_digit;
//convert digit to ones and tens places
always_comb always_comb
begin begin
ones_digit = seconds % 10; ones_digit = seconds % 10;
tens_digit = seconds / 10; tens_digit = seconds / 10;
end end
//instantiate the display_converter to convert the counter //convert both ones and tens place digits to their seven segement equivalent
//to a seven segment display number
display_converter ones (ones_digit, display_ones); display_converter ones (ones_digit, display_ones);
display_converter tens (tens_digit, display_tens); display_converter tens (tens_digit, display_tens);

View File

@ -38,7 +38,7 @@
entirely. Detected in testbench entirely. Detected in testbench
- off-by-one error detected in the counter - off-by-one error detected in the counter
## read_data ### read_data
- audio buffer address to write to was never changing, caught in simulation - audio buffer address to write to was never changing, caught in simulation
- some off-by-one errors in the byte shifting were found and corrected - some off-by-one errors in the byte shifting were found and corrected