diff --git a/src/Kconfig b/src/Kconfig index 69768a4e..e94ff5b2 100644 --- a/src/Kconfig +++ b/src/Kconfig @@ -6,12 +6,10 @@ choice prompt "Micro-controller Architecture" config MACH_AVR bool "Atmega AVR" - config MACH_SAM3X8E - bool "SAM3x8e (Arduino Due)" + config MACH_SAM3 + bool "SAM3/SAM4 (Due and Duet)" config MACH_SAMD21 bool "SAMD21 (Arduino Zero)" - config MACH_SAM4E8E - bool "SAM4e8e (Duet Wifi/Eth)" config MACH_LPC176X bool "LPC176x (Smoothieboard)" config MACH_STM32F1 @@ -27,7 +25,6 @@ endchoice source "src/avr/Kconfig" source "src/sam3/Kconfig" source "src/samd21/Kconfig" -source "src/sam4e8e/Kconfig" source "src/lpc176x/Kconfig" source "src/stm32f1/Kconfig" source "src/pru/Kconfig" diff --git a/src/sam3/Kconfig b/src/sam3/Kconfig index 03bdac8a..f87b84fa 100644 --- a/src/sam3/Kconfig +++ b/src/sam3/Kconfig @@ -1,12 +1,13 @@ -# Kconfig settings for SAM3 processors +# Kconfig settings for SAM3/SAM4 processors -if MACH_SAM3X8E +if MACH_SAM3 -config SAM_SELECT +config SAM3_SELECT bool default y select HAVE_GPIO select HAVE_GPIO_ADC + select HAVE_GPIO_I2C if MACH_SAM4E8E select HAVE_GPIO_SPI select HAVE_GPIO_BITBANGING @@ -14,9 +15,23 @@ config BOARD_DIRECTORY string default "sam3" +choice + prompt "Processor model" + config MACH_SAM3X8E + bool "SAM3x8e (Arduino Due)" + config MACH_SAM4E8E + bool "SAM4e8e (Duet Wifi/Eth)" +endchoice + +config MCU + string + default "sam3x8e" if MACH_SAM3X8E + default "sam4e8e" if MACH_SAM4E8E + config CLOCK_FREQ int - default 42000000 # 84000000/2 + default 42000000 if MACH_SAM3X8E # 84000000/2 + default 60000000 if MACH_SAM4E8E # 120000000/2 config SERIAL bool diff --git a/src/sam3/Makefile b/src/sam3/Makefile index 98809cdd..c49fab5d 100644 --- a/src/sam3/Makefile +++ b/src/sam3/Makefile @@ -1,33 +1,42 @@ -# Additional SAM3 build rules +# Additional SAM3/SAM4 build rules # Setup the toolchain CROSS_PREFIX=arm-none-eabi- dirs-y += src/sam3 src/generic -dirs-y += lib/sam3x/gcc/gcc +dirs-$(CONFIG_MACH_SAM3X8E) += lib/sam3x/gcc/gcc +dirs-$(CONFIG_MACH_SAM4E8E) += lib/sam4e/gcc/gcc -CFLAGS += -mthumb -mcpu=cortex-m3 -falign-loops=16 -CFLAGS += -Ilib/sam3x/include -Ilib/cmsis-core -CFLAGS += -D__SAM3X8E__ +CFLAGS-$(CONFIG_MACH_SAM3X8E) += -mcpu=cortex-m3 -falign-loops=16 +CFLAGS-$(CONFIG_MACH_SAM3X8E) += -Ilib/sam3x/include -D__SAM3X8E__ +CFLAGS-$(CONFIG_MACH_SAM4E8E) += -mcpu=cortex-m4 -mfpu=fpv4-sp-d16 -mfloat-abi=hard +CFLAGS-$(CONFIG_MACH_SAM4E8E) += -Ilib/sam4e/include -D__SAM4E8E__ +CFLAGS += -mthumb $(CFLAGS-y) -Ilib/cmsis-core -CFLAGS_klipper.elf += -Llib/sam3x/gcc/gcc -CFLAGS_klipper.elf += -T lib/sam3x/gcc/gcc/sam3x8e_flash.ld -CFLAGS_klipper.elf += --specs=nano.specs --specs=nosys.specs +eflags-$(CONFIG_MACH_SAM3X8E) += -Llib/sam3x/gcc/gcc +eflags-$(CONFIG_MACH_SAM3X8E) += -T lib/sam3x/gcc/gcc/sam3x8e_flash.ld +eflags-$(CONFIG_MACH_SAM4E8E) += -Llib/sam4e/gcc/gcc +eflags-$(CONFIG_MACH_SAM4E8E) += -T lib/sam4e/gcc/gcc/sam4e8e_flash.ld +CFLAGS_klipper.elf += $(eflags-y) --specs=nano.specs --specs=nosys.specs # Add source files -src-y += sam3/main.c sam3/timer.c -src-y += sam3/gpio.c sam3/adc.c sam3/spi.c +src-y += sam3/main.c sam3/timer.c sam3/gpio.c src-y += generic/crc16_ccitt.c generic/alloc.c src-y += generic/armcm_irq.c generic/timer_irq.c -src-y += ../lib/sam3x/gcc/system_sam3xa.c -src-y += ../lib/sam3x/gcc/gcc/startup_sam3xa.c src-$(CONFIG_SERIAL) += sam3/serial.c generic/serial_irq.c +src-$(CONFIG_MACH_SAM3X8E) += sam3/adc.c sam3/spi.c +src-$(CONFIG_MACH_SAM3X8E) += ../lib/sam3x/gcc/system_sam3xa.c +src-$(CONFIG_MACH_SAM3X8E) += ../lib/sam3x/gcc/gcc/startup_sam3xa.c +src-$(CONFIG_MACH_SAM4E8E) += sam3/sam4e_afec.c sam3/sam4e_spi.c +src-$(CONFIG_MACH_SAM4E8E) += sam3/i2c.c sam3/sam4_cache.c +src-$(CONFIG_MACH_SAM4E8E) += ../lib/sam4e/gcc/system_sam4e.c +src-$(CONFIG_MACH_SAM4E8E) += ../lib/sam4e/gcc/gcc/startup_sam4e.c # Build the additional hex output file target-y += $(OUT)klipper.bin $(OUT)klipper.bin: $(OUT)klipper.elf - @echo " Creating hex file $@" + @echo " Creating bin file $@" $(Q)$(OBJCOPY) -O binary $< $@ # Flash rules diff --git a/src/sam3/adc.c b/src/sam3/adc.c index 4a4d2cf0..b9c5fb12 100644 --- a/src/sam3/adc.c +++ b/src/sam3/adc.c @@ -10,7 +10,6 @@ #include "compiler.h" // ARRAY_SIZE #include "gpio.h" // gpio_adc_setup #include "internal.h" // GPIO -#include "sam3x8e.h" // ADC #include "sched.h" // sched_shutdown static const uint8_t adc_pins[] = { @@ -43,7 +42,7 @@ gpio_adc_setup(uint8_t pin) | ADC_MR_STARTUP_SUT768 | ADC_MR_TRANSFER(1)); } - return (struct gpio_adc){ .bit = 1 << chan }; + return (struct gpio_adc){ .chan = 1 << chan }; } // Try to sample a value. Returns zero if sample ready, otherwise @@ -55,11 +54,11 @@ gpio_adc_sample(struct gpio_adc g) uint32_t chsr = ADC->ADC_CHSR & 0xffff; if (!chsr) { // Start sample - ADC->ADC_CHER = g.bit; + ADC->ADC_CHER = g.chan; ADC->ADC_CR = ADC_CR_START; goto need_delay; } - if (chsr != g.bit) + if (chsr != g.chan) // Sampling in progress on another channel goto need_delay; if (!(ADC->ADC_ISR & ADC_ISR_DRDY)) @@ -75,7 +74,7 @@ need_delay: uint16_t gpio_adc_read(struct gpio_adc g) { - ADC->ADC_CHDR = g.bit; + ADC->ADC_CHDR = g.chan; return ADC->ADC_LCDR; } @@ -84,7 +83,7 @@ void gpio_adc_cancel_sample(struct gpio_adc g) { irqstatus_t flag = irq_save(); - if ((ADC->ADC_CHSR & 0xffff) == g.bit) + if ((ADC->ADC_CHSR & 0xffff) == g.chan) gpio_adc_read(g); irq_restore(flag); } diff --git a/src/sam3/gpio.c b/src/sam3/gpio.c index f48c5f0d..a0dfa0a4 100644 --- a/src/sam3/gpio.c +++ b/src/sam3/gpio.c @@ -1,4 +1,4 @@ -// GPIO functions on sam3x8e +// GPIO functions on sam3/sam4 // // Copyright (C) 2016-2018 Kevin O'Connor // @@ -9,11 +9,14 @@ #include "compiler.h" // ARRAY_SIZE #include "gpio.h" // gpio_out_setup #include "internal.h" // gpio_peripheral -#include "sam3x8e.h" // Pio #include "sched.h" // sched_shutdown static Pio * const digital_regs[] = { +#if CONFIG_MACH_SAM3X8E PIOA, PIOB, PIOC, PIOD +#elif CONFIG_MACH_SAM4E8E + PIOA, PIOB, PIOC, PIOD, PIOE +#endif }; @@ -24,12 +27,16 @@ static Pio * const digital_regs[] = { void gpio_peripheral(uint32_t gpio, char ptype, int32_t pull_up) { - uint32_t bank = GPIO2PORT(gpio), bit = GPIO2BIT(gpio); + uint32_t bank = GPIO2PORT(gpio), bit = GPIO2BIT(gpio), pt = ptype - 'A'; Pio *regs = digital_regs[bank]; - if (ptype == 'A') - regs->PIO_ABSR &= ~bit; - else - regs->PIO_ABSR |= bit; + +#if CONFIG_MACH_SAM3X8E + regs->PIO_ABSR = (regs->PIO_ABSR & ~bit) | (pt & 0x01 ? bit : 0); +#else + regs->PIO_ABCDSR[0] = (regs->PIO_ABCDSR[0] & ~bit) | (pt & 0x01 ? bit : 0); + regs->PIO_ABCDSR[1] = (regs->PIO_ABCDSR[1] & ~bit) | (pt & 0x02 ? bit : 0); +#endif + if (pull_up > 0) regs->PIO_PUER = bit; else diff --git a/src/sam3/gpio.h b/src/sam3/gpio.h index 1c412d8d..26a05aff 100644 --- a/src/sam3/gpio.h +++ b/src/sam3/gpio.h @@ -22,7 +22,7 @@ void gpio_in_reset(struct gpio_in g, int8_t pull_up); uint8_t gpio_in_read(struct gpio_in g); struct gpio_adc { - uint32_t bit; + uint32_t chan; }; struct gpio_adc gpio_adc_setup(uint8_t pin); uint32_t gpio_adc_sample(struct gpio_adc g); @@ -30,6 +30,7 @@ uint16_t gpio_adc_read(struct gpio_adc g); void gpio_adc_cancel_sample(struct gpio_adc g); struct spi_config { + void *sspi; uint32_t cfg; }; struct spi_config spi_setup(uint32_t bus, uint8_t mode, uint32_t rate); @@ -37,4 +38,14 @@ void spi_prepare(struct spi_config config); void spi_transfer(struct spi_config config, uint8_t receive_data , uint8_t len, uint8_t *data); +struct i2c_config { + void *twi; + uint8_t addr; +}; + +struct i2c_config i2c_setup(uint32_t bus, uint32_t rate, uint8_t addr); +void i2c_write(struct i2c_config config, uint8_t write_len, uint8_t *write); +void i2c_read(struct i2c_config config, uint8_t reg_len, uint8_t *reg + , uint8_t read_len, uint8_t *read); + #endif // gpio.h diff --git a/src/sam4e8e/i2c.c b/src/sam3/i2c.c similarity index 100% rename from src/sam4e8e/i2c.c rename to src/sam3/i2c.c diff --git a/src/sam3/internal.h b/src/sam3/internal.h index 8246d7a4..d90dda0b 100644 --- a/src/sam3/internal.h +++ b/src/sam3/internal.h @@ -1,8 +1,15 @@ #ifndef __SAM3_INTERNAL_H #define __SAM3_INTERNAL_H -// Local definitions for sam3 code +// Local definitions for sam3/sam4 code #include // uint32_t +#include "autoconf.h" // CONFIG_MACH_SAM3X8E + +#if CONFIG_MACH_SAM3X8E +#include "sam3x8e.h" +#elif CONFIG_MACH_SAM4E8E +#include "sam4e.h" +#endif #define GPIO(PORT, NUM) (((PORT)-'A') * 32 + (NUM)) #define GPIO2PORT(PIN) ((PIN) / 32) diff --git a/src/sam3/main.c b/src/sam3/main.c index dd8445ac..3908fddb 100644 --- a/src/sam3/main.c +++ b/src/sam3/main.c @@ -1,14 +1,14 @@ -// Main starting point for SAM3x8e boards. +// Main starting point for SAM3/SAM4 boards // -// Copyright (C) 2016,2017 Kevin O'Connor +// Copyright (C) 2016-2018 Kevin O'Connor // // This file may be distributed under the terms of the GNU GPLv3 license. #include "command.h" // DECL_CONSTANT -#include "sam3x8e.h" // WDT +#include "internal.h" // WDT #include "sched.h" // sched_main -DECL_CONSTANT(MCU, "sam3x8e"); +DECL_CONSTANT(MCU, CONFIG_MCU); /**************************************************************** diff --git a/src/sam4e8e/sam4_cache.c b/src/sam3/sam4_cache.c similarity index 100% rename from src/sam4e8e/sam4_cache.c rename to src/sam3/sam4_cache.c diff --git a/src/sam4e8e/afec.c b/src/sam3/sam4e_afec.c similarity index 100% rename from src/sam4e8e/afec.c rename to src/sam3/sam4e_afec.c diff --git a/src/sam4e8e/spi.c b/src/sam3/sam4e_spi.c similarity index 100% rename from src/sam4e8e/spi.c rename to src/sam3/sam4e_spi.c diff --git a/src/sam3/serial.c b/src/sam3/serial.c index 1fe55751..e0249448 100644 --- a/src/sam3/serial.c +++ b/src/sam3/serial.c @@ -1,4 +1,4 @@ -// sam3x8e serial port +// sam3/sam4 serial port // // Copyright (C) 2016-2018 Kevin O'Connor // @@ -7,50 +7,65 @@ #include "autoconf.h" // CONFIG_SERIAL_BAUD #include "board/serial_irq.h" // serial_rx_data #include "internal.h" // gpio_peripheral -#include "sam3x8e.h" // UART #include "sched.h" // DECL_INIT +// Serial port pins +#if CONFIG_MACH_SAM3X8E +#define Serial_IRQ_Handler UART_Handler +static Uart * const Port = UART; +static const uint32_t Pmc_id = ID_UART, Irq_id = UART_IRQn; +static const uint32_t rx_pin = GPIO('A', 8); +static const uint32_t tx_pin = GPIO('A', 9); +#elif CONFIG_MACH_SAM4E8E +#define Serial_IRQ_Handler UART0_Handler +static Uart * const Port = UART0; +static const uint32_t Pmc_id = ID_UART0, Irq_id = UART0_IRQn; +static const uint32_t rx_pin = GPIO('A', 9); +static const uint32_t tx_pin = GPIO('A', 10); +#endif + void serial_init(void) { - gpio_peripheral(GPIO('A', 8), 'A', 1); - gpio_peripheral(GPIO('A', 9), 'A', 0); + gpio_peripheral(rx_pin, 'A', 1); + gpio_peripheral(tx_pin, 'A', 0); // Reset uart - PMC->PMC_PCER0 = 1 << ID_UART; - UART->UART_PTCR = UART_PTCR_RXTDIS | UART_PTCR_TXTDIS; - UART->UART_CR = UART_CR_RSTRX | UART_CR_RSTTX | UART_CR_RXDIS | UART_CR_TXDIS; - UART->UART_IDR = 0xFFFFFFFF; + PMC->PMC_PCER0 = 1 << Pmc_id; + Port->UART_PTCR = UART_PTCR_RXTDIS | UART_PTCR_TXTDIS; + Port->UART_CR = (UART_CR_RSTRX | UART_CR_RSTTX + | UART_CR_RXDIS | UART_CR_TXDIS); + Port->UART_IDR = 0xFFFFFFFF; // Enable uart - UART->UART_MR = (US_MR_CHRL_8_BIT | US_MR_NBSTOP_1_BIT | UART_MR_PAR_NO + Port->UART_MR = (US_MR_CHRL_8_BIT | US_MR_NBSTOP_1_BIT | UART_MR_PAR_NO | UART_MR_CHMODE_NORMAL); - UART->UART_BRGR = SystemCoreClock / (16 * CONFIG_SERIAL_BAUD); - UART->UART_IER = UART_IER_RXRDY; - NVIC_EnableIRQ(UART_IRQn); - NVIC_SetPriority(UART_IRQn, 0); - UART->UART_CR = UART_CR_RXEN | UART_CR_TXEN; + Port->UART_BRGR = SystemCoreClock / (16 * CONFIG_SERIAL_BAUD); + Port->UART_IER = UART_IER_RXRDY; + NVIC_EnableIRQ(Irq_id); + NVIC_SetPriority(Irq_id, 0); + Port->UART_CR = UART_CR_RXEN | UART_CR_TXEN; } DECL_INIT(serial_init); void __visible -UART_Handler(void) +Serial_IRQ_Handler(void) { - uint32_t status = UART->UART_SR; + uint32_t status = Port->UART_SR; if (status & UART_SR_RXRDY) - serial_rx_byte(UART->UART_RHR); + serial_rx_byte(Port->UART_RHR); if (status & UART_SR_TXRDY) { uint8_t data; int ret = serial_get_tx_byte(&data); if (ret) - UART->UART_IDR = UART_IDR_TXRDY; + Port->UART_IDR = UART_IDR_TXRDY; else - UART->UART_THR = data; + Port->UART_THR = data; } } void serial_enable_tx_irq(void) { - UART->UART_IER = UART_IDR_TXRDY; + Port->UART_IER = UART_IDR_TXRDY; } diff --git a/src/sam3/spi.c b/src/sam3/spi.c index 91b28e34..b6b832e5 100644 --- a/src/sam3/spi.c +++ b/src/sam3/spi.c @@ -1,10 +1,9 @@ -// SPI transmissions on sam3x8e +// SPI transmissions on sam3 // // Copyright (C) 2018 Petri Honkala // // This file may be distributed under the terms of the GNU GPLv3 license. -#include // REGPTR #include "command.h" // shutdown #include "gpio.h" // spi_setup #include "internal.h" // gpio_peripheral diff --git a/src/sam3/timer.c b/src/sam3/timer.c index f7698c65..d5bc8c6a 100644 --- a/src/sam3/timer.c +++ b/src/sam3/timer.c @@ -1,6 +1,6 @@ -// SAM3x8e timer interrupt scheduling +// SAM3/SAM4 timer interrupt scheduling // -// Copyright (C) 2016,2017 Kevin O'Connor +// Copyright (C) 2016-2018 Kevin O'Connor // // This file may be distributed under the terms of the GNU GPLv3 license. @@ -8,7 +8,7 @@ #include "board/misc.h" // timer_read_time #include "board/timer_irq.h" // timer_dispatch_many #include "command.h" // DECL_SHUTDOWN -#include "sam3x8e.h" // TC0 +#include "internal.h" // TC0 #include "sched.h" // DECL_INIT // Set the next irq time diff --git a/src/sam4e8e/Kconfig b/src/sam4e8e/Kconfig deleted file mode 100644 index 72e21857..00000000 --- a/src/sam4e8e/Kconfig +++ /dev/null @@ -1,30 +0,0 @@ -# Kconfig settings for SAM4e8e processors - -if MACH_SAM4E8E - -config SAM_SELECT - bool - default y - select HAVE_GPIO - select HAVE_GPIO_I2C - select HAVE_GPIO_ADC - select HAVE_GPIO_SPI - select HAVE_GPIO_BITBANGING - -config BOARD_DIRECTORY - string - default "sam4e8e" - -config CLOCK_FREQ - int - default 60000000 # 120000000/2 - -config SERIAL - bool - default y -config SERIAL_BAUD - depends on SERIAL - int "Baud rate for serial port" - default 250000 - -endif diff --git a/src/sam4e8e/Makefile b/src/sam4e8e/Makefile deleted file mode 100644 index a80741bf..00000000 --- a/src/sam4e8e/Makefile +++ /dev/null @@ -1,41 +0,0 @@ -# Additional sam4e8e build rules - -# Setup the toolchain -CROSS_PREFIX=arm-none-eabi- -dirs-y += src/sam4e8e src/generic - -CFLAGS += -mthumb -mcpu=cortex-m4 -mfpu=fpv4-sp-d16 -mfloat-abi=hard -CFLAGS += -D__SAM4E8E__ - -CFLAGS_klipper.elf += -L lib/sam4e/gcc/gcc -CFLAGS_klipper.elf += -T lib/sam4e/gcc/gcc/sam4e8e_flash.ld -CFLAGS_klipper.elf += --specs=nano.specs --specs=nosys.specs - -dirs-y += lib/sam4e/gcc lib/sam4e/gcc/gcc -CFLAGS += -Ilib/sam4e/include -Ilib/cmsis-core -src-y += ../lib/sam4e/gcc/system_sam4e.c ../lib/sam4e/gcc/gcc/startup_sam4e.c - -src-$(CONFIG_HAVE_GPIO_SPI) += sam4e8e/spi.c -src-$(CONFIG_HAVE_GPIO_I2C) += sam4e8e/i2c.c -src-$(CONFIG_SERIAL) += sam4e8e/serial.c generic/serial_irq.c -src-$(CONFIG_HAVE_GPIO) += sam4e8e/gpio.c sam4e8e/afec.c -src-y += generic/crc16_ccitt.c generic/alloc.c -src-y += generic/armcm_irq.c generic/timer_irq.c -src-y += sam4e8e/main.c sam4e8e/sam4_cache.c sam4e8e/timer.c - -# Build the additional hex output file -target-y += $(OUT)klipper.bin - -$(OUT)klipper.bin: $(OUT)klipper.elf - @echo " Creating bin file $@" - $(Q)$(OBJCOPY) -O binary $< $@ - -# Flash rules -lib/bossac/bin/bossac: - @echo " Building bossac" - $(Q)make -C lib/bossac bin/bossac - -flash: $(OUT)klipper.bin lib/bossac/bin/bossac - @echo " Flashing $^ to $(FLASH_DEVICE) via bossac" - $(Q)if [ -z $(FLASH_DEVICE) ]; then echo "Please specify FLASH_DEVICE"; exit 1; fi - $(Q)lib/bossac/bin/bossac -U -p "$(FLASH_DEVICE)" -e -w $(OUT)klipper.bin -v -b -R diff --git a/src/sam4e8e/gpio.c b/src/sam4e8e/gpio.c deleted file mode 100644 index 3e2c9796..00000000 --- a/src/sam4e8e/gpio.c +++ /dev/null @@ -1,173 +0,0 @@ -// SAM4e8e GPIO port -// -// Copyright (C) 2018 Florian Heilmann -// -// This file may be distributed under the terms of the GNU GPLv3 license. - -#include "board/irq.h" // irq_save -#include "command.h" // shutdown -#include "gpio.h" // gpio_out_setup -#include "internal.h" // gpio_peripheral -#include "sam4e.h" // Pio -#include "sched.h" // sched_shutdown - -static Pio * const digital_regs[] = { - PIOA, PIOB, PIOC, PIOD, PIOE -}; - - -/**************************************************************** - * Pin multiplexing - ****************************************************************/ - -void -gpio_peripheral(uint32_t gpio, char ptype, int32_t pull_up) -{ - uint32_t bank = GPIO2PORT(gpio), bit = GPIO2BIT(gpio); - Pio *regs = digital_regs[bank]; - regs ->PIO_IDR = bit; - - // Enable peripheral for pin - uint32_t sr; - - switch (ptype) { - case 'A': - sr = regs->PIO_ABCDSR[0]; - regs->PIO_ABCDSR[0] &= (~bit & sr); - sr = regs->PIO_ABCDSR[1]; - regs->PIO_ABCDSR[1] &= (~bit & sr); - break; - case 'B': - sr = regs->PIO_ABCDSR[0]; - regs->PIO_ABCDSR[0] = (bit | sr); - sr = regs->PIO_ABCDSR[1]; - regs->PIO_ABCDSR[1] &= (~bit & sr); - break; - case 'C': - sr = regs->PIO_ABCDSR[0]; - regs->PIO_ABCDSR[0] &= (~bit & sr); - sr = regs->PIO_ABCDSR[1]; - regs->PIO_ABCDSR[1] = (bit | sr); - break; - case 'D': - sr = regs->PIO_ABCDSR[0]; - regs->PIO_ABCDSR[0] = (bit | sr); - sr = regs->PIO_ABCDSR[1]; - regs->PIO_ABCDSR[1] = (bit | sr); - break; - } - - // Disable pin in IO controller - regs->PIO_PDR = bit; - - // Set pullup - if (pull_up > 0) { - regs->PIO_PUER = bit; - } else { - regs->PIO_PUDR = bit; - } -} - - -/**************************************************************** - * General Purpose Input Output (GPIO) pins - ****************************************************************/ - -struct gpio_out -gpio_out_setup(uint8_t pin, uint8_t val) -{ - if (GPIO2PORT(pin) >= ARRAY_SIZE(digital_regs)) - goto fail; - uint32_t port = GPIO2PORT(pin); - Pio *regs = digital_regs[port]; - uint32_t bank_id = ID_PIOA + port; - if ((PMC->PMC_PCSR0 & (1u << bank_id)) == 0) { - PMC->PMC_PCER0 = 1 << bank_id; - } - struct gpio_out g = { .regs=regs, .bit=GPIO2BIT(pin) }; - gpio_out_reset(g, val); - return g; -fail: - shutdown("Not an output pin"); -} - -void -gpio_out_reset(struct gpio_out g, uint8_t val) -{ - Pio *regs = g.regs; - irqstatus_t flag = irq_save(); - if (val) - regs->PIO_SODR = g.bit; - else - regs->PIO_CODR = g.bit; - regs->PIO_OER = g.bit; - regs->PIO_OWER = g.bit; - regs->PIO_PER = g.bit; - regs->PIO_PUDR = g.bit; - irq_restore(flag); -} - -void -gpio_out_toggle_noirq(struct gpio_out g) -{ - Pio *regs = g.regs; - regs->PIO_ODSR ^= g.bit; -} - -void -gpio_out_toggle(struct gpio_out g) -{ - irqstatus_t flag = irq_save(); - gpio_out_toggle_noirq(g); - irq_restore(flag); -} - -void -gpio_out_write(struct gpio_out g, uint8_t val) -{ - Pio *regs = g.regs; - if (val) - regs->PIO_SODR = g.bit; - else - regs->PIO_CODR = g.bit; -} - -struct gpio_in -gpio_in_setup(uint8_t pin, int8_t pull_up) -{ - if (GPIO2PORT(pin) >= ARRAY_SIZE(digital_regs)) - goto fail; - uint32_t port = GPIO2PORT(pin); - Pio *regs = digital_regs[port]; - uint32_t bank_id = ID_PIOA + port; - if ((PMC->PMC_PCSR0 & (1u << bank_id)) == 0) { - PMC->PMC_PCER0 = 1 << bank_id; - } - struct gpio_in g = { .regs=regs, .bit=GPIO2BIT(pin) }; - gpio_in_reset(g, pull_up); - return g; -fail: - shutdown("Not an input pin"); -} - -void -gpio_in_reset(struct gpio_in g, int8_t pull_up) -{ - Pio *regs = g.regs; - irqstatus_t flag = irq_save(); - regs->PIO_IDR = g.bit; - if (pull_up) - regs->PIO_PUER = g.bit; - else - regs->PIO_PUDR = g.bit; - regs->PIO_ODR = g.bit; - regs->PIO_PER = g.bit; - irq_restore(flag); -} - -uint8_t -gpio_in_read(struct gpio_in g) -{ - Pio *regs = g.regs; - return !!(regs->PIO_PDSR & g.bit); -} diff --git a/src/sam4e8e/gpio.h b/src/sam4e8e/gpio.h deleted file mode 100644 index a32a59a7..00000000 --- a/src/sam4e8e/gpio.h +++ /dev/null @@ -1,57 +0,0 @@ -#ifndef __SAM4E8E_GPIO_H -#define __SAM4E8E_GPIO_H - -#include - -struct gpio_out { - uint8_t pin; - void *regs; - uint32_t bit; -}; - -struct gpio_out gpio_out_setup(uint8_t pin, uint8_t val); -void gpio_out_reset(struct gpio_out g, uint8_t val); -void gpio_out_toggle_noirq(struct gpio_out g); -void gpio_out_toggle(struct gpio_out g); -void gpio_out_write(struct gpio_out g, uint8_t val); - -struct gpio_in { - uint8_t pin; - void *regs; - uint32_t bit; -}; - -struct gpio_in gpio_in_setup(uint8_t pin, int8_t pull_up); -void gpio_in_reset(struct gpio_in g, int8_t pull_up); -uint8_t gpio_in_read(struct gpio_in g); - -struct gpio_adc { - uint32_t chan; -}; - -struct gpio_adc gpio_adc_setup(uint8_t pin); -uint32_t gpio_adc_sample(struct gpio_adc g); -uint16_t gpio_adc_read(struct gpio_adc g); -void gpio_adc_cancel_sample(struct gpio_adc g); - -struct spi_config { - void *sspi; - uint32_t cfg; -}; -struct spi_config spi_setup(uint32_t bus, uint8_t mode, uint32_t rate); -void spi_transfer(struct spi_config config, uint8_t receive_data - , uint8_t len, uint8_t *data); -void spi_prepare(struct spi_config config); - -struct i2c_config { - void *twi; - uint8_t addr; -}; - -struct i2c_config i2c_setup(uint32_t bus, uint32_t rate, uint8_t addr); -void i2c_write(struct i2c_config config, - uint8_t write_len, uint8_t *write); -void i2c_read(struct i2c_config config, - uint8_t reg_len, uint8_t *reg, - uint8_t read_len, uint8_t *read); -#endif // gpio.h diff --git a/src/sam4e8e/internal.h b/src/sam4e8e/internal.h deleted file mode 100644 index cf0e0f81..00000000 --- a/src/sam4e8e/internal.h +++ /dev/null @@ -1,13 +0,0 @@ -#ifndef __SAM4_INTERNAL_H -#define __SAM4_INTERNAL_H -// Local definitions for sam4 code - -#include // uint32_t - -#define GPIO(PORT, NUM) (((PORT)-'A') * 32 + (NUM)) -#define GPIO2PORT(PIN) ((PIN) / 32) -#define GPIO2BIT(PIN) (1<<((PIN) % 32)) - -void gpio_peripheral(uint32_t gpio, char ptype, int32_t pull_up); - -#endif // internal.h diff --git a/src/sam4e8e/main.c b/src/sam4e8e/main.c deleted file mode 100644 index f3666075..00000000 --- a/src/sam4e8e/main.c +++ /dev/null @@ -1,48 +0,0 @@ -// SAM4e8e port main entry -// -// Copyright (C) 2018 Florian Heilmann -// -// This file may be distributed under the terms of the GNU GPLv3 license. - -// CMSIS -#include "sam4e.h" - -// Klipper -#include "command.h" // DECL_CONSTANT -#include "sched.h" // sched_main - -DECL_CONSTANT(MCU, "sam4e8e"); - -#define WDT_PASSWORD 0xA5000000 -#define WDT_SLOW_CLOCK_DIV 128 - -void -watchdog_reset(void) -{ - WDT->WDT_CR = WDT_PASSWORD | WDT_CR_WDRSTT; -} -DECL_TASK(watchdog_reset); - -void -watchdog_init(void) -{ - uint32_t timeout = 500000 / (WDT_SLOW_CLOCK_DIV * 1000000 / 32768UL); - WDT->WDT_MR = WDT_MR_WDRSTEN | WDT_MR_WDV(timeout) | WDT_MR_WDD(timeout); -} -DECL_INIT(watchdog_init); - -void -command_reset(uint32_t *args) -{ - NVIC_SystemReset(); -} -DECL_COMMAND_FLAGS(command_reset, HF_IN_SHUTDOWN, "reset"); - -// Main entry point -int -main(void) -{ - SystemInit(); - sched_main(); - return 0; -} diff --git a/src/sam4e8e/serial.c b/src/sam4e8e/serial.c deleted file mode 100644 index c75623bc..00000000 --- a/src/sam4e8e/serial.c +++ /dev/null @@ -1,56 +0,0 @@ -// SAM4e8e serial port -// -// Copyright (C) 2018 Florian Heilmann -// -// This file may be distributed under the terms of the GNU GPLv3 license. - -#include "autoconf.h" // CONFIG_SERIAL_BAUD -#include "board/serial_irq.h" // serial_rx_data -#include "internal.h" // gpio_peripheral -#include "sam4e.h" // UART0 -#include "sched.h" // DECL_INIT - -void -serial_init(void) -{ - gpio_peripheral(GPIO('A', 9), 'A', 1); - gpio_peripheral(GPIO('A', 10), 'A', 0); - - // Reset uart - PMC->PMC_PCER0 = 1 << ID_UART0; - UART0->UART_PTCR = UART_PTCR_RXTDIS | UART_PTCR_TXTDIS; - UART0->UART_CR = UART_CR_RSTRX | UART_CR_RSTTX | UART_CR_RXDIS | UART_CR_TXDIS; - UART0->UART_IDR = 0xFFFFFFFF; - - // Enable uart - UART0->UART_MR = (US_MR_CHRL_8_BIT | US_MR_NBSTOP_1_BIT | UART_MR_PAR_NO - | UART_MR_CHMODE_NORMAL); - UART0->UART_BRGR = SystemCoreClock / (16 * CONFIG_SERIAL_BAUD); - UART0->UART_IER = UART_IER_RXRDY; - NVIC_EnableIRQ(UART0_IRQn); - NVIC_SetPriority(UART0_IRQn, 0); - UART0->UART_CR = UART_CR_RXEN | UART_CR_TXEN; -} -DECL_INIT(serial_init); - -void __visible -UART0_Handler(void) -{ - uint32_t status = UART0->UART_SR; - if (status & UART_SR_RXRDY) - serial_rx_byte(UART0->UART_RHR); - if (status & UART_SR_TXRDY) { - uint8_t data; - int ret = serial_get_tx_byte(&data); - if (ret) - UART0->UART_IDR = UART_IDR_TXRDY; - else - UART0->UART_THR = data; - } -} - -void -serial_enable_tx_irq(void) -{ - UART0->UART_IER = UART_IDR_TXRDY; -} diff --git a/src/sam4e8e/timer.c b/src/sam4e8e/timer.c deleted file mode 100644 index 8115ea8a..00000000 --- a/src/sam4e8e/timer.c +++ /dev/null @@ -1,67 +0,0 @@ -// SAM4e8e timer port -// -// Copyright (C) 2018 Florian Heilmann -// -// This file may be distributed under the terms of the GNU GPLv3 license. - -// CMSIS -#include "sam4e.h" -// Klipper -#include "board/irq.h" // irq_disable -#include "board/misc.h" // timer_read_time -#include "board/timer_irq.h" // timer_dispatch_many -#include "sched.h" // DECL_INIT - -// Set the next irq time -static void -timer_set(uint32_t value) -{ - TC0->TC_CHANNEL[0].TC_RA = value; -} - -// Return the current time (in absolute clock ticks). -uint32_t -timer_read_time(void) -{ - return TC0->TC_CHANNEL[0].TC_CV; -} - -// Activate timer dispatch as soon as possible -void -timer_kick(void) -{ - timer_set(timer_read_time() + 50); - TC0->TC_CHANNEL[0].TC_SR; -} - -void -timer_init(void) -{ - if ((PMC->PMC_PCSR0 & (1u << ID_TC0)) == 0) { - PMC->PMC_PCER0 = 1 << ID_TC0; - } - TcChannel *tc_channel = &TC0->TC_CHANNEL[0]; - tc_channel->TC_CCR = TC_CCR_CLKDIS; - tc_channel->TC_IDR = 0xFFFFFFFF; - tc_channel->TC_SR; - tc_channel->TC_CMR = TC_CMR_WAVE | TC_CMR_WAVSEL_UP | TC_CMR_TCCLKS_TIMER_CLOCK1; - tc_channel->TC_IER = TC_IER_CPAS; - NVIC_SetPriority(TC0_IRQn, 1); - NVIC_EnableIRQ(TC0_IRQn); - timer_kick(); - tc_channel->TC_CCR = TC_CCR_CLKEN | TC_CCR_SWTRG; -} -DECL_INIT(timer_init); - -// IRQ handler -void __visible __aligned(16) // aligning helps stabilize perf benchmarks -TC0_Handler(void) -{ - irq_disable(); - uint32_t status = TC0->TC_CHANNEL[0].TC_SR; - if (likely(status & TC_SR_CPAS)) { - uint32_t next = timer_dispatch_many(); - timer_set(next); - } - irq_enable(); -} diff --git a/test/configs/sam3x8e.config b/test/configs/sam3x8e.config index a388f836..9bf772a8 100644 --- a/test/configs/sam3x8e.config +++ b/test/configs/sam3x8e.config @@ -1,2 +1,3 @@ # Base config file for Atmel SAM3x8e ARM processor +CONFIG_MACH_SAM3=y CONFIG_MACH_SAM3X8E=y diff --git a/test/configs/sam4e8e.config b/test/configs/sam4e8e.config index 06147213..d55a5bfe 100644 --- a/test/configs/sam4e8e.config +++ b/test/configs/sam4e8e.config @@ -1,2 +1,3 @@ # Base config file for Atmel SAM4E8E ARM processor +CONFIG_MACH_SAM3=y CONFIG_MACH_SAM4E8E=y