Skip to content

Instantly share code, notes, and snippets.

@urish
Last active March 4, 2024 17:36
Show Gist options
  • Star 0 You must be signed in to star a gist
  • Fork 0 You must be signed in to fork a gist
  • Save urish/e401614102b0e27c361ac99c5e26aefb to your computer and use it in GitHub Desktop.
Save urish/e401614102b0e27c361ac99c5e26aefb to your computer and use it in GitHub Desktop.
Quick test firmware for TT02 using the standard caravel breakout board
#include <defs.h>
//#include <math.h>
#include <stub.h>
#include <hw/common.h>
#include <uart.h>
#include <uart_api.h>
// there is some Caravel issue happening that prevents the usual SET and CLR from working
// a fast read followed by write results in the whole register being cleared.
unsigned int temp;
#define SET(PIN,N) {temp |= (1<<(N)); PIN = temp;}
#define CLR(PIN,N) {temp &= ~(1<<(N)); PIN = temp;}
// --------------------------------------------------------
// Firmware routines
// --------------------------------------------------------
void configure_io()
{
// GPIO 0 is turned off to prevent toggling the debug pin; For debug, make this an output and
// drive it externally to ground.
reg_mprj_io_0 = GPIO_MODE_MGMT_STD_ANALOG;
// Changing configuration for IO[1-4] will interfere with programming flash. if you change them,
// You may need to hold reset while powering up the board and initiating flash to keep the process
// configuring these IO from their default values.
// https://github.com/TinyTapeout/tinytapeout-02/blob/tt02/INFO.md#pinout
reg_mprj_io_1 = GPIO_MODE_MGMT_STD_OUTPUT;
reg_mprj_io_2 = GPIO_MODE_MGMT_STD_INPUT_NOPULL;
reg_mprj_io_3 = GPIO_MODE_MGMT_STD_INPUT_NOPULL;
reg_mprj_io_4 = GPIO_MODE_MGMT_STD_INPUT_NOPULL;
// design select
reg_mprj_io_12 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_13 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_14 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_15 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_16 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_17 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_18 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_19 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_20 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
// inputs
reg_mprj_io_21 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_22 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_23 = GPIO_MODE_MGMT_STD_INPUT_PULLDOWN;
reg_mprj_io_24 = GPIO_MODE_MGMT_STD_INPUT_PULLDOWN;
reg_mprj_io_25 = GPIO_MODE_MGMT_STD_INPUT_PULLDOWN;
reg_mprj_io_26 = GPIO_MODE_MGMT_STD_INPUT_PULLDOWN;
reg_mprj_io_27 = GPIO_MODE_MGMT_STD_INPUT_PULLDOWN;
reg_mprj_io_28 = GPIO_MODE_MGMT_STD_INPUT_PULLDOWN;
// outputs
reg_mprj_io_29 = GPIO_MODE_USER_STD_OUTPUT;
reg_mprj_io_30 = GPIO_MODE_USER_STD_OUTPUT;
reg_mprj_io_31 = GPIO_MODE_USER_STD_OUTPUT;
reg_mprj_io_32 = GPIO_MODE_USER_STD_OUTPUT;
reg_mprj_io_33 = GPIO_MODE_USER_STD_OUTPUT;
reg_mprj_io_34 = GPIO_MODE_USER_STD_OUTPUT;
reg_mprj_io_35 = GPIO_MODE_USER_STD_OUTPUT;
reg_mprj_io_36 = GPIO_MODE_USER_STD_OUTPUT;
// ready
reg_mprj_io_37 = GPIO_MODE_USER_STD_OUTPUT;
// slow clock
reg_mprj_io_10 = GPIO_MODE_USER_STD_OUT_MONITORED;
// set slow clock divider
reg_mprj_io_11 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
// drive sel, 00 external, 01 LA, 1x internal
reg_mprj_io_9 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
reg_mprj_io_8 = GPIO_MODE_MGMT_STD_BIDIRECTIONAL;
// Initiate the serial transfer to configure IO
reg_mprj_xfer = 1;
while (reg_mprj_xfer == 1);
}
void delay(const int d)
{
// Configure timer for a single-shot countdown */
reg_timer0_config = 0;
reg_timer0_data = d;
reg_timer0_config = 1;
// Loop, waiting for value to reach zero
reg_timer0_update = 1; // latch current value
while (reg_timer0_value > 0)
{
reg_timer0_update = 1;
}
}
void main()
{
reg_gpio_mode1 = 1;
reg_gpio_mode0 = 0;
reg_gpio_ien = 1;
reg_gpio_oe = 1;
configure_io();
SET(reg_mprj_datal, 9);
CLR(reg_mprj_datal, 11);
int selected_design = 51;
for (int i = 0; i < 9; i++) {
if (selected_design & (1 << i)) {
SET(reg_mprj_datal, 12 + i);
} else {
CLR(reg_mprj_datal, 12 + i);
}
}
delay(100000);
// Reset
SET(reg_mprj_datal, 22);
SET(reg_mprj_datal, 21);
delay(100000);
SET(reg_mprj_datal, 21);
delay(100000);
CLR(reg_mprj_datal, 22);
SET(reg_mprj_datal, 21);
delay(100000);
SET(reg_mprj_datal, 21);
delay(100000);
// flash along with the slow clock
while (true)
{
delay(1000000);
SET(reg_mprj_datal, 21);
reg_gpio_out = 1;
delay(1000000);
CLR(reg_mprj_datal, 21);
reg_gpio_out = 0;
}
}
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment