diff --git a/src/dmd_counter.h b/src/dmd_counter.h new file mode 100644 index 0000000..bfb252e --- /dev/null +++ b/src/dmd_counter.h @@ -0,0 +1,39 @@ +#ifndef DMD_COUNTER_H +#define DMD_COUNTER_H + +#include "dmd_counter.pio.h" +#include "dmd_reader_pins.h" +#include "hardware/gpio.h" +#include "hardware/pio.h" + +void dmd_counter_program_init(PIO pio, uint sm, uint offset) { + pio_sm_config c = dmd_count_dotclk_program_get_default_config(offset); + + // Set the IN base pin + sm_config_set_in_pins(&c, DE); + + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, DOTCLK, 1, false); + pio_sm_set_consecutive_pindirs(pio, sm, RCLK, 3, false); // RCLK, RDATA, DE + + // Connect these GPIOs to this PIO block + pio_gpio_init(pio, DOTCLK); + pio_gpio_init(pio, DE); + pio_gpio_init(pio, RDATA); + pio_gpio_init(pio, RCLK); + + // Shifting to left matches the customary MSB-first ordering of SPI. + sm_config_set_in_shift(&c, + false, // Shift-to-right = false + true, // Autopull enabled + 32 // Autopull threshold = 32 + ); + + // We only send, so disable the TX FIFO to make the RX FIFO deeper. + sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +#endif // DMD_COUNTER_H diff --git a/src/dmd_counter.pio b/src/dmd_counter.pio index 231533f..4d74b76 100644 --- a/src/dmd_counter.pio +++ b/src/dmd_counter.pio @@ -16,7 +16,6 @@ jmp x-- clockdecrement clockdecrement: wait 1 gpio DOTCLK - .wrap .program dmd_count_de @@ -28,7 +27,6 @@ clockdecrement: jmp x-- clockdecrement clockdecrement: wait 1 gpio DE - .wrap .program dmd_count_rdata @@ -40,7 +38,6 @@ clockdecrement: jmp x-- clockdecrement clockdecrement: wait 1 gpio RDATA - .wrap .program dmd_count_rclk @@ -52,39 +49,4 @@ clockdecrement: jmp x-- clockdecrement clockdecrement: wait 1 gpio RCLK - .wrap - - -% c-sdk { -static inline void dmd_counter_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_count_dotclk_program_get_default_config(offset); - - // Set the IN base pin - sm_config_set_in_pins(&c, 7); // DE - - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, 3, 1, false); // DOTCLK - pio_sm_set_consecutive_pindirs(pio, sm, 5, 3, false); // RCLK, RDATA, DE - - // Connect these GPIOs to this PIO block - pio_gpio_init(pio, 3); // DOTCLK - pio_gpio_init(pio, 7); // DE - pio_gpio_init(pio, 6); // RDATA - pio_gpio_init(pio, 5); // RCLK - - // Shifting to left matches the customary MSB-first ordering of SPI. - sm_config_set_in_shift( - &c, - false, // Shift-to-right = false - true, // Autopull enabled - 32 // Autopull threshold = 32 - ); - - // We only send, so disable the TX FIFO to make the RX FIFO deeper. - sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} \ No newline at end of file diff --git a/src/dmd_interface_desega.h b/src/dmd_interface_desega.h new file mode 100644 index 0000000..f8cafbe --- /dev/null +++ b/src/dmd_interface_desega.h @@ -0,0 +1,54 @@ +#ifndef DMD_INTERFACE_DESEGA_H +#define DMD_INTERFACE_DESEGA_H + +#include "dmd_interface_desega.pio.h" +#include "dmd_reader_pins.h" +#include "hardware/gpio.h" +#include "hardware/pio.h" + +void dmd_reader_desega_program_init(PIO pio, uint sm, + uint offset) { + pio_sm_config c = dmd_reader_desega_program_get_default_config(offset); + + // Set the IN pin, we don't use any other + sm_config_set_in_pins(&c, SDATA); + + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, SDATA, 2, + false); // SDATA, DOTCLK + + // Connect these GPIOs to this PIO block + pio_gpio_init(pio, DOTCLK); + pio_gpio_init(pio, SDATA); + + // Shifting to left matches the customary MSB-first ordering of SPI. + sm_config_set_in_shift(&c, + false, // Shift-to-right = false + true, // Autopull enabled + 32 // Autopull threshold + ); + + // We only send, so disable the TX FIFO to make the RX FIFO deeper. + sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +void dmd_framedetect_desega_program_init(PIO pio, uint sm, + uint offset) { + pio_sm_config c = dmd_framedetect_desega_program_get_default_config(offset); + // DE is used for jump control + sm_config_set_jmp_pin(&c, DE); + + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, DE, 1, false); + + // Connect this GPIO to this PIO block + pio_gpio_init(pio, DE); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +#endif // DMD_INTERFACE_DESEGA_H diff --git a/src/dmd_interface_desega.pio b/src/dmd_interface_desega.pio index 0305a32..9478610 100644 --- a/src/dmd_interface_desega.pio +++ b/src/dmd_interface_desega.pio @@ -4,14 +4,8 @@ .define COLLAT 4 .define DOTCLK 3 .define SDATA 2 - .define FRAME_START_IRQ 4 -.define PUBLIC desega_DE DE -.define PUBLIC desega_DOTCLK DOTCLK -.define PUBLIC desega_SDATA SDATA - - .program dmd_reader_desega ; initialize y with 8191, number of pixels ((128 x LSB + 128 x MSB) x 32) - 1 because counting starts at 0. set x, 31 ; x = 31 (max 5-bit value) @@ -36,10 +30,9 @@ dotloop: wait 1 gpio DOTCLK ; raising edge in pins 1 ; read pin data jmp x-- dotloop - .wrap - +; Frame detection program runs in parallel to the reader program and signals the start of a new frame using an IRQ. .program dmd_framedetect_desega .wrap_target @@ -62,53 +55,4 @@ delay_loop: wait 1 gpio DE ; Wait again for it to go high before restarting cycle jmp wait_low ; went high, time to go back to wait_low - .wrap - - -% c-sdk { -static inline void dmd_reader_desega_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_reader_desega_program_get_default_config(offset); - - // Set the IN pin, we don't use any other - sm_config_set_in_pins(&c, desega_SDATA); - - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, desega_SDATA, 2, false); // SDATA, DOTCLK - - // Connect these GPIOs to this PIO block - pio_gpio_init(pio, desega_DOTCLK); - pio_gpio_init(pio, desega_SDATA); - - // Shifting to left matches the customary MSB-first ordering of SPI. - sm_config_set_in_shift( - &c, - false, // Shift-to-right = false - true, // Autopull enabled - 32 // Autopull threshold - ); - - // We only send, so disable the TX FIFO to make the RX FIFO deeper. - sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} - -% c-sdk { -static inline void dmd_framedetect_desega_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_framedetect_desega_program_get_default_config(offset); - // DE is used for jump control - sm_config_set_jmp_pin(&c, desega_DE); - - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, desega_DE, 1, false); - - // Connect this GPIO to this PIO block - pio_gpio_init(pio, desega_DE); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} diff --git a/src/dmd_interface_sam.h b/src/dmd_interface_sam.h new file mode 100644 index 0000000..4e76fa6 --- /dev/null +++ b/src/dmd_interface_sam.h @@ -0,0 +1,50 @@ +#ifndef DMD_INTERFACE_SAM_H +#define DMD_INTERFACE_SAM_H + +#include "dmd_interface_sam.pio.h" +#include "dmd_reader_pins.h" +#include "hardware/gpio.h" +#include "hardware/pio.h" + +void dmd_reader_sam_program_init(PIO pio, uint sm, uint offset) { + pio_sm_config c = dmd_reader_sam_program_get_default_config(offset); + + // Set the IN pin, we don't use any other + sm_config_set_in_pins(&c, SDATA); + + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, SDATA, 2, false); // SDATA, DOTCLK + + // Connect these GPIOs to this PIO block + pio_gpio_init(pio, DOTCLK); + pio_gpio_init(pio, SDATA); + + // Shifting to left matches the customary MSB-first ordering of SPI. + sm_config_set_in_shift(&c, + false, // Shift-to-right = false + true, // Autopull enabled + 32 // Autopull threshold + ); + + // We only send, so disable the TX FIFO to make the RX FIFO deeper. + sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +void dmd_framedetect_sam_program_init(PIO pio, uint sm, + uint offset) { + pio_sm_config c = dmd_framedetect_sam_program_get_default_config(offset); + + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, RDATA, 1, false); + + // Connect these GPIOs to this PIO block + pio_gpio_init(pio, RDATA); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +#endif // DMD_INTERFACE_SAM_H \ No newline at end of file diff --git a/src/dmd_interface_sam.pio b/src/dmd_interface_sam.pio index 2e820ef..ece2255 100644 --- a/src/dmd_interface_sam.pio +++ b/src/dmd_interface_sam.pio @@ -4,14 +4,8 @@ .define COLLAT 4 .define DOTCLK 3 .define SDATA 2 - .define FRAME_START_IRQ 4 -.define PUBLIC sam_RCLK RCLK -.define PUBLIC sam_RDATA RDATA -.define PUBLIC sam_DOTCLK DOTCLK -.define PUBLIC sam_SDATA SDATA - .program dmd_reader_sam ; initialize y with 16383, number of pixels (128x32x4) - 1 because counting starts at 0. set x, 31 ; x = 31 (max 5-bit value) @@ -37,56 +31,10 @@ dotloop: jmp x-- dotloop .wrap - +; Frame detection program runs in parallel to the reader program and signals the start of a new frame using an IRQ. .program dmd_framedetect_sam .wrap_target wait 0 gpio RDATA wait 1 gpio RDATA irq FRAME_START_IRQ .wrap - - -% c-sdk { -static inline void dmd_reader_sam_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_reader_sam_program_get_default_config(offset); - - // Set the IN pin, we don't use any other - sm_config_set_in_pins(&c, sam_SDATA); - - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, sam_SDATA, 2, false); // SDATA, DOTCLK - - // Connect these GPIOs to this PIO block - pio_gpio_init(pio, sam_DOTCLK); - pio_gpio_init(pio, sam_SDATA); - - // Shifting to left matches the customary MSB-first ordering of SPI. - sm_config_set_in_shift( - &c, - false, // Shift-to-right = false - true, // Autopull enabled - 32 // Autopull threshold - ); - - // We only send, so disable the TX FIFO to make the RX FIFO deeper. - sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} - -% c-sdk { -static inline void dmd_framedetect_sam_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_framedetect_sam_program_get_default_config(offset); - - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, sam_RDATA, 1, false); - - // Connect these GPIOs to this PIO block - pio_gpio_init(pio, sam_RDATA); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} diff --git a/src/dmd_interface_spike.h b/src/dmd_interface_spike.h new file mode 100644 index 0000000..23874d0 --- /dev/null +++ b/src/dmd_interface_spike.h @@ -0,0 +1,59 @@ +#ifndef DMD_INTERFACE_SPIKE_H +#define DMD_INTERFACE_SPIKE_H + +#include "dmd_interface_spike.pio.h" +#include "dmd_reader_pins.h" +#include "hardware/gpio.h" +#include "hardware/pio.h" + +void dmd_reader_spike_program_init(PIO pio, uint sm, uint offset) { + pio_sm_config c = dmd_reader_spike_program_get_default_config(offset); + + // Set the IN base pin to the provided `pin` parameter. This is the data pin, + // we don't use any other + sm_config_set_in_pins(&c, SDATA); + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, SDATA, 2, false); // SDATA, DOTCLK + + // Connect these GPIOs to this PIO block + pio_gpio_init(pio, DOTCLK); + pio_gpio_init(pio, SDATA); + + // Shifting to left matches the customary MSB-first ordering of SPI. + sm_config_set_in_shift(&c, + false, // Shift-to-right = false + true, // Autopull enabled + 32 // Autopull threshold + ); + + // We only receive, so disable the TX FIFO to make the RX FIFO deeper. + sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +void dmd_framedetect_spike_program_init(PIO pio, uint sm, uint offset) { + pio_sm_config c = dmd_framedetect_spike_program_get_default_config(offset); + // RDATA is used for jump control + sm_config_set_jmp_pin(&c, RDATA); + + // Shifting to left matches the customary MSB-first ordering of SPI. + sm_config_set_in_shift(&c, + false, // Shift-to-right = false + false, // No autopull, we don't read data from this SM + 32 // Autopull threshold + ); + + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, RCLK, 2, false); // RCLK, RDATA + + // Connect these GPIOs to this PIO block + pio_gpio_init(pio, RDATA); + pio_gpio_init(pio, RCLK); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +#endif // DMD_INTERFACE_SPIKE_H diff --git a/src/dmd_interface_spike.pio b/src/dmd_interface_spike.pio index 84d6617..98c29d2 100644 --- a/src/dmd_interface_spike.pio +++ b/src/dmd_interface_spike.pio @@ -4,14 +4,7 @@ .define COLLAT 4 .define DOTCLK 3 .define SDATA 2 - -.define PLANE_START_IRQ 4 - -.define PUBLIC spike_RCLK RCLK -.define PUBLIC spike_RDATA RDATA -.define PUBLIC spike_DOTCLK DOTCLK -.define PUBLIC spike_SDATA SDATA - +.define FRAME_START_IRQ 4 .program dmd_reader_spike ; initialize y with 16383, number of pixels (128x32x4) - 1 because counting starts at 0. @@ -27,8 +20,8 @@ mov x, y ; load number of pixels mov isr, null ; reset shift counter - irq clear PLANE_START_IRQ - wait irq PLANE_START_IRQ + irq clear FRAME_START_IRQ + wait irq FRAME_START_IRQ dotloop: wait 0 gpio DOTCLK ; falling edge @@ -36,18 +29,17 @@ dotloop: in null 3 ; left padding 3x zero in pins 1 ; read pin data jmp x-- dotloop - .wrap - +; Frame detection program runs in parallel to the reader program and signals the start of a new frame using an IRQ. .program dmd_framedetect_spike -; Frame detection in Spike: -; white for RDATA to go H -; check if it is still H 150-250ms later - in this case, this is the most significant bit -; which is the last plane -; now wait for RDATA to go L and H again, this is the beginning of a new frame -; based on 125MHz clock frequency we have to wait 18750-31250 clock cycles -; we use 24576 here, because it0s 0b11 << 13 + ; Frame detection in Spike: + ; white for RDATA to go H + ; check if it is still H 150-250ms later - in this case, this is the most significant bit + ; which is the last plane + ; now wait for RDATA to go L and H again, this is the beginning of a new frame + ; based on 125MHz clock frequency we have to wait 18750-31250 clock cycles + ; we use 24576 here, because it0s 0b11 << 13 ; initialize isr with 24576 set x, 3 @@ -81,61 +73,5 @@ lineloop: wait 0 gpio RCLK jmp x-- lineloop - irq PLANE_START_IRQ - + irq FRAME_START_IRQ .wrap - -% c-sdk { -static inline void dmd_reader_spike_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_reader_spike_program_get_default_config(offset); - - // Set the IN base pin to the provided `pin` parameter. This is the data pin, we don't use any other - sm_config_set_in_pins(&c, spike_SDATA); - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, spike_SDATA, 2, false); // SDATA, DOTCLK - - // Connect these GPIOs to this PIO block - pio_gpio_init(pio, spike_DOTCLK); - pio_gpio_init(pio, spike_SDATA); - - // Shifting to left matches the customary MSB-first ordering of SPI. - sm_config_set_in_shift( - &c, - false, // Shift-to-right = false - true, // Autopull enabled - 32 // Autopull threshold - ); - - // We only receive, so disable the TX FIFO to make the RX FIFO deeper. - sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} - -% c-sdk { -static inline void dmd_framedetect_spike_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_framedetect_spike_program_get_default_config(offset); - // RDATA is used for jump control - sm_config_set_jmp_pin(&c, spike_RDATA); - - // Shifting to left matches the customary MSB-first ordering of SPI. - sm_config_set_in_shift( - &c, - false, // Shift-to-right = false - false, // No autopull, we don't read data from this SM - 32 // Autopull threshold - ); - - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, spike_RCLK, 2, false); // RCLK, RDATA - - // Connect these GPIOs to this PIO block - pio_gpio_init(pio, spike_RDATA); - pio_gpio_init(pio, spike_RCLK); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} diff --git a/src/dmd_interface_whitestar.h b/src/dmd_interface_whitestar.h new file mode 100644 index 0000000..148dd09 --- /dev/null +++ b/src/dmd_interface_whitestar.h @@ -0,0 +1,50 @@ +#ifndef DMD_INTERFACE_WHITESTAR_H +#define DMD_INTERFACE_WHITESTAR_H + +#include "dmd_interface_whitestar.pio.h" +#include "dmd_reader_pins.h" +#include "hardware/gpio.h" +#include "hardware/pio.h" + +void dmd_reader_whitestar_program_init(PIO pio, uint sm, uint offset) { + pio_sm_config c = dmd_reader_whitestar_program_get_default_config(offset); + + // Set the IN pin, we don't use any other + sm_config_set_in_pins(&c, SDATA); + + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, SDATA, 2, false); // SDATA, DOTCLK + + // Connect these GPIOs to this PIO block + pio_gpio_init(pio, DOTCLK); + pio_gpio_init(pio, SDATA); + + // Shifting to left matches the customary MSB-first ordering of SPI. + sm_config_set_in_shift(&c, + false, // Shift-to-right = false + true, // Autopull enabled + 32 // Autopull threshold + ); + + // We only send, so disable the TX FIFO to make the RX FIFO deeper. + sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +void dmd_framedetect_whitestar_program_init(PIO pio, uint sm, uint offset) { + pio_sm_config c = + dmd_framedetect_whitestar_program_get_default_config(offset); + + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, RDATA, 1, false); + + // Connect these GPIOs to this PIO block + pio_gpio_init(pio, RDATA); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +#endif // DMD_INTERFACE_WHITESTAR_H diff --git a/src/dmd_interface_whitestar.pio b/src/dmd_interface_whitestar.pio index ff45ba9..bf269a8 100644 --- a/src/dmd_interface_whitestar.pio +++ b/src/dmd_interface_whitestar.pio @@ -4,13 +4,8 @@ .define COLLAT 4 .define DOTCLK 3 .define SDATA 2 - .define FRAME_START_IRQ 4 -.define PUBLIC whitestar_RDATA RDATA -.define PUBLIC whitestar_DOTCLK DOTCLK -.define PUBLIC whitestar_SDATA SDATA - .program dmd_reader_whitestar ; initialize y with 8191, number of pixels ((128 x LSB + 128 x MSB) x 32) - 1 because counting starts at 0. set x, 31 ; x = 31 (max 5-bit value) @@ -39,56 +34,10 @@ dotloop: ; It is ignored because we already read the specified amount of dots and now wait for a new frame. .wrap - +; Frame detection program runs in parallel to the reader program and signals the start of a new frame using an IRQ. .program dmd_framedetect_whitestar .wrap_target wait 0 gpio RDATA wait 1 gpio RDATA irq FRAME_START_IRQ .wrap - - -% c-sdk { -static inline void dmd_reader_whitestar_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_reader_whitestar_program_get_default_config(offset); - - // Set the IN pin, we don't use any other - sm_config_set_in_pins(&c, whitestar_SDATA); - - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, whitestar_SDATA, 2, false); // SDATA, DOTCLK - - // Connect these GPIOs to this PIO block - pio_gpio_init(pio, whitestar_DOTCLK); - pio_gpio_init(pio, whitestar_SDATA); - - // Shifting to left matches the customary MSB-first ordering of SPI. - sm_config_set_in_shift( - &c, - false, // Shift-to-right = false - true, // Autopull enabled - 32 // Autopull threshold - ); - - // We only send, so disable the TX FIFO to make the RX FIFO deeper. - sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} - -% c-sdk { -static inline void dmd_framedetect_whitestar_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_framedetect_whitestar_program_get_default_config(offset); - - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, whitestar_RDATA, 1, false); - - // Connect these GPIOs to this PIO block - pio_gpio_init(pio, whitestar_RDATA); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} diff --git a/src/dmd_interface_wpc.h b/src/dmd_interface_wpc.h new file mode 100644 index 0000000..f617823 --- /dev/null +++ b/src/dmd_interface_wpc.h @@ -0,0 +1,52 @@ +#ifndef DMD_INTERFACE_WPC_H +#define DMD_INTERFACE_WPC_H + +#include "dmd_interface_wpc.pio.h" +#include "dmd_reader_pins.h" +#include "hardware/gpio.h" +#include "hardware/pio.h" + +void dmd_reader_wpc_program_init(PIO pio, uint sm, uint offset) { + pio_sm_config c = dmd_reader_wpc_program_get_default_config(offset); + + // Set the IN pin, we don't use any other + sm_config_set_in_pins(&c, SDATA); + + // Connect these GPIOs to this PIO block + pio_gpio_init(pio, DOTCLK); + pio_gpio_init(pio, SDATA); + + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, SDATA, 2, false); // SDATA, DOTCLK + + // Shifting to left matches the customary MSB-first ordering of SPI. + sm_config_set_in_shift(&c, + false, // Shift-to-right = false + true, // Autopull enabled + 32 // Autopull threshold + ); + + // We only send, so disable the TX FIFO to make the RX FIFO deeper. + sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +void dmd_framedetect_wpc_program_init(PIO pio, uint sm, uint offset) { + pio_sm_config c = dmd_framedetect_wpc_program_get_default_config(offset); + + // Connect these GPIOs to this PIO block + pio_gpio_init(pio, DE); + pio_gpio_init(pio, RDATA); + pio_gpio_init(pio, DOTCLK); + + // Set the pin direction at the PIO + pio_sm_set_consecutive_pindirs(pio, sm, RDATA, 2, false); // RDATA, DE + pio_sm_set_consecutive_pindirs(pio, sm, DOTCLK, 1, false); + + // Load our configuration, do not yet start the program + pio_sm_init(pio, sm, offset, &c); +} + +#endif // DMD_INTERFACE_WPC_H diff --git a/src/dmd_interface_wpc.pio b/src/dmd_interface_wpc.pio index e089ebc..f2d6edb 100644 --- a/src/dmd_interface_wpc.pio +++ b/src/dmd_interface_wpc.pio @@ -4,14 +4,8 @@ .define COLLAT 4 .define DOTCLK 3 .define SDATA 2 - .define PLANE_START_IRQ 4 -.define PUBLIC wpc_DE DE -.define PUBLIC wpc_RDATA RDATA -.define PUBLIC wpc_DOTCLK DOTCLK -.define PUBLIC wpc_SDATA SDATA - .program dmd_reader_wpc set x, 31 ; load 31, 5 bits is max allowed (0b11111) in x, 5 ; shift in 5 bits, isr is 31 now @@ -36,7 +30,7 @@ plane_loop: jmp x-- plane_loop .wrap - +; Frame detection program runs in parallel to the reader program and signals the start of a new frame using an IRQ. .program dmd_framedetect_wpc .wrap_target wait 0 gpio RDATA @@ -46,52 +40,3 @@ plane_loop: nop [31] irq PLANE_START_IRQ .wrap - - -% c-sdk { -static inline void dmd_reader_wpc_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_reader_wpc_program_get_default_config(offset); - - // Set the IN pin, we don't use any other - sm_config_set_in_pins(&c, wpc_SDATA); - - // Connect these GPIOs to this PIO block - pio_gpio_init(pio, wpc_DOTCLK); - pio_gpio_init(pio, wpc_SDATA); - - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, wpc_SDATA, 2, false); // SDATA, DOTCLK - - // Shifting to left matches the customary MSB-first ordering of SPI. - sm_config_set_in_shift( - &c, - false, // Shift-to-right = false - true, // Autopull enabled - 32 // Autopull threshold - ); - - // We only send, so disable the TX FIFO to make the RX FIFO deeper. - sm_config_set_fifo_join(&c, PIO_FIFO_JOIN_RX); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} - -% c-sdk { -static inline void dmd_framedetect_wpc_program_init(PIO pio, uint sm, uint offset) { - pio_sm_config c = dmd_framedetect_wpc_program_get_default_config(offset); - - // Connect these GPIOs to this PIO block - pio_gpio_init(pio, wpc_DE); - pio_gpio_init(pio, wpc_RDATA); - pio_gpio_init(pio, wpc_DOTCLK); - - // Set the pin direction at the PIO - pio_sm_set_consecutive_pindirs(pio, sm, wpc_RDATA, 2, false); // RDATA, DE - pio_sm_set_consecutive_pindirs(pio, sm, wpc_DOTCLK, 1, false); - - // Load our configuration, do not yet start the program - pio_sm_init(pio, sm, offset, &c); -} -%} diff --git a/src/dmd_reader.c b/src/dmd_reader.c index fc9f466..922d2d9 100644 --- a/src/dmd_reader.c +++ b/src/dmd_reader.c @@ -1,15 +1,16 @@ #include "dmd_reader.h" +#include "dmd_reader_pins.h" #include #include #include "crc32.h" -#include "dmd_counter.pio.h" -#include "dmd_interface_desega.pio.h" -#include "dmd_interface_sam.pio.h" -#include "dmd_interface_spike.pio.h" -#include "dmd_interface_whitestar.pio.h" -#include "dmd_interface_wpc.pio.h" +#include "dmd_counter.h" +#include "dmd_interface_desega.h" +#include "dmd_interface_sam.h" +#include "dmd_interface_spike.h" +#include "dmd_interface_whitestar.h" +#include "dmd_interface_wpc.h" #include "hardware/dma.h" #include "hardware/gpio.h" #include "hardware/irq.h" @@ -36,10 +37,6 @@ * */ -#define SPI_IRQ_PIN 17 -#define LED1_PIN 27 -#define LED2_PIN 28 - #ifdef SUPRESS_DUPLICATES #define USE_CRC #endif @@ -76,14 +73,6 @@ typedef struct __attribute__((__packed__)) block_pix_crc_header_t { uint32_t crc32; // crc32 of the pixel data } block_pix_crc_header_t; -// SPI Defines -#define SPI0 spi0 -#define SPI_BASE 16 -#define SPI0_MISO SPI_BASE -#define SPI0_CS (SPI_BASE + 1) -#define SPI0_SCK (SPI_BASE + 2) -#define SPI0_MOSI (SPI_BASE + 3) - // DMD types #define DMD_UNKNOWN 0 #define DMD_WPC 1 @@ -171,7 +160,7 @@ uint dmd_int = 0; volatile bool frame_received = false; -/* ---------- Stable-High Check on SPI_IRQ_PIN at boot ---------- */ +/* ---------- Stable-High Check on SPI0_CS at boot ---------- */ static bool pin_is_stably_high(uint pin, uint32_t stable_ms, uint32_t sample_ms, uint32_t timeout_ms) { @@ -262,29 +251,29 @@ void spi_abort() { } /** - * @brief Notify on pin SPI_IRQ_PIN that data are ready on SPI + * @brief Notify on pin SPI0_CS that data are ready on SPI * * The SPI master (the Pico is slave) should start a data transfer when this - * signal is received It toggles pin SPI_IRQ_PIN to H + * signal is received It toggles pin SPI0_CS to H * */ -void start_spi() { gpio_put(SPI_IRQ_PIN, 1); } +void start_spi() { gpio_put(SPI0_CS, 1); } /** - * @brief Set pin SPI_IRQ_PIN to L to signal that there is no active SPI data + * @brief Set pin SPI0_CS to L to signal that there is no active SPI data * transfer * */ -void finish_spi() { gpio_put(SPI_IRQ_PIN, 0); } +void finish_spi() { gpio_put(SPI0_CS, 0); } /** - * @brief A simple debug procedure that toggles the IRQ pin multiple times + * @brief A simple debug procedure that toggles the SPI0_CS pin multiple times */ void spi_notify_onoff(int count) { for (int i = 0; i < count; i++) { - gpio_put(SPI_IRQ_PIN, 1); + gpio_put(SPI0_CS, 1); sleep_ms(100); - gpio_put(SPI_IRQ_PIN, 0); + gpio_put(SPI0_CS, 0); sleep_ms(100); } } @@ -363,7 +352,7 @@ int detect_dmd() { printf("Data East/Sega detected\n"); spi_notify_onoff(DMD_DESEGA); return DMD_DESEGA; - + } else if ((dotclk > 645000) && (dotclk < 665000) && (de > 5075) && (de < 5200) && (rdata > 75) && (rdata < 85)) { printf("Stern Whitestar detected\n"); @@ -519,10 +508,10 @@ bool init() { printf("DMD reader starting\n"); - // this is uses to notify the Pi that data is available - gpio_init(SPI_IRQ_PIN); - gpio_set_dir(SPI_IRQ_PIN, GPIO_OUT); - gpio_put(SPI_IRQ_PIN, 0); + // this is used to notify the Pi that data is available + gpio_init(SPI0_CS); + gpio_set_dir(SPI0_CS, GPIO_OUT); + gpio_put(SPI0_CS, 0); printf("IRQ pin initialized\n"); int dmd_type = DMD_UNKNOWN; @@ -748,11 +737,11 @@ bool init() { int read_dmd() { stdio_init_all(); - gpio_init(SPI_IRQ_PIN); - gpio_set_dir(SPI_IRQ_PIN, GPIO_IN); - gpio_disable_pulls(SPI_IRQ_PIN); + gpio_init(SPI0_CS); + gpio_set_dir(SPI0_CS, GPIO_IN); + gpio_disable_pulls(SPI0_CS); - if (pin_is_stably_high(SPI_IRQ_PIN, 100, 5, 1500)) { + if (pin_is_stably_high(SPI0_CS, 100, 5, 1500)) { return -1; } diff --git a/src/dmd_reader_pins.h b/src/dmd_reader_pins.h new file mode 100644 index 0000000..df4e6ff --- /dev/null +++ b/src/dmd_reader_pins.h @@ -0,0 +1,22 @@ +#ifndef DMD_READER_PINS_H +#define DMD_READER_PINS_H + +#define DE 7 +#define RDATA 6 +#define RCLK 5 +#define COLLAT 4 +#define DOTCLK 3 +#define SDATA 2 + +#define LED1_PIN 27 +#define LED2_PIN 28 + +// SPI Defines +#define SPI0 spi0 +#define SPI_BASE 16 +#define SPI0_MISO SPI_BASE // 16 +#define SPI0_CS (SPI_BASE + 1) // 17 +#define SPI0_SCK (SPI_BASE + 2) // 18 +#define SPI0_MOSI (SPI_BASE + 3) // 19 + +#endif // DMD_READER_PINS_H