WIP simulator support

This commit is contained in:
joeycastillo
2024-10-06 15:19:59 -04:00
parent 39e498dfa2
commit 0c577b89e9
53 changed files with 4876 additions and 3 deletions

1
.gitignore vendored
View File

@ -1,4 +1,5 @@
**/build/
**/build-sim/
*.b#*
*.bin
*.d

View File

@ -0,0 +1,136 @@
/*
* Copyright (c) 2024 Joey Castillo
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
//-----------------------------------------------------------------------------
#define DUMMY __attribute__ ((weak, alias ("irq_handler_dummy")))
//-----------------------------------------------------------------------------
void irq_handler_reset(void);
void irq_handler_dummy(void);
void _exit(int status);
DUMMY void irq_handler_nmi(void);
DUMMY void irq_handler_hard_fault(void);
DUMMY void irq_handler_sv_call(void);
DUMMY void irq_handler_pend_sv(void);
DUMMY void irq_handler_sys_tick(void);
DUMMY void irq_handler_pm(void);
DUMMY void irq_handler_sysctrl(void);
DUMMY void irq_handler_wdt(void);
DUMMY void irq_handler_rtc(void);
DUMMY void irq_handler_eic(void);
DUMMY void irq_handler_nvmctrl(void);
DUMMY void irq_handler_dmac(void);
DUMMY void irq_handler_usb(void);
DUMMY void irq_handler_evsys(void);
DUMMY void irq_handler_sercom0(void);
DUMMY void irq_handler_sercom1(void);
DUMMY void irq_handler_sercom2(void);
DUMMY void irq_handler_tcc0(void);
DUMMY void irq_handler_tc1(void);
DUMMY void irq_handler_tc2(void);
DUMMY void irq_handler_adc(void);
DUMMY void irq_handler_ac(void);
DUMMY void irq_handler_dac(void);
DUMMY void irq_handler_ptc(void);
extern int main(void);
void _stack_top(void) {};
extern unsigned int _etext;
extern unsigned int _data;
extern unsigned int _edata;
extern unsigned int _bss;
extern unsigned int _ebss;
//-----------------------------------------------------------------------------
__attribute__ ((used, section(".vectors")))
void (* const vectors[])(void) =
{
&_stack_top, // 0 - Initial Stack Pointer Value
// Cortex-M0+ handlers
irq_handler_reset, // 1 - Reset
irq_handler_nmi, // 2 - NMI
irq_handler_hard_fault, // 3 - Hard Fault
0, // 4 - Reserved
0, // 5 - Reserved
0, // 6 - Reserved
0, // 7 - Reserved
0, // 8 - Reserved
0, // 9 - Reserved
0, // 10 - Reserved
irq_handler_sv_call, // 11 - SVCall
0, // 12 - Reserved
0, // 13 - Reserved
irq_handler_pend_sv, // 14 - PendSV
irq_handler_sys_tick, // 15 - SysTick
// Peripheral handlers
irq_handler_pm, // 0 - Power Manager
irq_handler_sysctrl, // 1 - System Controller
irq_handler_wdt, // 2 - Watchdog Timer
irq_handler_rtc, // 3 - Real Time Counter
irq_handler_eic, // 4 - External Interrupt Controller
irq_handler_nvmctrl, // 5 - Non-Volatile Memory Controller
irq_handler_dmac, // 6 - Direct Memory Access Controller
irq_handler_usb, // 7 - USB Controller
irq_handler_evsys, // 8 - Event System
irq_handler_sercom0, // 9 - Serial Communication Interface 0
irq_handler_sercom1, // 10 - Serial Communication Interface 1
irq_handler_sercom2, // 11 - Serial Communication Interface 2
irq_handler_tcc0, // 12 - Timer/Counter for Control 0
irq_handler_tc1, // 13 - Timer/Counter 1
irq_handler_tc2, // 14 - Timer/Counter 2
irq_handler_adc, // 15 - Analog-to-Digital Converter
irq_handler_ac, // 16 - Analog Comparator
irq_handler_dac, // 17 - Digital-to-Analog Converter
irq_handler_ptc, // 18 - Peripheral Touch Controller
};
//-----------------------------------------------------------------------------
void irq_handler_reset(void)
{
main();
while (1);
}
//-----------------------------------------------------------------------------
void irq_handler_dummy(void)
{
while (1);
}
//-----------------------------------------------------------------------------
void _exit(int status)
{
(void)status;
while (1);
}

View File

@ -0,0 +1,62 @@
/*
* Copyright (c) 2024 Joey Castillo
*
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include "system.h"
#include "pins.h"
const tc_instance_details_t TC_Peripherals[] = {
};
const uint8_t Num_TC_Instances = 0;
const uint8_t TC_First_Index = 0;
const tcc_instance_details_t TCC_Peripherals[] = {
};
const uint8_t Num_TCC_Instances = 0;
const sercom_instance_details_t SERCOM_Peripherals[] = {
};
const uint8_t Num_SERCOM_Instances = 0;
//-----------------------------------------------------------------------------
void sys_init(void) {
}
void _enable_48mhz_gclk1(void) {
}
uint32_t get_cpu_frequency(void) {
return 8000000;
}
bool set_cpu_frequency(uint32_t freq) {
return false;
}
void _enter_standby_mode() {
}

View File

@ -0,0 +1,155 @@
/*
* Copyright (c) 2024 Joey Castillo
*
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
//-----------------------------------------------------------------------------
#define DUMMY __attribute__ ((weak, alias ("irq_handler_dummy")))
//-----------------------------------------------------------------------------
void irq_handler_reset(void);
void irq_handler_dummy(void);
void _exit(int status);
DUMMY void irq_handler_nmi(void);
DUMMY void irq_handler_hard_fault(void);
DUMMY void irq_handler_sv_call(void);
DUMMY void irq_handler_pend_sv(void);
DUMMY void irq_handler_sys_tick(void);
DUMMY void irq_handler_pm(void);
DUMMY void irq_handler_sysctrl(void);
DUMMY void irq_handler_wdt(void);
DUMMY void irq_handler_rtc(void);
DUMMY void irq_handler_eic(void);
DUMMY void irq_handler_nvmctrl(void);
DUMMY void irq_handler_dmac(void);
DUMMY void irq_handler_usb(void);
DUMMY void irq_handler_evsys(void);
DUMMY void irq_handler_sercom0(void);
DUMMY void irq_handler_sercom1(void);
DUMMY void irq_handler_sercom2(void);
DUMMY void irq_handler_sercom3(void);
DUMMY void irq_handler_sercom4(void);
DUMMY void irq_handler_sercom5(void);
DUMMY void irq_handler_tcc0(void);
DUMMY void irq_handler_tcc1(void);
DUMMY void irq_handler_tcc2(void);
DUMMY void irq_handler_tc3(void);
DUMMY void irq_handler_tc4(void);
DUMMY void irq_handler_tc5(void);
DUMMY void irq_handler_tc6(void);
DUMMY void irq_handler_tc7(void);
DUMMY void irq_handler_adc(void);
DUMMY void irq_handler_ac(void);
DUMMY void irq_handler_dac(void);
DUMMY void irq_handler_ptc(void);
DUMMY void irq_handler_i2s(void);
extern int main(void);
void _stack_top(void) {};
extern unsigned int _etext;
extern unsigned int _data;
extern unsigned int _edata;
extern unsigned int _bss;
extern unsigned int _ebss;
//-----------------------------------------------------------------------------
__attribute__ ((used, section(".vectors")))
void (* const vectors[])(void) =
{
&_stack_top, // 0 - Initial Stack Pointer Value
// Cortex-M0+ handlers
irq_handler_reset, // 1 - Reset
irq_handler_nmi, // 2 - NMI
irq_handler_hard_fault, // 3 - Hard Fault
0, // 4 - Reserved
0, // 5 - Reserved
0, // 6 - Reserved
0, // 7 - Reserved
0, // 8 - Reserved
0, // 9 - Reserved
0, // 10 - Reserved
irq_handler_sv_call, // 11 - SVCall
0, // 12 - Reserved
0, // 13 - Reserved
irq_handler_pend_sv, // 14 - PendSV
irq_handler_sys_tick, // 15 - SysTick
// Peripheral handlers
irq_handler_pm, // 0 - Power Manager
irq_handler_sysctrl, // 1 - System Controller
irq_handler_wdt, // 2 - Watchdog Timer
irq_handler_rtc, // 3 - Real Time Counter
irq_handler_eic, // 4 - External Interrupt Controller
irq_handler_nvmctrl, // 5 - Non-Volatile Memory Controller
irq_handler_dmac, // 6 - Direct Memory Access Controller
irq_handler_usb, // 7 - Universal Serial Bus Controller
irq_handler_evsys, // 8 - Event System
irq_handler_sercom0, // 9 - Serial Communication Interface 0
irq_handler_sercom1, // 10 - Serial Communication Interface 1
irq_handler_sercom2, // 11 - Serial Communication Interface 2
irq_handler_sercom3, // 12 - Serial Communication Interface 3
irq_handler_sercom4, // 13 - Serial Communication Interface 4
irq_handler_sercom5, // 14 - Serial Communication Interface 5
irq_handler_tcc0, // 15 - Timer/Counter for Control 0
irq_handler_tcc1, // 16 - Timer/Counter for Control 1
irq_handler_tcc2, // 17 - Timer/Counter for Control 2
irq_handler_tc3, // 18 - Timer/Counter 3
irq_handler_tc4, // 19 - Timer/Counter 4
irq_handler_tc5, // 20 - Timer/Counter 5
irq_handler_tc6, // 21 - Timer/Counter 6
irq_handler_tc7, // 22 - Timer/Counter 7
irq_handler_adc, // 23 - Analog-to-Digital Converter
irq_handler_ac, // 24 - Analog Comparator
irq_handler_dac, // 25 - Digital-to-Analog Converter
irq_handler_ptc, // 26 - Peripheral Touch Controller
irq_handler_i2s, // 27 - Inter-IC Sound Interface
};
//-----------------------------------------------------------------------------
void irq_handler_reset(void)
{
main();
while (1);
}
//-----------------------------------------------------------------------------
void irq_handler_dummy(void)
{
while (1);
}
//-----------------------------------------------------------------------------
void _exit(int status)
{
(void)status;
while (1);
}

View File

@ -0,0 +1,62 @@
/*
* Copyright (c) 2024 Joey Castillo
*
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include "system.h"
#include "pins.h"
const tc_instance_details_t TC_Peripherals[] = {
};
const uint8_t Num_TC_Instances = 0;
const uint8_t TC_First_Index = 0;
const tcc_instance_details_t TCC_Peripherals[] = {
};
const uint8_t Num_TCC_Instances = 0;
const sercom_instance_details_t SERCOM_Peripherals[] = {
};
const uint8_t Num_SERCOM_Instances = 0;
//-----------------------------------------------------------------------------
void sys_init(void) {
}
void _enable_48mhz_gclk1(void) {
}
uint32_t get_cpu_frequency(void) {
return 8000000;
}
bool set_cpu_frequency(uint32_t freq) {
return false;
}
void _enter_standby_mode() {
}

View File

@ -0,0 +1,446 @@
/*
* Copyright (c) 2024 Joey Castillo
*
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
//-----------------------------------------------------------------------------
#define DUMMY __attribute__ ((weak, alias ("irq_handler_dummy")))
//-----------------------------------------------------------------------------
void irq_handler_reset(void);
void irq_handler_dummy(void);
void _exit(int status);
DUMMY void irq_handler_nmi(void);
DUMMY void irq_handler_hard_fault(void);
DUMMY void irq_handler_memory_management(void);
DUMMY void irq_handler_bus_fault(void);
DUMMY void irq_handler_usage_fault(void);
DUMMY void irq_handler_sv_call(void);
DUMMY void irq_handler_debug_monitor(void);
DUMMY void irq_handler_pend_sv(void);
DUMMY void irq_handler_sys_tick(void);
DUMMY void irq_handler_pm(void);
DUMMY void irq_handler_mclk(void);
DUMMY void irq_handler_oscctrl_0(void);
DUMMY void irq_handler_oscctrl_1(void);
DUMMY void irq_handler_oscctrl_2(void);
DUMMY void irq_handler_oscctrl_3(void);
DUMMY void irq_handler_oscctrl_4(void);
DUMMY void irq_handler_osc32kctrl(void);
DUMMY void irq_handler_supc_0(void);
DUMMY void irq_handler_supc_1(void);
DUMMY void irq_handler_wdt(void);
DUMMY void irq_handler_rtc(void);
DUMMY void irq_handler_eic_0(void);
DUMMY void irq_handler_eic_1(void);
DUMMY void irq_handler_eic_2(void);
DUMMY void irq_handler_eic_3(void);
DUMMY void irq_handler_eic_4(void);
DUMMY void irq_handler_eic_5(void);
DUMMY void irq_handler_eic_6(void);
DUMMY void irq_handler_eic_7(void);
DUMMY void irq_handler_eic_8(void);
DUMMY void irq_handler_eic_9(void);
DUMMY void irq_handler_eic_10(void);
DUMMY void irq_handler_eic_11(void);
DUMMY void irq_handler_eic_12(void);
DUMMY void irq_handler_eic_13(void);
DUMMY void irq_handler_eic_14(void);
DUMMY void irq_handler_eic_15(void);
DUMMY void irq_handler_freqm(void);
DUMMY void irq_handler_nvmctrl_0(void);
DUMMY void irq_handler_nvmctrl_1(void);
DUMMY void irq_handler_dmac_0(void);
DUMMY void irq_handler_dmac_1(void);
DUMMY void irq_handler_dmac_2(void);
DUMMY void irq_handler_dmac_3(void);
DUMMY void irq_handler_dmac_4(void);
DUMMY void irq_handler_evsys_0(void);
DUMMY void irq_handler_evsys_1(void);
DUMMY void irq_handler_evsys_2(void);
DUMMY void irq_handler_evsys_3(void);
DUMMY void irq_handler_evsys_4(void);
DUMMY void irq_handler_pac(void);
DUMMY void irq_handler_ramecc(void);
DUMMY void irq_handler_sercom0_0(void);
DUMMY void irq_handler_sercom0_1(void);
DUMMY void irq_handler_sercom0_2(void);
DUMMY void irq_handler_sercom0_3(void);
DUMMY void irq_handler_sercom1_0(void);
DUMMY void irq_handler_sercom1_1(void);
DUMMY void irq_handler_sercom1_2(void);
DUMMY void irq_handler_sercom1_3(void);
DUMMY void irq_handler_sercom2_0(void);
DUMMY void irq_handler_sercom2_1(void);
DUMMY void irq_handler_sercom2_2(void);
DUMMY void irq_handler_sercom2_3(void);
DUMMY void irq_handler_sercom3_0(void);
DUMMY void irq_handler_sercom3_1(void);
DUMMY void irq_handler_sercom3_2(void);
DUMMY void irq_handler_sercom3_3(void);
DUMMY void irq_handler_sercom4_0(void);
DUMMY void irq_handler_sercom4_1(void);
DUMMY void irq_handler_sercom4_2(void);
DUMMY void irq_handler_sercom4_3(void);
DUMMY void irq_handler_sercom5_0(void);
DUMMY void irq_handler_sercom5_1(void);
DUMMY void irq_handler_sercom5_2(void);
DUMMY void irq_handler_sercom5_3(void);
DUMMY void irq_handler_sercom6_0(void);
DUMMY void irq_handler_sercom6_1(void);
DUMMY void irq_handler_sercom6_2(void);
DUMMY void irq_handler_sercom6_3(void);
DUMMY void irq_handler_sercom7_0(void);
DUMMY void irq_handler_sercom7_1(void);
DUMMY void irq_handler_sercom7_2(void);
DUMMY void irq_handler_sercom7_3(void);
DUMMY void irq_handler_can0(void);
DUMMY void irq_handler_can1(void);
DUMMY void irq_handler_usb_0(void);
DUMMY void irq_handler_usb_1(void);
DUMMY void irq_handler_usb_2(void);
DUMMY void irq_handler_usb_3(void);
DUMMY void irq_handler_gmac(void);
DUMMY void irq_handler_tcc0_0(void);
DUMMY void irq_handler_tcc0_1(void);
DUMMY void irq_handler_tcc0_2(void);
DUMMY void irq_handler_tcc0_3(void);
DUMMY void irq_handler_tcc0_4(void);
DUMMY void irq_handler_tcc0_5(void);
DUMMY void irq_handler_tcc0_6(void);
DUMMY void irq_handler_tcc1_0(void);
DUMMY void irq_handler_tcc1_1(void);
DUMMY void irq_handler_tcc1_2(void);
DUMMY void irq_handler_tcc1_3(void);
DUMMY void irq_handler_tcc1_4(void);
DUMMY void irq_handler_tcc2_0(void);
DUMMY void irq_handler_tcc2_1(void);
DUMMY void irq_handler_tcc2_2(void);
DUMMY void irq_handler_tcc2_3(void);
DUMMY void irq_handler_tcc3_0(void);
DUMMY void irq_handler_tcc3_1(void);
DUMMY void irq_handler_tcc3_2(void);
DUMMY void irq_handler_tcc4_0(void);
DUMMY void irq_handler_tcc4_1(void);
DUMMY void irq_handler_tcc4_2(void);
DUMMY void irq_handler_tc0(void);
DUMMY void irq_handler_tc1(void);
DUMMY void irq_handler_tc2(void);
DUMMY void irq_handler_tc3(void);
DUMMY void irq_handler_tc4(void);
DUMMY void irq_handler_tc5(void);
DUMMY void irq_handler_tc6(void);
DUMMY void irq_handler_tc7(void);
DUMMY void irq_handler_pdec_0(void);
DUMMY void irq_handler_pdec_1(void);
DUMMY void irq_handler_pdec_2(void);
DUMMY void irq_handler_adc0_0(void);
DUMMY void irq_handler_adc0_1(void);
DUMMY void irq_handler_adc1_0(void);
DUMMY void irq_handler_adc1_1(void);
DUMMY void irq_handler_ac(void);
DUMMY void irq_handler_dac_0(void);
DUMMY void irq_handler_dac_1(void);
DUMMY void irq_handler_dac_2(void);
DUMMY void irq_handler_dac_3(void);
DUMMY void irq_handler_dac_4(void);
DUMMY void irq_handler_i2s(void);
DUMMY void irq_handler_pcc(void);
DUMMY void irq_handler_aes(void);
DUMMY void irq_handler_trng(void);
DUMMY void irq_handler_icm(void);
DUMMY void irq_handler_pukcc(void);
DUMMY void irq_handler_qspi(void);
DUMMY void irq_handler_sdhc0(void);
DUMMY void irq_handler_sdhc1(void);
extern int main(void);
void _stack_top(void) {};
extern unsigned int _etext;
extern unsigned int _data;
extern unsigned int _edata;
extern unsigned int _bss;
extern unsigned int _ebss;
//-----------------------------------------------------------------------------
__attribute__ ((used, section(".vectors")))
void (* const vectors[])(void) =
{
&_stack_top, // 0 - Initial Stack Pointer Value
// Cortex-M4 handlers
irq_handler_reset, // 1 - Reset
irq_handler_nmi, // 2 - NMI
irq_handler_hard_fault, // 3 - Hard Fault
irq_handler_memory_management, // 4 - Memory Management
irq_handler_bus_fault, // 5 - Bus Fault
irq_handler_usage_fault, // 6 - Usage Fault
0, // 7 - Reserved
0, // 8 - Reserved
0, // 9 - Reserved
0, // 10 - Reserved
irq_handler_sv_call, // 11 - SVCall
irq_handler_debug_monitor, // 12 - Debug monitor
0, // 13 - Reserved
irq_handler_pend_sv, // 14 - PendSV
irq_handler_sys_tick, // 15 - SysTick
// Peripheral handlers
irq_handler_pm, // 0 - Power Manager
irq_handler_mclk, // 1 - Main Clock
irq_handler_oscctrl_0, // 2 - OSCCTRL_XOSCFAIL_0, OSCCTRL_XOSCRDY_0
irq_handler_oscctrl_1, // 3 - OSCCTRL_XOSCFAIL_1, OSCCTRL_XOSCRDY_1
irq_handler_oscctrl_2, // 4 - OSCCTRL_DFLLLOCKC, OSCCTRL_DFLLLOCKF, OSCCTRL_DFLLOOB, OSCCTRL_DFLLRCS, OSCCTRL_DFLLRDY
irq_handler_oscctrl_3, // 5 - OSCCTRL_DPLLLCKF_0, OSCCTRL_DPLLLCKR_0, OSCCTRL_DPLLLDRTO_0, OSCCTRL_DPLLLTO_0
irq_handler_oscctrl_4, // 6 - OSCCTRL_DPLLLCKF_1, OSCCTRL_DPLLLCKR_1, OSCCTRL_DPLLLDRTO_1, OSCCTRL_DPLLLTO_1
irq_handler_osc32kctrl, // 7 - 32kHz Oscillators Control
irq_handler_supc_0, // 8 - SUPC_B12SRDY, SUPC_B33SRDY, SUPC_BOD12RDY, SUPC_BOD33RDY, SUPC_VCORERDY, SUPC_VREGRDY
irq_handler_supc_1, // 9 - SUPC_BOD12DET, SUPC_BOD33DET
irq_handler_wdt, // 10 - Watchdog Timer
irq_handler_rtc, // 11 - Real-Time Counter
irq_handler_eic_0, // 12 - External Interrupt Controller
irq_handler_eic_1, // 13 - External Interrupt Controller
irq_handler_eic_2, // 14 - External Interrupt Controller
irq_handler_eic_3, // 15 - External Interrupt Controller
irq_handler_eic_4, // 16 - External Interrupt Controller
irq_handler_eic_5, // 17 - External Interrupt Controller
irq_handler_eic_6, // 18 - External Interrupt Controller
irq_handler_eic_7, // 19 - External Interrupt Controller
irq_handler_eic_8, // 20 - External Interrupt Controller
irq_handler_eic_9, // 21 - External Interrupt Controller
irq_handler_eic_10, // 22 - External Interrupt Controller
irq_handler_eic_11, // 23 - External Interrupt Controller
irq_handler_eic_12, // 24 - External Interrupt Controller
irq_handler_eic_13, // 25 - External Interrupt Controller
irq_handler_eic_14, // 26 - External Interrupt Controller
irq_handler_eic_15, // 27 - External Interrupt Controller
irq_handler_freqm, // 28 - Frequency Measurement
irq_handler_nvmctrl_0, // 29 - Non-Volatile Memory Controller 0-7
irq_handler_nvmctrl_1, // 30 - Non-Volatile Memory Controller 8-10
irq_handler_dmac_0, // 31 - Direct Memory Access Controller
irq_handler_dmac_1, // 32 - Direct Memory Access Controller
irq_handler_dmac_2, // 33 - Direct Memory Access Controller
irq_handler_dmac_3, // 34 - Direct Memory Access Controller
irq_handler_dmac_4, // 35 - Direct Memory Access Controller
irq_handler_evsys_0, // 36 - Event System
irq_handler_evsys_1, // 37 - Event System
irq_handler_evsys_2, // 38 - Event System
irq_handler_evsys_3, // 39 - Event System
irq_handler_evsys_4, // 40 - Event System
irq_handler_pac, // 41 - Peripheral Access Controller
0, // 42 - Reserved
0, // 43 - Reserved
0, // 44 - Reserved
irq_handler_ramecc, // 45 - RAM ECC
irq_handler_sercom0_0, // 46 - Serial Communication Interface 0
irq_handler_sercom0_1, // 47 - Serial Communication Interface 0
irq_handler_sercom0_2, // 48 - Serial Communication Interface 0
irq_handler_sercom0_3, // 49 - Serial Communication Interface 0
irq_handler_sercom1_0, // 50 - Serial Communication Interface 1
irq_handler_sercom1_1, // 51 - Serial Communication Interface 1
irq_handler_sercom1_2, // 52 - Serial Communication Interface 1
irq_handler_sercom1_3, // 53 - Serial Communication Interface 1
irq_handler_sercom2_0, // 54 - Serial Communication Interface 2
irq_handler_sercom2_1, // 55 - Serial Communication Interface 2
irq_handler_sercom2_2, // 56 - Serial Communication Interface 2
irq_handler_sercom2_3, // 57 - Serial Communication Interface 2
irq_handler_sercom3_0, // 58 - Serial Communication Interface 3
irq_handler_sercom3_1, // 59 - Serial Communication Interface 3
irq_handler_sercom3_2, // 60 - Serial Communication Interface 3
irq_handler_sercom3_3, // 61 - Serial Communication Interface 3
#ifdef ID_SERCOM4
irq_handler_sercom4_0, // 62 - Serial Communication Interface 4
irq_handler_sercom4_1, // 63 - Serial Communication Interface 4
irq_handler_sercom4_2, // 64 - Serial Communication Interface 4
irq_handler_sercom4_3, // 65 - Serial Communication Interface 4
#else
0, // 62 - Reserved
0, // 63 - Reserved
0, // 64 - Reserved
0, // 65 - Reserved
#endif
#ifdef ID_SERCOM5
irq_handler_sercom5_0, // 66 - Serial Communication Interface 5
irq_handler_sercom5_1, // 67 - Serial Communication Interface 5
irq_handler_sercom5_2, // 68 - Serial Communication Interface 5
irq_handler_sercom5_3, // 69 - Serial Communication Interface 5
#else
0, // 66 - Reserved
0, // 67 - Reserved
0, // 68 - Reserved
0, // 69 - Reserved
#endif
#ifdef ID_SERCOM6
irq_handler_sercom6_0, // 70 - Serial Communication Interface 6
irq_handler_sercom6_1, // 71 - Serial Communication Interface 6
irq_handler_sercom6_2, // 72 - Serial Communication Interface 6
irq_handler_sercom6_3, // 73 - Serial Communication Interface 6
#else
0, // 70 - Reserved
0, // 71 - Reserved
0, // 72 - Reserved
0, // 73 - Reserved
#endif
#ifdef ID_SERCOM7
irq_handler_sercom7_0, // 74 - Serial Communication Interface 7
irq_handler_sercom7_1, // 75 - Serial Communication Interface 7
irq_handler_sercom7_2, // 76 - Serial Communication Interface 7
irq_handler_sercom7_3, // 77 - Serial Communication Interface 7
#else
0, // 74 - Reserved
0, // 75 - Reserved
0, // 76 - Reserved
0, // 77 - Reserved
#endif
#ifdef ID_CAN0
irq_handler_can0, // 78 - Control Area Network 0
#else
0, // 78 - Reserved
#endif
#ifdef ID_CAN1
irq_handler_can1, // 79 - Control Area Network 1
#else
0, // 79 - Reserved
#endif
irq_handler_usb_0, // 80 - USB_EORSM_DNRSM, USB_EORST_RST, USB_LPMSUSP_DDISC, USB_LPM_DCONN, USB_MSOF, USB_RAMACER, USB_RXSTP_TXSTP_0, USB_RXSTP_TXSTP_1, USB_RXSTP_TXSTP_2, USB_RXSTP_TXSTP_3, USB_RXSTP_TXSTP_4, USB_RXSTP_TXSTP_5, USB_RXSTP_TXSTP_6, USB_RXSTP_TXSTP_7, USB_STALL0_STALL_0, USB_STALL0_STALL_1, USB_STALL0_STALL_2, USB_STALL0_STALL_3, USB_STALL0_STALL_4, USB_STALL0_STALL_5, USB_STALL0_STALL_6, USB_STALL0_STALL_7, USB_STALL1_0, USB_STALL1_1, USB_STALL1_2, USB_STALL1_3, USB_STALL1_4, USB_STALL1_5, USB_STALL1_6, USB_STALL1_7, USB_SUSPEND, USB_TRFAIL0_TRFAIL_0, USB_TRFAIL0_TRFAIL_1, USB_TRFAIL0_TRFAIL_2, USB_TRFAIL0_TRFAIL_3, USB_TRFAIL0_TRFAIL_4, USB_TRFAIL0_TRFAIL_5, USB_TRFAIL0_TRFAIL_6, USB_TRFAIL0_TRFAIL_7, USB_TRFAIL1_PERR_0, USB_TRFAIL1_PERR_1, USB_TRFAIL1_PERR_2, USB_TRFAIL1_PERR_3, USB_TRFAIL1_PERR_4, USB_TRFAIL1_PERR_5, USB_TRFAIL1_PERR_6, USB_TRFAIL1_PERR_7, USB_UPRSM, USB_WAKEUP
irq_handler_usb_1, // 81 - USB_SOF_HSOF
irq_handler_usb_2, // 82 - USB_TRCPT0_0, USB_TRCPT0_1, USB_TRCPT0_2, USB_TRCPT0_3, USB_TRCPT0_4, USB_TRCPT0_5, USB_TRCPT0_6, USB_TRCPT0_7
irq_handler_usb_3, // 83 - 83 USB_TRCPT1_0, USB_TRCPT1_1, USB_TRCPT1_2, USB_TRCPT1_3, USB_TRCPT1_4, USB_TRCPT1_5, USB_TRCPT1_6, USB_TRCPT1_7
#ifdef ID_GMAC
irq_handler_gmac, // 84 - Ethernet MAC
#else
0, // 84 - Reserved
#endif
irq_handler_tcc0_0, // 85 - TCC0_CNT_A, TCC0_DFS_A, TCC0_ERR_A, TCC0_FAULT0_A, TCC0_FAULT1_A, TCC0_FAULTA_A, TCC0_FAULTB_A, TCC0_OVF, TCC0_TRG, TCC0_UFS_A
irq_handler_tcc0_1, // 86 - TCC0_MC_0
irq_handler_tcc0_2, // 87 - TCC0_MC_1
irq_handler_tcc0_3, // 88 - TCC0_MC_2
irq_handler_tcc0_4, // 89 - TCC0_MC_3
irq_handler_tcc0_5, // 90 - TCC0_MC_4
irq_handler_tcc0_1, // 91 - TCC0_MC_5
irq_handler_tcc1_0, // 92 - TCC1_CNT_A, TCC1_DFS_A, TCC1_ERR_A, TCC1_FAULT0_A, TCC1_FAULT1_A, TCC1_FAULTA_A, TCC1_FAULTB_A, TCC1_OVF, TCC1_TRG, TCC1_UFS_A
irq_handler_tcc1_1, // 93 - TCC1_MC_0
irq_handler_tcc1_2, // 94 - TCC1_MC_1
irq_handler_tcc1_3, // 95 - TCC1_MC_2
irq_handler_tcc1_4, // 96 - TCC1_MC_3
irq_handler_tcc2_0, // 97 - TCC2_CNT_A, TCC2_DFS_A, TCC2_ERR_A, TCC2_FAULT0_A, TCC2_FAULT1_A, TCC2_FAULTA_A, TCC2_FAULTB_A, TCC2_OVF, TCC2_TRG, TCC2_UFS_A
irq_handler_tcc2_1, // 98 - TCC2_MC_0
irq_handler_tcc2_2, // 99 - TCC2_MC_1
irq_handler_tcc2_3, // 100 - TCC2_MC_2
#ifdef ID_TCC3
irq_handler_tcc3_0, // 101 - TCC3_CNT_A, TCC3_DFS_A, TCC3_ERR_A, TCC3_FAULT0_A, TCC3_FAULT1_A, TCC3_FAULTA_A, TCC3_FAULTB_A, TCC3_OVF, TCC3_TRG, TCC3_UFS_A
irq_handler_tcc3_1, // 102 - TCC3_MC_0
irq_handler_tcc3_2, // 103 - TCC3_MC_1
#else
0, // 101 - Reserved
0, // 102 - Reserved
0, // 103 - Reserved
#endif
#ifdef ID_TCC4
irq_handler_tcc4_0, // 104 - TCC4_CNT_A, TCC4_DFS_A, TCC4_ERR_A, TCC4_FAULT0_A, TCC4_FAULT1_A, TCC4_FAULTA_A, TCC4_FAULTB_A, TCC4_OVF, TCC4_TRG, TCC4_UFS_A
irq_handler_tcc4_1, // 105 - TCC4_MC_0
irq_handler_tcc4_2, // 106 - TCC4_MC_1
#else
0, // 104 - Reserved
0, // 105 - Reserved
0, // 106 - Reserved
#endif
irq_handler_tc0, // 107 - Timer/Counter 0
irq_handler_tc1, // 108 - Timer/Counter 1
irq_handler_tc2, // 109 - Timer/Counter 2
irq_handler_tc3, // 100 - Timer/Counter 3
#ifdef ID_TC4
irq_handler_tc4, // 111 - Timer/Counter 4
#else
0, // 111 - Reserved
#endif
#ifdef ID_TC5
irq_handler_tc5, // 112 - Timer/Counter 5
#else
0, // 112 - Reserved
#endif
#ifdef ID_TC6
irq_handler_tc6, // 113 - Timer/Counter 6
#else
0, // 113 - Reserved
#endif
#ifdef ID_TC7
irq_handler_tc7, // 114 - Timer/Counter 7
#else
0, // 114 - Reserved
#endif
irq_handler_pdec_0, // 115 - PDEC_DIR_A, PDEC_ERR_A, PDEC_OVF, PDEC_VLC_A
irq_handler_pdec_1, // 116 - PDEC_MC_0
irq_handler_pdec_2, // 117 - PDEC_MC_1
irq_handler_adc0_0, // 118 - ADC0_OVERRUN, ADC0_WINMON
irq_handler_adc0_1, // 119 - ADC0_RESRDY
irq_handler_adc1_0, // 120 - ADC1_OVERRUN, ADC1_WINMON
irq_handler_adc1_1, // 121 - ADC1_RESRDY
irq_handler_ac, // 122 - Analog Comparator
irq_handler_dac_0, // 123 - DAC_OVERRUN_A_0, DAC_OVERRUN_A_1, DAC_UNDERRUN_A_0, DAC_UNDERRUN_A_1
irq_handler_dac_1, // 124 - DAC_EMPTY_0
irq_handler_dac_2, // 125 - DAC_EMPTY_1
irq_handler_dac_3, // 126 - DAC_RESRDY_0
irq_handler_dac_4, // 127 - DAC_RESRDY_1
irq_handler_i2s, // 128 - Inter-IC Sound Interface
irq_handler_pcc, // 129 - Parallel Capture Controller
irq_handler_aes, // 130 - Advanced Encryption Standard
irq_handler_trng, // 131 - True Random Number Generator
irq_handler_icm, // 132 - Integrity Check Monitor
irq_handler_pukcc, // 133 - Public-Key Cryptography Controller
irq_handler_qspi, // 134 - Quad SPI interface
irq_handler_sdhc0, // 135 - SD/MMC Host Controller 0
#ifdef ID_SDHC1
irq_handler_sdhc1, // 136 - SD/MMC Host Controller 1
#else
0, // 136 - Reserved
#endif
};
//-----------------------------------------------------------------------------
void irq_handler_reset(void)
{
main();
while (1);
}
//-----------------------------------------------------------------------------
void irq_handler_dummy(void)
{
while (1);
}
//-----------------------------------------------------------------------------
void _exit(int status)
{
(void)status;
while (1);
}

View File

@ -0,0 +1,62 @@
/*
* Copyright (c) 2024 Joey Castillo
*
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include "system.h"
#include "pins.h"
const tc_instance_details_t TC_Peripherals[] = {
};
const uint8_t Num_TC_Instances = 0;
const uint8_t TC_First_Index = 0;
const tcc_instance_details_t TCC_Peripherals[] = {
};
const uint8_t Num_TCC_Instances = 0;
const sercom_instance_details_t SERCOM_Peripherals[] = {
};
const uint8_t Num_SERCOM_Instances = 0;
//-----------------------------------------------------------------------------
void sys_init(void) {
}
void _enable_48mhz_gclk1(void) {
}
uint32_t get_cpu_frequency(void) {
return 8000000;
}
bool set_cpu_frequency(uint32_t freq) {
return false;
}
void _enter_standby_mode() {
}

View File

@ -0,0 +1,155 @@
/*
* Copyright (c) 2024 Joey Castillo
*
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
//-----------------------------------------------------------------------------
#define DUMMY __attribute__ ((weak, alias ("irq_handler_dummy")))
//-----------------------------------------------------------------------------
void irq_handler_reset(void);
void irq_handler_dummy(void);
void _exit(int status);
DUMMY void irq_handler_nmi(void);
DUMMY void irq_handler_hard_fault(void);
DUMMY void irq_handler_sv_call(void);
DUMMY void irq_handler_pend_sv(void);
DUMMY void irq_handler_sys_tick(void);
DUMMY void irq_handler_system(void);
DUMMY void irq_handler_wdt(void);
DUMMY void irq_handler_rtc(void);
DUMMY void irq_handler_eic(void);
DUMMY void irq_handler_nvmctrl(void);
DUMMY void irq_handler_dmac(void);
DUMMY void irq_handler_usb(void);
DUMMY void irq_handler_evsys(void);
DUMMY void irq_handler_sercom0(void);
DUMMY void irq_handler_sercom1(void);
DUMMY void irq_handler_sercom2(void);
DUMMY void irq_handler_sercom3(void);
DUMMY void irq_handler_sercom4(void);
DUMMY void irq_handler_sercom5(void);
DUMMY void irq_handler_tcc0(void);
DUMMY void irq_handler_tcc1(void);
DUMMY void irq_handler_tcc2(void);
DUMMY void irq_handler_tc0(void);
DUMMY void irq_handler_tc1(void);
DUMMY void irq_handler_tc2(void);
DUMMY void irq_handler_tc3(void);
DUMMY void irq_handler_tc4(void);
DUMMY void irq_handler_adc(void);
DUMMY void irq_handler_ac(void);
DUMMY void irq_handler_dac(void);
DUMMY void irq_handler_ptc(void);
DUMMY void irq_handler_aes(void);
DUMMY void irq_handler_trng(void);
extern int main(void);
void _stack_top(void) {};
extern unsigned int _etext;
extern unsigned int _data;
extern unsigned int _edata;
extern unsigned int _bss;
extern unsigned int _ebss;
//-----------------------------------------------------------------------------
__attribute__ ((used, section(".vectors")))
void (* const vectors[])(void) =
{
&_stack_top, // 0 - Initial Stack Pointer Value
// Cortex-M0+ handlers
irq_handler_reset, // 1 - Reset
irq_handler_nmi, // 2 - NMI
irq_handler_hard_fault, // 3 - Hard Fault
0, // 4 - Reserved
0, // 5 - Reserved
0, // 6 - Reserved
0, // 7 - Reserved
0, // 8 - Reserved
0, // 9 - Reserved
0, // 10 - Reserved
irq_handler_sv_call, // 11 - SVCall
0, // 12 - Reserved
0, // 13 - Reserved
irq_handler_pend_sv, // 14 - PendSV
irq_handler_sys_tick, // 15 - SysTick
// Peripheral handlers
irq_handler_system, // 0 - System Controller
irq_handler_wdt, // 1 - Watchdog Timer
irq_handler_rtc, // 2 - Real-Time Counter
irq_handler_eic, // 3 - External Interrupt Controller
irq_handler_nvmctrl, // 4 - Non-Volatile Memory Controller
irq_handler_dmac, // 5 - Direct Memory Access Controller
irq_handler_usb, // 6 - Universal Serial Bus Controller
irq_handler_evsys, // 7 - Event System
irq_handler_sercom0, // 8 - Serial Communication Interface 0
irq_handler_sercom1, // 9 - Serial Communication Interface 1
irq_handler_sercom2, // 10 - Serial Communication Interface 2
irq_handler_sercom3, // 11 - Serial Communication Interface 3
irq_handler_sercom4, // 12 - Serial Communication Interface 4
irq_handler_sercom5, // 13 - Serial Communication Interface 5
irq_handler_tcc0, // 14 - Timer/Counter for Control 0
irq_handler_tcc1, // 15 - Timer/Counter for Control 1
irq_handler_tcc2, // 16 - Timer/Counter for Control 2
irq_handler_tc0, // 17 - Timer/Counter 0
irq_handler_tc1, // 18 - Timer/Counter 1
irq_handler_tc2, // 19 - Timer/Counter 2
irq_handler_tc3, // 20 - Timer/Counter 3
irq_handler_tc4, // 21 - Timer/Counter 4
irq_handler_adc, // 22 - Analog-to-Digital Converter
irq_handler_ac, // 23 - Analog Comparator
irq_handler_dac, // 24 - Digital-to-Analog Converter
irq_handler_ptc, // 25 - Peripheral Touch Controller
irq_handler_aes, // 26 - Advanced Encryption Standard
irq_handler_trng, // 27 - True Random Number Generator
};
//-----------------------------------------------------------------------------
void irq_handler_reset(void)
{
main();
while (1);
}
//-----------------------------------------------------------------------------
void irq_handler_dummy(void)
{
while (1);
}
//-----------------------------------------------------------------------------
void _exit(int status)
{
(void)status;
while (1);
}

View File

@ -0,0 +1,62 @@
/*
* Copyright (c) 2024 Joey Castillo
*
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include "system.h"
#include "pins.h"
const tc_instance_details_t TC_Peripherals[] = {
};
const uint8_t Num_TC_Instances = 0;
const uint8_t TC_First_Index = 0;
const tcc_instance_details_t TCC_Peripherals[] = {
};
const uint8_t Num_TCC_Instances = 0;
const sercom_instance_details_t SERCOM_Peripherals[] = {
};
const uint8_t Num_SERCOM_Instances = 0;
//-----------------------------------------------------------------------------
void sys_init(void) {
}
void _enable_48mhz_gclk1(void) {
}
uint32_t get_cpu_frequency(void) {
return 8000000;
}
bool set_cpu_frequency(uint32_t freq) {
return false;
}
void _enter_standby_mode() {
}

View File

@ -0,0 +1,151 @@
/*
* Copyright (c) 2024 Joey Castillo
*
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
//-----------------------------------------------------------------------------
#define DUMMY __attribute__ ((weak, alias ("irq_handler_dummy")))
//-----------------------------------------------------------------------------
void irq_handler_reset(void);
void irq_handler_dummy(void);
void _exit(int status);
DUMMY void irq_handler_nmi(void);
DUMMY void irq_handler_hard_fault(void);
DUMMY void irq_handler_sv_call(void);
DUMMY void irq_handler_pend_sv(void);
DUMMY void irq_handler_sys_tick(void);
DUMMY void irq_handler_system(void);
DUMMY void irq_handler_wdt(void);
DUMMY void irq_handler_rtc(void);
DUMMY void irq_handler_eic(void);
DUMMY void irq_handler_freqm(void);
DUMMY void irq_handler_usb(void);
DUMMY void irq_handler_nvmctrl(void);
DUMMY void irq_handler_dmac(void);
DUMMY void irq_handler_evsys(void);
DUMMY void irq_handler_sercom0(void);
DUMMY void irq_handler_sercom1(void);
DUMMY void irq_handler_sercom2(void);
DUMMY void irq_handler_sercom3(void);
DUMMY void irq_handler_sercom4(void);
DUMMY void irq_handler_sercom5(void);
DUMMY void irq_handler_tcc0(void);
DUMMY void irq_handler_tc0(void);
DUMMY void irq_handler_tc1(void);
DUMMY void irq_handler_tc2(void);
DUMMY void irq_handler_tc3(void);
DUMMY void irq_handler_adc(void);
DUMMY void irq_handler_ac(void);
DUMMY void irq_handler_ptc(void);
DUMMY void irq_handler_slcd(void);
DUMMY void irq_handler_aes(void);
DUMMY void irq_handler_trng(void);
extern int main(void);
void _stack_top(void) {};
extern unsigned int _etext;
extern unsigned int _data;
extern unsigned int _edata;
extern unsigned int _bss;
extern unsigned int _ebss;
//-----------------------------------------------------------------------------
__attribute__ ((used, section(".vectors")))
void (* const vectors[])(void) =
{
&_stack_top, // 0 - Initial Stack Pointer Value
// Cortex-M0+ handlers
irq_handler_reset, // 1 - Reset
irq_handler_nmi, // 2 - NMI
irq_handler_hard_fault, // 3 - Hard Fault
0, // 4 - Reserved
0, // 5 - Reserved
0, // 6 - Reserved
0, // 7 - Reserved
0, // 8 - Reserved
0, // 9 - Reserved
0, // 10 - Reserved
irq_handler_sv_call, // 11 - SVCall
0, // 12 - Reserved
0, // 13 - Reserved
irq_handler_pend_sv, // 14 - PendSV
irq_handler_sys_tick, // 15 - SysTick
// Peripheral handlers
irq_handler_system, // 0 - System Controller
irq_handler_wdt, // 1 - Watchdog Timer
irq_handler_rtc, // 2 - Real-Time Counter
irq_handler_eic, // 3 - External Interrupt Controller
irq_handler_freqm, // 4 - External Interrupt Controller
irq_handler_usb, // 5 - Universal Serial Bus Controller
irq_handler_nvmctrl, // 6 - Non-Volatile Memory Controller
irq_handler_dmac, // 7 - Direct Memory Access Controller
irq_handler_evsys, // 8 - Event System
irq_handler_sercom0, // 9 - Serial Communication Interface 0
irq_handler_sercom1, // 10 - Serial Communication Interface 1
irq_handler_sercom2, // 11 - Serial Communication Interface 2
irq_handler_sercom3, // 12 - Serial Communication Interface 3
irq_handler_sercom4, // 13 - Serial Communication Interface 4
irq_handler_sercom5, // 14 - Serial Communication Interface 5
irq_handler_tcc0, // 15 - Timer/Counter for Control 0
irq_handler_tc0, // 16 - Timer/Counter 0
irq_handler_tc1, // 17 - Timer/Counter 1
irq_handler_tc2, // 18 - Timer/Counter 2
irq_handler_tc3, // 19 - Timer/Counter 3
irq_handler_adc, // 20 - Analog-to-Digital Converter
irq_handler_ac, // 21 - Analog Comparator
irq_handler_ptc, // 22 - Peripheral Touch Controller
irq_handler_slcd, // 23 - Segment Liquid Crystal Display Controller
irq_handler_aes, // 24 - Advanced Encryption Standard
irq_handler_trng, // 25 - True Random Number Generator
};
//-----------------------------------------------------------------------------
void irq_handler_reset(void)
{
main();
while (1);
}
//-----------------------------------------------------------------------------
void irq_handler_dummy(void)
{
while (1);
}
//-----------------------------------------------------------------------------
void _exit(int status)
{
(void)status;
while (1);
}

View File

@ -0,0 +1,62 @@
/*
* Copyright (c) 2024 Joey Castillo
*
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include "system.h"
#include "pins.h"
const tc_instance_details_t TC_Peripherals[] = {
};
const uint8_t Num_TC_Instances = 0;
const uint8_t TC_First_Index = 0;
const tcc_instance_details_t TCC_Peripherals[] = {
};
const uint8_t Num_TCC_Instances = 0;
const sercom_instance_details_t SERCOM_Peripherals[] = {
};
const uint8_t Num_SERCOM_Instances = 0;
//-----------------------------------------------------------------------------
void sys_init(void) {
}
void _enable_48mhz_gclk1(void) {
}
uint32_t get_cpu_frequency(void) {
return 8000000;
}
bool set_cpu_frequency(uint32_t freq) {
return false;
}
void _enter_standby_mode() {
}

88
dummy/common/app.h Normal file
View File

@ -0,0 +1,88 @@
/**
* @file app.h
* @brief Gossamer application framework
*/
/*
* MIT License
*
* Copyright (c) 2020 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
#include <stddef.h>
#include "pins.h"
/** @brief A function you will implement to initialize your application's low-
* level setup. The app_init function is called after system clocks are
* initialized, and before anything else.
* @details You may be wondering why there is an `app_init` function as well as
* an `app_setup` function. The main difference is that app_init is
* only meant to be callec once, at boot, whereas you might want to
* call app_setup multiple times, for example if you want to disable
* some peripherals before entering STANDBY mode, and re-enable them
* after waking up. In essence, you should set up anything that will
* run forever in app_init, whereas anything that could get turned off
* in the course of execution should be set up in app_setup.
* @note If your application plans to use the real-time clock perhiperal, you
* probably want to call the `rtc_init` function here.
*/
void app_init(void);
/** @brief OPTIONAL: A function you may implement to restore state after waking
* up from BACKUP mode on the SAM L21 or L22. This function is called
* after system_init, but before app_setup. You can stash a bit of your
* application state in the RTC's BKUP and GPn registers, and use this
* function as an opportinity to restore it before app_setup is called.
* @note You do not need to implement this function unless you are using the
* SAM L21 or L22 and you want to restore state from BACKUP mode.
*/
void app_wake_from_backup(void);
/** @brief A function you will implement to set up your app. The app_setup
* function is like setup() in Arduino. It is called once when the
* program begins, after app_init and app_wake_from_backup, if it
* exists. You should use this function to set up your application
* state and configure any peripherals you need to use.
*/
void app_setup(void);
/** @brief A function you will implement to serve as the app's main run loop.
* This method will be called repeatedly, or if you enter STANDBY mode,
* as soon as the device wakes from that mode.
* @note In order to wake from STANDBY mode, you must set up an interrupt or
* wake source. Otherwise your app will remain in STANDBY indefinitely.
* @return true if your app is prepared to enter STANDBY mode. If you return
* false, your app's app_loop method will be called again immediately.
*/
bool app_loop(void);
/** @brief OPTIONAL: A function to yield control of the CPU to other tasks.
* This function is called in the delay function to allow other tasks
* to run while the CPU is busy waiting. By default, this function does
* nothing, but if you are using the USB peripheral, you should
* implement this function and call `tud_task` at minumum, along with
* any other USB-related tasks you need to run.
*/
void yield(void);

89
dummy/common/delay.c Normal file
View File

@ -0,0 +1,89 @@
#include "delay.h"
#include <emscripten.h>
#include <emscripten/html5.h>
#include "system.h"
#include "app.h"
#define ANIMATION_FRAME_ID_IS_VALID(id) ((id) >= 0)
#define ANIMATION_FRAME_ID_INVALID (-1)
#define ANIMATION_FRAME_ID_SUSPENDED (-2)
static bool sleeping = true;
static volatile long animation_frame_id = ANIMATION_FRAME_ID_INVALID;
// make compiler happy
bool main_loop_is_sleeping(void);
static void main_loop_set_sleeping(bool sleeping);
static EM_BOOL main_loop(double time, void *userData);
static inline void request_next_frame(void) {
if (animation_frame_id == ANIMATION_FRAME_ID_INVALID) {
animation_frame_id = emscripten_request_animation_frame(main_loop, NULL);
}
}
static EM_BOOL main_loop(double time, void *userData) {
if (main_loop_is_sleeping()) {
request_next_frame();
return EM_FALSE;
}
if (sleeping) {
sleeping = false;
}
animation_frame_id = ANIMATION_FRAME_ID_INVALID;
bool can_sleep = app_loop();
if (can_sleep) {
sleeping = true;
animation_frame_id = ANIMATION_FRAME_ID_INVALID;
return EM_FALSE;
}
request_next_frame();
return EM_FALSE;
}
void resume_main_loop(void) {
if (!ANIMATION_FRAME_ID_IS_VALID(animation_frame_id)) {
animation_frame_id = emscripten_request_animation_frame(main_loop, NULL);
}
}
void suspend_main_loop(void) {
if (ANIMATION_FRAME_ID_IS_VALID(animation_frame_id)) {
emscripten_cancel_animation_frame(animation_frame_id);
}
animation_frame_id = ANIMATION_FRAME_ID_SUSPENDED;
}
void main_loop_sleep(uint32_t ms) {
main_loop_set_sleeping(true);
emscripten_sleep(ms);
main_loop_set_sleeping(false);
animation_frame_id = ANIMATION_FRAME_ID_INVALID;
}
bool main_loop_is_sleeping(void) {
return EM_ASM_INT({ return Module['suspended']; }) != 0;
}
static void main_loop_set_sleeping(bool sleeping) {
EM_ASM({
Module['suspended'] = $0;
}, sleeping);
}
void delay_init(void) {
}
void delay_ms(const uint16_t ms) {
main_loop_sleep(ms);
}
void delay_us(const uint16_t us) {
main_loop_sleep(us / 1000);
}

27
dummy/common/delay.h Normal file
View File

@ -0,0 +1,27 @@
/**
* @file delay.h
* @brief Delay routines
*/
#include <stdint.h>
#include <stdbool.h>
#include <stddef.h>
#pragma once
/**
* @brief Initializes the system tick peripheral. This is required to use the delay functions.
* @details The system tick only runs while the CPU is running, and does not fire in STANDBY mode.
*/
void delay_init(void);
/**
* @brief Delays for the given number of milliseconds.
* @param ms The number of milliseconds to delay.
*/
void delay_ms(const uint16_t ms);
/**
* @brief Delays for the given number of microseconds.
* @param us The number of microseconds to delay.
*/
void delay_us(const uint16_t us);

142
dummy/common/hal_gpio.h Normal file
View File

@ -0,0 +1,142 @@
/**
* @file hal_gpio.h
* @brief GPIO Macros
*/
/*
* Copyright (c) 2014-2016, Alex Taradov <alex@taradov.com>
* All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are met:
*
* 1. Redistributions of source code must retain the above copyright notice,
* this list of conditions and the following disclaimer.
* 2. Redistributions in binary form must reproduce the above copyright
* notice, this list of conditions and the following disclaimer in the
* documentation and/or other materials provided with the distribution.
* 3. The name of the author may not be used to endorse or promote products
* derived from this software without specific prior written permission.
*
* THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS"
* AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
* IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
* ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE
* LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR
* CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF
* SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS
* INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN
* CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE)
* ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE
* POSSIBILITY OF SUCH DAMAGE.
*/
#include <stdint.h>
#pragma once
/*- Definitions -------------------------------------------------------------*/
#define HAL_GPIO_PORTA 0
#define HAL_GPIO_PORTB 1
#define HAL_GPIO_PORTC 2
#define HAL_GPIO_PMUX_A 0
#define HAL_GPIO_PMUX_B 1
#define HAL_GPIO_PMUX_C 2
#define HAL_GPIO_PMUX_D 3
#define HAL_GPIO_PMUX_E 4
#define HAL_GPIO_PMUX_F 5
#define HAL_GPIO_PMUX_G 6
#define HAL_GPIO_PMUX_H 7
#define HAL_GPIO_PMUX_I 8
#define HAL_GPIO_PMUX_J 9
#define HAL_GPIO_PMUX_K 10
#define HAL_GPIO_PMUX_L 11
#define HAL_GPIO_PMUX_M 12
#define HAL_GPIO_PMUX_N 13
#define HAL_GPIO_PIN(name, port, pin) \
static inline void HAL_GPIO_##name##_set(void) \
{ \
(void)HAL_GPIO_##name##_set; \
} \
\
static inline void HAL_GPIO_##name##_clr(void) \
{ \
(void)HAL_GPIO_##name##_clr; \
} \
\
static inline void HAL_GPIO_##name##_toggle(void) \
{ \
(void)HAL_GPIO_##name##_toggle; \
} \
\
static inline void HAL_GPIO_##name##_write(int value) \
{ \
(void)HAL_GPIO_##name##_write; \
} \
\
static inline void HAL_GPIO_##name##_drvstr(int value) \
{ \
(void)HAL_GPIO_##name##_write; \
} \
\
static inline void HAL_GPIO_##name##_in(void) \
{ \
(void)HAL_GPIO_##name##_in; \
} \
\
static inline void HAL_GPIO_##name##_out(void) \
{ \
(void)HAL_GPIO_##name##_out; \
} \
\
static inline void HAL_GPIO_##name##_off(void) \
{ \
(void)HAL_GPIO_##name##_off; \
} \
\
static inline void HAL_GPIO_##name##_pullup(void) \
{ \
(void)HAL_GPIO_##name##_pullup; \
} \
\
static inline void HAL_GPIO_##name##_pulldown(void) \
{ \
(void)HAL_GPIO_##name##_pulldown; \
} \
\
static inline int HAL_GPIO_##name##_read(void) \
{ \
return 0; \
(void)HAL_GPIO_##name##_read; \
} \
\
static inline int HAL_GPIO_##name##_state(void) \
{ \
return 0; \
(void)HAL_GPIO_##name##_state; \
} \
\
static inline void HAL_GPIO_##name##_pmuxen(int mux) \
{ \
(void)HAL_GPIO_##name##_pmuxen; \
} \
\
static inline void HAL_GPIO_##name##_pmuxdis(void) \
{ \
(void)HAL_GPIO_##name##_pmuxdis; \
} \
\
static inline uint8_t HAL_GPIO_##name##_pin(void) \
{ \
return 0; \
(void)HAL_GPIO_##name##_pin; \
} \
\
HAL_GPIO_PIN(SWCLK, A, 30)
HAL_GPIO_PIN(SWDIO, A, 31)
#ifdef APP_USES_TINYUSB
HAL_GPIO_PIN(USB_N, A, 24)
HAL_GPIO_PIN(USB_P, A, 25)
#endif

3
dummy/common/sam.h Normal file
View File

@ -0,0 +1,3 @@
#pragma once
typedef int generic_clock_generator_t;

109
dummy/common/system.h Normal file
View File

@ -0,0 +1,109 @@
/**
* @file system.h
* @brief Gossamer system routines
*/
/*
* MIT License
*
* Copyright (c) 2020 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include <stdint.h>
#include <stdbool.h>
#include <stddef.h>
#pragma once
typedef int tc_instance_details_t;
typedef int tcc_instance_details_t;
typedef int sercom_instance_details_t;
extern const tc_instance_details_t TC_Peripherals[];
extern const uint8_t Num_TC_Instances;
extern const uint8_t TC_First_Index;
extern const tcc_instance_details_t TCC_Peripherals[];
extern const uint8_t Num_TCC_Instances;
extern const sercom_instance_details_t SERCOM_Peripherals[];
extern const uint8_t Num_SERCOM_Instances;
////< @file system.h
/// @{
/** @brief Initializes the system clocks and performs any required system-wide setup.
* @details Gossamer aims for consistency at system startup, no matter which
* chip you are working with. To that end:
* * GCLK0, the main system clock, is set to 8 MHz.
* * GCLK2 is the low-power 32768 Hz clock, OSCULP32K
* * GCLK3 is a 1024 Hz clock, derived from the most accurate source available.
* GCLK0 is set to ONDEMAND with RUNSTDBY off, so the main clock remains
* off when in standby mode. GCLK2 and GCLK3 are also ONDEMAND, but RUNSTDBY
* is on. This ensures that if a peripheral requests it, the clock will remain
* on in standby, but if no peripheral requests it, it will not run at all.
* Also note that while GCLK1 is not turned on at startup, it may be reserved for
* internal use depending on your use case. If you intend to use USB, the
* `usb_init` function will claim GCLK1 for the 48 MHz DFLL clock.
*/
void sys_init(void);
/** @brief Gets the CPU frequency.
* @return 8000000 by default, or another value if set by `set_cpu_frequency`
*/
uint32_t get_cpu_frequency(void);
/** @brief Sets the CPU frequency.
* @param freq one of 1000000, 2000000, 4000000, 8000000, 12000000 or 16000000.
* @details Supported CPU frequencies vary from chip to chip:
* * On the SAM D11 and D21, you can choose 8, 4, 2 or 1 MHz.
* * On the SAM L21 and L22, you can choose 16, 12, 8 or 4 MHz.
* While you can run these chips at higher frequencies using the DFLL,
* Gossamer aims for simplicity: this means that it only supports the
* internal oscillator at one of its standard frequencies.
* @note Some peripherals like SERCOMs and TC/TCCs read the CPU frequency when
* they are configured, to set critical timing-related parameters like baud
* rate or period. If you change the CPU frequency after setting up these
* peripherals and then attempt to use them, they will very likely behave in
* unexpected ways. Thus you should disable any peripherals that depend on
* GCLK0 before calling set_cpu_frequency, and then re-enable them after.
*/
bool set_cpu_frequency(uint32_t freq);
/** @brief Enables the 48 MHz clock on GCLK1 for USB operation.
* @details This function is called by the USB stack when it is initialized.
* @warning At this time, the 48 MHz clock is hard-coded to use USB Clock
* Recovery Mode, and as such will only be available if your device
* is plugged into a USB host. It is possible to derive the 48 MHz
* DFLL from an external 32kHz crystal, but this is not currently
* implemented in Gossamer.
*/
void _enable_48mhz_gclk1(void);
/** @brief Enters the low-power STANDBY mode. Does not return until an interrupt fires.
* @details You should not generally need to call this function; at the end of every
* app_loop invocation, the main run loop enters standby mode if your app
* indicated that it was appropriate.
*/
void _enter_standby_mode(void);
/// @}

122
dummy/common/tusb_config.h Normal file
View File

@ -0,0 +1,122 @@
/*
* The MIT License (MIT)
*
* Copyright (c) 2019 Ha Thach (tinyusb.org)
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*
*/
#ifndef _TUSB_CONFIG_H_
#define _TUSB_CONFIG_H_
#ifdef __cplusplus
extern "C" {
#endif
#if defined(_SAMD21_)
#define CFG_TUSB_MCU OPT_MCU_SAMD21
#elif defined(_SAMD11_)
#define CFG_TUSB_MCU OPT_MCU_SAMD11
#elif defined(_SAML21_)
#define CFG_TUSB_MCU OPT_MCU_SAML21
#elif defined(_SAML22_)
#define CFG_TUSB_MCU OPT_MCU_SAML22
#endif
#define BOARD_DEVICE_RHPORT_NUM 0
#define BOARD_DEVICE_RHPORT_SPEED OPT_MODE_
#define CFG_TUSB_RHPORT0_MODE (OPT_MODE_DEVICE | OPT_MODE_DEFAULT_SPEED)
#define CFG_TUSB_OS OPT_OS_NONE
#ifndef CFG_TUSB_DEBUG
#define CFG_TUSB_DEBUG 0
#endif
// Enable Device stack
#define CFG_TUD_ENABLED 1
// Default is max speed that hardware controller could support with on-chip PHY
#define CFG_TUD_MAX_SPEED OPT_MODE_FULL_SPEED
/* USB DMA on some MCUs can only access a specific SRAM region with restriction on alignment.
* Tinyusb use follows macros to declare transferring memory so that they can be put
* into those specific section.
* e.g
* - CFG_TUSB_MEM SECTION : __attribute__ (( section(".usb_ram") ))
* - CFG_TUSB_MEM_ALIGN : __attribute__ ((aligned(4)))
*/
#ifndef CFG_TUSB_MEM_SECTION
#define CFG_TUSB_MEM_SECTION
#endif
#ifndef CFG_TUSB_MEM_ALIGN
#define CFG_TUSB_MEM_ALIGN __attribute__ ((aligned(4)))
#endif
//--------------------------------------------------------------------
// DEVICE CONFIGURATION
//--------------------------------------------------------------------
#ifndef CFG_TUD_ENDPOINT0_SIZE
#define CFG_TUD_ENDPOINT0_SIZE 64
#endif
//------------- CLASS -------------//
#ifndef CFG_TUD_CDC
#define CFG_TUD_CDC 0
#endif
#ifndef CFG_TUD_MSC
#define CFG_TUD_MSC 0
#endif
#ifndef CFG_TUD_HID
#define CFG_TUD_HID 0
#endif
#ifndef CFG_TUD_MIDI
#define CFG_TUD_MIDI 0
#endif
#ifndef CFG_TUD_VENDOR
#define CFG_TUD_VENDOR 0
#endif
// CDC FIFO size of TX and RX
#define CFG_TUD_CDC_RX_BUFSIZE (64)
#define CFG_TUD_CDC_TX_BUFSIZE (64)
// CDC Endpoint transfer buffer size, more is faster
#define CFG_TUD_CDC_EP_BUFSIZE (64)
// MIDI FIFO size of TX and RX
#define CFG_TUD_MIDI_RX_BUFSIZE (64)
#define CFG_TUD_MIDI_TX_BUFSIZE (64)
// MSC Buffer size of Device Mass storage
#define CFG_TUD_MSC_EP_BUFSIZE (512)
#ifdef __cplusplus
}
#endif
#endif /* _TUSB_CONFIG_H_ */

50
dummy/peripherals/adc.c Normal file
View File

@ -0,0 +1,50 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include "pins.h"
#include "system.h"
#include "adc.h"
static void _adc_sync(void) {
}
void adc_set_sampling_length(uint8_t length) {
}
uint16_t adc_get_analog_value_for_channel(uint8_t channel) {
return 32767;
}
uint16_t adc_get_analog_value(uint8_t pin) {
return 32767;
}
void adc_init(void) {
}
void adc_enable(void) {
}
void adc_disable(void) {
}

88
dummy/peripherals/adc.h Normal file
View File

@ -0,0 +1,88 @@
/**
* @file adc.h
* @brief Analog to Digital Converter
*/
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
/**
* @brief Initializes the ADC peripheral, but does not enable it.
* @details This function sets up some sensible defaults for basic use cases:
* * Clocks the ADC with the main oscillator divided down to a
* 500 kHz ADC clock.
* * Sets sampling length to one clock cycle, which is appropriate
* for inputs with impedance up to 28 kOhm.
* * Sets oversampling of 16 samples, resulting in a conversion time
* of 32 microseconds.
* * Sets the ADC up for single-ended measurement (you are measuring
* the voltage between the analog input pin and ground, not between
* two analog input pins)
* * On SAM L21 and L22, sets the reference voltage to VDDANA, which
* allows use of the full 0-3.3V range.
* * On SAM D11 and D21, sets the reference voltage to VDDANA / 2 and
* the gain to 1/2, which also allows use of the full 0-3.3V range.
*/
void adc_init(void);
/**
* @brief Enables the ADC peripheral
*/
void adc_enable(void);
/**
* @brief Sets the sampling length for the ADC.
* @details The sampling length sets the number of ADC clock cycles for which the
* ADC will sample the input, less 1 (so 0 represents 1 clock cycle).
* The default is 0, which is a good choice for inputs with impedance
* up to 28 kOhm. Each additional clock cycle of sampling time adds
* about 32 kOhm to the maximum input impedance.
* @see https://blog.thea.codes/getting-the-most-out-of-the-samd21-adc/
*/
void adc_set_sampling_length(uint8_t length);
/**
* @brief Gets the analog value on the given ADC pin.
* @param pin The ADC pin you wish to read (i.e. `HAL_GPIO_A0_pin()`)
* @return The analog value of the given ADC pin, from 0-65535 by default.
* If the pin is not an ADC pin, returns 0.
*/
uint16_t adc_get_analog_value(uint8_t pin);
/**
* @brief Gets the analog value on the given ADC channel.
* @param channel The ADC channel you wish to read (this will come from the datasheet)
* @return The analog value of the given ADC channel, from 0-65535 by default.
*/
uint16_t adc_get_analog_value_for_channel(uint8_t channel);
/**
* @brief Disables the ADC peripheral
*/
void adc_disable(void);

43
dummy/peripherals/dac.c Normal file
View File

@ -0,0 +1,43 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include "pins.h"
#include "system.h"
#include "dac.h"
#ifdef DAC
static void _dac_sync() {
}
void dac_init(void) {
}
void dac_enable(dac_channel_mask_t channelmask) {
}
void dac_disable(uint16_t channel) {
}
#endif

71
dummy/peripherals/dac.h Normal file
View File

@ -0,0 +1,71 @@
/**
* @file dac.h
* @brief Digital to Analog Converter
*/
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
// channel mask enum for dac_enable
typedef enum {
DAC_CHANNEL_NONE = 0,
DAC_CHANNEL_0 = 1,
DAC_CHANNEL_1 = 2,
DAC_CHANNEL_BOTH = 3
} dac_channel_mask_t;
/**
* @brief Initializes the DAC peripheral, but does not enable it.
* @param channel The DAC channel to enable.
* @warning Currently only supports the DAC on VOUT[0]
*/
void dac_init(void);
/**
* @brief Enables the DAC channels specified in the mask, and disables others.
* @param channelmask A bitmask of the channels to enable:
* 1 for channel 0, 2 for channel 1, 3 for both channels.
* For MCUs with only one DAC channel, this parameter is ignored.
*/
void dac_enable(dac_channel_mask_t channelmask);
/**
* @brief Set the analog value of the DAC.
* @param channel The DAC channel to set.
* @param value The value to set the DAC to. The range is platform-dependent:
* * On SAM L21, the valid range is from 0 to 4095.
* * On SAM D21 and D11, the valid range is from 0 to 1023.
* In both cases, 0 is 0V and the maximum value is VDDANA.
*/
void dac_set_analog_value(uint16_t channel, uint16_t value);
/**
* @brief Disables the given DAC channel.
* @warning Currently only supports the DAC on VOUT[0]
*/
void dac_disable(uint16_t channel);

54
dummy/peripherals/dma.c Normal file
View File

@ -0,0 +1,54 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
* Based heavily on Adafruit_ZeroDMA
* Written by Phil "PaintYourDragon" Burgess for Adafruit Industries,
* based partly on DMA insights from Atmel ASFCORE 3.
*
* Adafruit invests time and resources providing this open source code,
* please support Adafruit and open-source hardware by purchasing
* products from Adafruit!
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include <string.h>
#include <malloc.h>
#include "pins.h"
#include "system.h"
#include "dma.h"
void dma_init(void) {
}
bool dma_configure(gossamer_dma_job_t *dmaJob, uint8_t peripheralTrigger, dma_trigger_action_t triggerAction, dma_configuration_flags_t flags) {
return false;
}
DmacDescriptor *dma_add_descriptor(gossamer_dma_job_t *dmaJob, void *src, void *dst, uint32_t count, dma_beat_size_t size, dma_address_increment_t addressIncrement, dma_stepsize_t stepSize, dma_stepsel_t stepSel) {
return 0;
}
bool dma_start_job(gossamer_dma_job_t *dmaJob) {
return false;
}
void DMAC_Handler(void) {
}

108
dummy/peripherals/dma.h Normal file
View File

@ -0,0 +1,108 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
* Based heavily on Adafruit_ZeroDMA
* Written by Phil "PaintYourDragon" Burgess for Adafruit Industries,
* based partly on DMA insights from Atmel ASFCORE 3.
*
* Adafruit invests time and resources providing this open source code,
* please support Adafruit and open-source hardware by purchasing
* products from Adafruit!
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
#include "dma_util.h"
#ifndef _SAMD51_
typedef struct {
uint8_t channel; // (0 to DMAC_CH_NUM-1, or 0xFF)
volatile dma_status_t jobStatus; // Last known DMA job status
bool hasDescriptors; // 'true' if one or more descriptors assigned
bool loopFlag; // 'true' if descriptor chain loops back to start
void (*callbacks[DMA_CALLBACK_N])(void *); // Callback function (is passed an instance of this struct)
} gossamer_dma_job_t;
typedef int DmacDescriptor;
/**
* @brief Initialize the DMA system.
* @details Sets up peripheral clocks and points the DMA controller at an empty
* list of descriptors.
*
*/
void dma_init(void);
/**
* @brief Configures a DMA job.
* @details Configures a DMA job with the given peripheral trigger and trigger action.
* You must configure the job before adding descriptors to it.
* @param dmaJob A pointer to the DMA job to configure. This will be modified in place.
* @param peripheralTrigger The peripheral trigger to use for this job. These are
* defined in your microcontroller's data sheet, in the DMAC's
* register details section, under a headling like "Trigger Source"
* @param triggerAction The trigger action to use for this job. One of:
* * DMA_TRIGGER_ACTION_BLOCK
* * DMA_TRIGGER_ACTION_BEAT
* * DMA_TRIGGER_ACTION_TRANSACTION
* @param flags A OR'ed bitmask of flags to use for this job. Available flags are:
* * DMA_CONFIG_LOOP - Loop the job when it completes
* * DMA_CONFIG_RUNSTDBY - Keep the job running in standby mode
*/
bool dma_configure(gossamer_dma_job_t *dmaJob, uint8_t peripheralTrigger, dma_trigger_action_t triggerAction, dma_configuration_flags_t flags);
/**
* @brief Adds a descriptor to a DMA job.
* @details Adds a descriptor to a DMA job. You must configure the job before adding
* descriptors to it.
* @param dmaJob A pointer to the DMA job. Must be previously configured with dma_configure().
* @param src The source address for this descriptor.
* @param dst The destination address for this descriptor.
* @param count The number of beats to transfer.
* @param size The beat size. One of:
* * DMA_BEAT_SIZE_BYTE - One byte per beat
* * DMA_BEAT_SIZE_HWORD - One half word (two bytes) per beat
* * DMA_BEAT_SIZE_WORD - One word (four bytes) per beat
* @param srcInc Whether to increment the source address after each beat.
* @param dstInc Whether to increment the destination address after each beat.
* @param stepSize Address increment step size. One of:
* * DMA_STEPSIZE_1 - Increment by 1 * beat size
* * DMA_STEPSIZE_2 - Increment by 2 * beat size
* * DMA_STEPSIZE_4 - Increment by 4 * beat size
* * DMA_STEPSIZE_8 - ...you get the idea
* * DMA_STEPSIZE_16
* * DMA_STEPSIZE_32
* * DMA_STEPSIZE_64
* * DMA_STEPSIZE_128
* @param stepSel Which address to increment by stepSize after each step. You can only have one:
* * DMA_STEPSEL_SOURCE - Increment the source address after each step
* * DMA_STEPSEL_DESTINATION - Increment the destination address after each step
*
*/
DmacDescriptor *dma_add_descriptor(gossamer_dma_job_t *dmaJob, void *src, void *dst, uint32_t count, dma_beat_size_t size, dma_address_increment_t addressIncrement, dma_stepsize_t stepSize, dma_stepsel_t stepSel);
bool dma_start_job(gossamer_dma_job_t *dmaJob);
#endif

View File

@ -0,0 +1,109 @@
#ifndef DMA_UTIL_H_INCLUDED
#define DMA_UTIL_H_INCLUDED
/// TODO: DMA on SAMD51
#ifndef _SAMD51_
typedef enum {
DMA_CONFIG_LOOP = 1 << 0,
DMA_CONFIG_RUNSTDBY = 1 << 1,
} dma_configuration_flags_t;
typedef enum {
DMA_INCREMENT_NONE = 0,
DMA_INCREMENT_SOURCE = (1 << 0),
DMA_INCREMENT_DESTINATION = (1 << 1),
DMA_INCREMENT_BOTH = (1 << 1) | (1 << 0),
} dma_address_increment_t;
typedef enum {
DMA_TRIGGER_ACTION_BLOCK = 0,
DMA_TRIGGER_ACTION_BEAT = 1,
DMA_TRIGGER_ACTION_TRANSACTION = 2,
} dma_trigger_action_t;
typedef enum {
// First item here is for any transfer errors. A transfer error is
// flagged if a bus error is detected during an AHB access or when
// the DMAC fetches an invalid descriptor
DMA_CALLBACK_TRANSFER_ERROR,
DMA_CALLBACK_TRANSFER_DONE,
DMA_CALLBACK_CHANNEL_SUSPEND,
DMA_CALLBACK_N, // Number of available callbacks
} dma_callback_type_t;
typedef enum {
DMA_BEAT_SIZE_BYTE = 0, // 8-bit
DMA_BEAT_SIZE_HWORD, // 16-bit
DMA_BEAT_SIZE_WORD, // 32-bit
} dma_beat_size_t;
typedef enum {
DMA_EVENT_OUTPUT_DISABLE = 0, // Disable event generation
DMA_EVENT_OUTPUT_BLOCK, // Event strobe when block xfer complete
DMA_EVENT_OUTPUT_RESERVED,
DMA_EVENT_OUTPUT_BEAT, // Event strobe when beat xfer complete
} dma_event_output_selection_t;
typedef enum {
DMA_BLOCK_ACTION_NONE = 0,
// Channel in normal operation and sets transfer complete interrupt
// flag after block transfer
DMA_BLOCK_ACTION_INTERRUPT,
// Trigger channel suspend after block transfer and sets channel
// suspend interrupt flag once the channel is suspended
DMA_BLOCK_ACTION_SUSPEND,
// Sets transfer complete interrupt flag after a block transfer and
// trigger channel suspend. The channel suspend interrupt flag will
// be set once the channel is suspended.
DMA_BLOCK_ACTION_INTERRUPT_AND_SUSPEND,
} dma_block_action_t;
// DMA step selection. This bit determines whether the step size setting
// is applied to source or destination address.
typedef enum {
DMA_STEPSEL_DESTINATION = 0,
DMA_STEPSEL_SOURCE,
} dma_stepsel_t;
// Address increment step size. These bits select the address increment step
// size. The setting apply to source or destination address, depending on
// STEPSEL setting.
typedef enum {
DMA_STEPSIZE_1 = 0, // beat size * 1
DMA_STEPSIZE_2, // beat size * 2
DMA_STEPSIZE_4, // beat size * 4
DMA_STEPSIZE_8, // etc...
DMA_STEPSIZE_16,
DMA_STEPSIZE_32,
DMA_STEPSIZE_64,
DMA_STEPSIZE_128,
} dma_stepsize_t;
// higher numbers are higher priority
typedef enum {
DMA_PRIORITY_0, // lowest (default)
DMA_PRIORITY_1,
DMA_PRIORITY_2,
DMA_PRIORITY_3, // highest
} dma_priority_t;
typedef enum {
DMA_STATUS_OK = 0,
DMA_STATUS_ERR_NOT_FOUND,
DMA_STATUS_ERR_NOT_INITIALIZED,
DMA_STATUS_ERR_INVALID_ARG,
DMA_STATUS_ERR_IO,
DMA_STATUS_ERR_TIMEOUT,
DMA_STATUS_BUSY,
DMA_STATUS_SUSPEND,
DMA_STATUS_ABORTED,
DMA_STATUS_JOBSTATUS = -1 // For printStatus() function
} dma_status_t;
#endif
#endif // DMA_UTIL_H_INCLUDED

66
dummy/peripherals/eic.c Normal file
View File

@ -0,0 +1,66 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include <stddef.h>
#include "eic.h"
#include "hal_gpio.h"
static void _eic_sync(void) {
}
void eic_init(void) {
}
void eic_enable(void) {
}
int8_t eic_configure_pin(const uint8_t pin, eic_interrupt_trigger_t trigger) {
return 0;
}
bool eic_enable_interrupt(const uint8_t pin) {
return false;
}
bool eic_disable_interrupt(const uint8_t pin) {
return false;
}
bool eic_enable_event(const uint8_t pin) {
return false;
}
bool eic_disable_event(const uint8_t pin) {
return false;
}
void eic_disable(void) {
}
void eic_configure_callback(eic_cb_t callback) {
}
void irq_handler_eic(void);
void irq_handler_eic(void) {
}

95
dummy/peripherals/eic.h Normal file
View File

@ -0,0 +1,95 @@
/**
* @file eic.h
* @brief External Interrupt Controller
*/
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
///@brief An enum defining the types of interrupt trigger you wish to scan for.
typedef enum eic_interrupt_trigger_t {
INTERRUPT_TRIGGER_NONE = 0,
INTERRUPT_TRIGGER_RISING,
INTERRUPT_TRIGGER_FALLING,
INTERRUPT_TRIGGER_BOTH,
} eic_interrupt_trigger_t;
typedef void (*eic_cb_t)(uint8_t channel);
/** @brief Initializes the external interrupt controller, but does not enable it.
*/
void eic_init(void);
/** @brief Enables the external interrupt controller.
*/
void eic_enable(void);
/** @brief Configures an external interrupt on one of the external interrupt pins.
* @details This function configures the interrupt channel with the specified trigger, but it does not
* set pin direction, mux or pull; you must set up the pin yourself. This function also does
* not enable an interrupt or event generation. You must call eic_enable_interrupt() or
* eic_enable_event() to either wake the processor or generate an event for a peripheral.
* @param pin The external interrupt pin you wish to configure — use HAL_GPIO_xxx_PIN() macro.
* @param trigger The condition on which you wish to trigger: rising, falling or both.
* @return the EIC channel number associated with the pin, or -1 if the pin is not an interrupt pin.
* @note Be sure to check your pin multiplexing table to ensure that you do not have multiple pins
* assigned to the same interrupt channel. Also note that the NMI pin is not currently supported.
*/
int8_t eic_configure_pin(const uint8_t pin, eic_interrupt_trigger_t trigger);
/** @brief Enables an interrupt on the given interrupt channel.
* @param pin The external interrupt pin.
*/
bool eic_enable_interrupt(const uint8_t pin);
/** @brief Disables the interrupt on the given interrupt channel.
* @param pin The external interrupt pin.
*/
bool eic_disable_interrupt(const uint8_t pin);
/** @brief Enables an interrupt on the given interrupt channel.
* @param pin The external interrupt pin.
*/
bool eic_enable_event(const uint8_t pin);
/** @brief Disables the interrupt on the given interrupt channel.
* @param pin The external interrupt pin.
*/
bool eic_disable_event(const uint8_t pin);
/** @brief Configures an external interrupt callback.
* @details You only get the one callback, so if you need to handle multiple interrupts, you'll need
* to check the EIC->INTFLAG register in your callback to determine which interrupt fired.
* @param callback The function that will be called when the interrupt fires.
* @note This function is called from the interrupt handler, so it should be as short as possible.
*/
void eic_configure_callback(eic_cb_t callback);
/** @brief Disables the external interrupt controller.
*/
void eic_disable(void);

50
dummy/peripherals/i2c.c Normal file
View File

@ -0,0 +1,50 @@
/*
Cribbed from the Castor & Pollux Gemini firmware:
https://github.com/wntrblm/Castor_and_Pollux/
Copyright (c) 2021 Alethea Katherine Flowers.
Published under the standard MIT License.
Full text available at: https://opensource.org/licenses/MIT
*/
#include "pins.h"
#include "system.h"
#include "sercom.h"
#include "i2c.h"
#if defined(I2C_SERCOM)
void i2c_init(void) {
}
void i2c_enable(void) {
}
i2c_result_t i2c_write(uint8_t address, uint8_t* data, size_t len) {
return 0;
}
i2c_result_t i2c_read(uint8_t address, uint8_t* data, size_t len) {
return 0;
}
void i2c_disable(void) {
}
#endif
void i2c_init_instance(uint8_t sercom, uint32_t baud) {
}
void i2c_enable_instance(uint8_t sercom) {
}
i2c_result_t i2c_write_instance(uint8_t sercom, uint8_t address, uint8_t* data, size_t len) {
return 0;
}
i2c_result_t i2c_read_instance(uint8_t sercom, uint8_t address, uint8_t* data, size_t len) {
return 0;
}
void i2c_disable_instance(uint8_t sercom) {
}

96
dummy/peripherals/i2c.h Normal file
View File

@ -0,0 +1,96 @@
/**
* @file i2c.h
* @brief I2C Peripheral
*/
/*
Cribbed from the Castor & Pollux Gemini firmware:
https://github.com/wntrblm/Castor_and_Pollux/
Copyright (c) 2021 Alethea Katherine Flowers.
Published under the standard MIT License.
Full text available at: https://opensource.org/licenses/MIT
*/
#pragma once
/* Routines for interacting with I2C devices. */
#include <stdint.h>
#include <stdbool.h>
#include <stddef.h>
typedef int i2c_result_t;
/**
* @brief Initializes the I2C peripheral for a board with defined SDA/SCL pins.
* Defaults to a bus speed of 100kHz.
* @details This function will only work if a board has pins named SDA and SCL,
* and relevant definitions for I2C_SERCOM. If you don't have these
* definitions, the build will fail at link time.
*/
void i2c_init(void);
/**
* @brief Enables the I2C peripheral for a board with defined SDA/SCL pins.
*/
void i2c_enable(void);
/**
* @brief Writes data to an I2C device at the provided address.
* @param address The I2C address of the device.
* @param data The data to write.
* @param len The length of the data to write.
*/
i2c_result_t i2c_write(uint8_t address, uint8_t* data, size_t len);
/**
* @brief Reads data from an I2C device at the provided address.
* @param address The I2C address of the device.
* @param data A pointer to the buffer to read into.
* @param len The length of the data to read.
*/
i2c_result_t i2c_read(uint8_t address, uint8_t* data, size_t len);
/**
* @brief Disables the I2C peripheral for a board with defined SDA/SCL pins.
*/
void i2c_disable(void);
/**
* @brief Initializes an I2C peripheral on the given SERCOM.
* @param sercom The SERCOM you wish to use, as numbered in the data sheet.
* @param baud The baud rate you wish to use.
* @note You are responsible for setting the appropriate pin mux for the SDA and SCL pins.
* This function does not know which pins you intend to use, or whether they are on
* the SERCOM or SERCOM_ALT pin mux.
*/
void i2c_init_instance(uint8_t sercom, uint32_t baud);
/**
* @brief Enables the I2C peripheral on the given SERCOM.
* @param sercom The SERCOM of the I2C peripheral, as numbered in the data sheet.
*/
void i2c_enable_instance(uint8_t sercom);
/**
* @brief Writes data to an I2C device on the given SERCOM at the provided address.
* @param sercom The SERCOM of the I2C peripheral, as numbered in the data sheet.
* @param address The I2C address of the device.
* @param data The data to write.
* @param len The length of the data to write.
*/
i2c_result_t i2c_write_instance(uint8_t sercom, uint8_t address, uint8_t* data, size_t len);
/**
* @brief Reads data from an I2C device on the given SERCOM at the provided address.
* @param sercom The SERCOM of the I2C peripheral, as numbered in the data sheet.
* @param address The I2C address of the device.
* @param data A pointer to the buffer to read into.
* @param len The length of the data to read.
*/
i2c_result_t i2c_read_instance(uint8_t sercom, uint8_t address, uint8_t* data, size_t len);
/**
* @brief Disables the I2C peripheral on the given SERCOM.
* @param sercom The SERCOM of the I2C peripheral, as numbered in the data sheet.
*/
void i2c_disable_instance(uint8_t sercom);

38
dummy/peripherals/i2s.c Normal file
View File

@ -0,0 +1,38 @@
/*
* MIT License
*
* Copyright (c) 2023 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include "pins.h"
#include "system.h"
#include "i2s.h"
/// TODO: I2S on SAM D51
#ifdef _SAMD21_
void i2s_init(uint8_t instance, uint16_t sampleRate, uint8_t bitsPerSample, i2s_mode_t mode) {
}
void i2s_enable_receiver(uint8_t instance) {
}
#endif

46
dummy/peripherals/i2s.h Normal file
View File

@ -0,0 +1,46 @@
/**
* @file i2s.h
* @brief Inter-IC Sound interface (SAM D21 only)
*/
/*
* MIT License
*
* Copyright (c) 2023 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
#ifdef I2S
typedef enum {
I2S_MODE_NORMAL,
I2S_MODE_RIGHT_JUSTIFIED,
I2S_MODE_LEFT_JUSTIFIED,
} i2s_mode_t;
void i2s_init(uint8_t instance, uint16_t sampleRate, uint8_t bitsPerSample, i2s_mode_t mode);
void i2s_enable_receiver(uint8_t instance);
#endif

58
dummy/peripherals/opamp.c Normal file
View File

@ -0,0 +1,58 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include "pins.h"
#include "system.h"
#include "opamp.h"
#ifdef OPAMP
void opamp_init(void) {
}
void opamp_enable(uint16_t instance) {
}
void opamp_set_muxpos(uint16_t instance, uint8_t muxpos) {
}
void opamp_set_muxneg(uint16_t instance, uint8_t muxneg) {
}
void opamp_set_potmux(uint16_t instance, uint8_t potmux) {
}
void opamp_set_res1mux(uint16_t instance, uint8_t res1mux) {
}
void opamp_set_res2mux(uint16_t instance, uint8_t res2mux) {
}
void opamp_set_analog_connection(uint16_t instance, bool connected) {
}
void opamp_disable(uint16_t instance) {
}
#endif

172
dummy/peripherals/opamp.h Normal file
View File

@ -0,0 +1,172 @@
/**
* @file opamp.h
* @brief Operational Amplifier Peripheral
*/
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
#ifdef OPAMP
#define OPAMP_MUXNEG_NEG (0)
#define OPAMP_MUXNEG_LADDER (1)
#define OPAMP_MUXNEG_OUT (2)
#define OPAMP0_MUXNEG_DAC (3)
#define OPAMP1_MUXNEG_DAC (3)
#define OPAMP2_MUXNEG_DAC (5)
#define OPAMP2_MUXNEG_NEG_0 (3)
#define OPAMP2_MUXNEG_NEG_1 (4)
#define OPAMP_MUXPOS_POS (0)
#define OPAMP_MUXPOS_LADDER (1)
#define OPAMP0_MUXPOS_DAC (2)
#define OPAMP1_MUXPOS_OUT_0 (2)
#define OPAMP2_MUXPOS_OUT_1 (2)
#define OPAMP_MUXPOS_GND (3)
#define OPAMP2_MUXPOS_POS_0 (4)
#define OPAMP2_MUXPOS_POS_1 (5)
#define OPAMP2_MUXPOS_LADDER_0 (6)
#define OPAMP_POTMUX_RATIO_14_2 (0)
#define OPAMP_POTMUX_RATIO_12_4 (1)
#define OPAMP_POTMUX_RATIO_8_8 (2)
#define OPAMP_POTMUX_RATIO_6_10 (3)
#define OPAMP_POTMUX_RATIO_4_12 (4)
#define OPAMP_POTMUX_RATIO_3_13 (5)
#define OPAMP_POTMUX_RATIO_2_14 (6)
#define OPAMP_POTMUX_RATIO_1_15 (7)
#define OPAMP_RES1MUX_POS (0)
#define OPAMP_RES1MUX_NEG (1)
#define OPAMP0_RES1MUX_DAC (2)
#define OPAMP1_RES1MUX_OUT_0 (2)
#define OPAMP2_RES1MUX_OUT_1 (2)
#define OPAMP_RES1MUX_GND (3)
#define OPAMP_RES1MUX_NC (4)
#define OPAMP_RES2MUX_VCC (0)
#define OPAMP_RES2MUX_OUT (1)
#define OPAMP_RES2MUX_NC (2)
/**
* @brief Initializes the OPAMP peripheral, but does not enable any opamps.
*/
void opamp_init(void);
/**
* @brief Enables the given opamp.
* @param instance The opamp instance to enable.
*/
void opamp_enable(uint16_t instance);
/**
* @brief Sets the positive input mux for the given opamp.
* @param instance The opamp instance to configure.
* @param muxpos The desired connection, one of:
* * OPAMP_MUXPOS_POS - the positive input pin for this instance
* * OPAMP_MUXPOS_GND - ground
* * OPAMP_MUXPOS_LADDER - the resistor ladder tap for this instance
* * OPAMP0_MUXPOS_DAC - the DAC output (only valid for OPAMP0)
* * OPAMP1_MUXPOS_OUT_0 - OPAMP0's output (only valid for OPAMP1)
* * OPAMP2_MUXPOS_OUT_1 - OPAMP1's output (only valid for OPAMP2)
* * OPAMP2_MUXPOS_POS_0 - OPAMP0's positive input pin (only valid for OPAMP2)
* * OPAMP2_MUXPOS_POS_1 - OPAMP1's positive input pin (only valid for OPAMP2)
* * OPAMP2_MUXPOS_LADDER_0 - OPAMP0's resistor ladder tap (only valid for OPAMP2)
*/
void opamp_set_muxpos(uint16_t instance, uint8_t muxpos);
/**
* @brief Sets the negative input mux for the given opamp.
* @param instance The opamp instance to configure.
* @param muxneg The desired connection, one of:
* * OPAMP_MUXNEG_NEG - the negative input pin for this instance
* * OPAMP_MUXNEG_LADDER - the resistor ladder tap for this instance
* * OPAMP_MUXNEG_OUT - the output of this instance
* * OPAMP0_MUXNEG_DAC - the DAC output (only valid for OPAMP0)
* * OPAMP1_MUXNEG_DAC - the DAC output (only valid for OPAMP1)
* * OPAMP2_MUXNEG_DAC - the DAC output (only valid for OPAMP2)
* * OPAMP2_MUXNEG_NEG_0 - OPAMP0's negative input pin (only valid for OPAMP2)
* * OPAMP2_MUXNEG_NEG_1 - OPAMP1's negative input pin (only valid for OPAMP2)
*/
void opamp_set_muxneg(uint16_t instance, uint8_t muxneg);
/**
* @brief Sets the potentiometer (resistor ladder) mux for the given opamp.
* @param instance The opamp instance to configure.
* @param potmux The desired resistor ladder ratio, one of:
* * OPAMP_POTMUX_RATIO_14_2 - 14:2 ratio
* * OPAMP_POTMUX_RATIO_12_4 - 12:4 ratio
* * OPAMP_POTMUX_RATIO_8_8 - 8:8 ratio
* * OPAMP_POTMUX_RATIO_6_10 - 6:10 ratio
* * OPAMP_POTMUX_RATIO_4_12 - 4:12 ratio
* * OPAMP_POTMUX_RATIO_3_13 - 3:13 ratio
* * OPAMP_POTMUX_RATIO_2_14 - 2:14 ratio
* * OPAMP_POTMUX_RATIO_1_15 - 1:15 ratio
*/
void opamp_set_potmux(uint16_t instance, uint8_t potmux);
/**
* @brief Sets the connection for the bottom of the resistor ladder for the given instance.
* @param instance The opamp instance to configure.
* @param res1mux The desired connection, one of:
* * OPAMP_RES1MUX_POS - the positive input pin for this instance
* * OPAMP_RES1MUX_NEG - the negative input pin for this instance
* * OPAMP_RES1MUX_GND - ground
* * OPAMP0_RES1MUX_DAC - the DAC output (only valid for OPAMP0)
* * OPAMP1_RES1MUX_OUT_0 - OPAMP0's output (only valid for OPAMP1)
* * OPAMP2_RES1MUX_OUT_1 - OPAMP1's output (only valid for OPAMP2)
* * OPAMP_RES1MUX_NC - not connected
*/
void opamp_set_res1mux(uint16_t instance, uint8_t res1mux);
/**
* @brief Sets the connection for the top of the resistor ladder for the given instance.
* @param instance The opamp instance to configure.
* @param res2mux The desired connection, one of:
* * OPAMP_RES2MUX_VCC - VDDANA
* * OPAMP_RES2MUX_OUT - the output of this instance
* * OPAMP_RES2MUX_NC - not connected
*/
void opamp_set_res2mux(uint16_t instance, uint8_t res2mux);
/**
* @brief Sets or removes the connection from the opamp output to the ADC / AC.
* @param instance The opamp instance to configure.
* @param connected True to connect the opamp output to the ADC / AC, false
* to disconnect it.
*/
void opamp_set_analog_connection(uint16_t instance, bool connected);
/**
* @brief Disables the given opamp.
* @param instance The opamp instance to disable.
* @note You should disable the opamp before reconfiguring it, and re-enable it afterwards.
*/
void opamp_disable(uint16_t instance);
#endif

47
dummy/peripherals/ptc.c Normal file
View File

@ -0,0 +1,47 @@
/*
* FreeTouch, a QTouch-compatible library - tested on ATSAMD21 only!
* The MIT License (MIT)
*
* Copyright (c) 2017 Limor 'ladyada' Fried for Adafruit Industries
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
#include "ptc.h"
#ifdef HAS_PTC
static void _ptc_sync() {
}
static bool _ptc_is_conversion_finished() {
return true;
}
void ptc_init(void) {
}
void ptc_enable(uint8_t channel) {
}
uint16_t ptc_get_value(uint8_t channel) {
return 0;
}
#endif

112
dummy/peripherals/ptc.h Normal file
View File

@ -0,0 +1,112 @@
/**
* @file ptc.h
* @brief Peripheral Touch Controller
*/
/*
* FreeTouch, a QTouch-compatible library - tested on ATSAMD21 only!
* The MIT License (MIT)
*
* Copyright (c) 2017 Limor 'ladyada' Fried for Adafruit Industries
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in
* all copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN
* THE SOFTWARE.
*/
#pragma once
#include <stdbool.h>
#include <stdint.h>
#ifdef _SAMD21_
#include "component/samd21_ptc_component.h"
#define HAS_PTC 1
#endif
#ifdef _SAMD11_
#include "component/samd11_ptc_component.h"
#define HAS_PTC 1
#endif
#ifdef HAS_PTC
/* Touch library oversampling (filter) setting */
typedef enum tag_oversample_level_t {
OVERSAMPLE_1,
OVERSAMPLE_2,
OVERSAMPLE_4,
OVERSAMPLE_8,
OVERSAMPLE_16,
OVERSAMPLE_32,
OVERSAMPLE_64
} ptc_oversample_t;
/* Touch library series resistor setting */
typedef enum tag_series_resistor_t {
RESISTOR_0,
RESISTOR_20K,
RESISTOR_50K,
RESISTOR_100K,
} ptc_series_resistor_t;
typedef enum tag_freq_mode_t {
FREQ_MODE_NONE,
FREQ_MODE_HOP,
FREQ_MODE_SPREAD,
FREQ_MODE_SPREAD_MEDIAN
} ptc_freq_mode_t;
typedef enum tag_freq_hop_t {
FREQ_HOP_1,
FREQ_HOP_2,
FREQ_HOP_3,
FREQ_HOP_4,
FREQ_HOP_5,
FREQ_HOP_6,
FREQ_HOP_7,
FREQ_HOP_8,
FREQ_HOP_9,
FREQ_HOP_10,
FREQ_HOP_11,
FREQ_HOP_12,
FREQ_HOP_13,
FREQ_HOP_14,
FREQ_HOP_15,
FREQ_HOP_16
} ptc_freq_hop_t;
/**
* @brief Initialize the peripheral touch controller.
*/
void ptc_init(void);
/**
* @brief Enable the given PTC channel.
* @param channel The PTC channel (NOT pin number) to enable.
* @note You are still responsible for configuring the pin mux.
* Also we don't yet have a way to disable a channel.
*/
void ptc_enable(uint8_t channel);
/**
* @brief Get a value from the given channel.
* @param channel The PTC channel (NOT pin number) to read.
* @return The touch value read from the channel.
*/
uint16_t ptc_get_value(uint8_t channel);
#endif

69
dummy/peripherals/rtc.c Normal file
View File

@ -0,0 +1,69 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include <stddef.h>
#include "rtc.h"
rtc_cb_t _rtc_callback = NULL;
#if defined(_SAMD21_) || defined(_SAMD11_)
#define CTRLREG (RTC->MODE2.CTRL)
#else
#define CTRLREG (RTC->MODE2.CTRLA)
#endif
bool rtc_is_enabled(void) {
return true;
}
static void _rtc_sync(void) {
}
void rtc_init(void) {
}
void rtc_enable(void) {
}
void rtc_set_date_time(rtc_date_time_t date_time) {
}
rtc_date_time_t rtc_get_date_time(void) {
rtc_date_time_t date_time = {0};
return date_time;
}
void rtc_enable_alarm_interrupt(rtc_date_time_t alarm_time, rtc_alarm_match_t mask) {
}
void rtc_configure_callback(rtc_cb_t callback) {
}
void rtc_disable_alarm_interrupt(void) {
}
void irq_handler_rtc(void);
void irq_handler_rtc(void) {
}

104
dummy/peripherals/rtc.h Normal file
View File

@ -0,0 +1,104 @@
/**
* @file rtc.h
* @brief Real-Time Clock
*/
/*
* MIT License
*
* Copyright (c) 2020 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
#define RTC_REFERENCE_YEAR (2020)
typedef union {
struct {
uint32_t second : 6; // 0-59
uint32_t minute : 6; // 0-59
uint32_t hour : 5; // 0-23
uint32_t day : 5; // 1-31
uint32_t month : 4; // 1-12
uint32_t year : 6; // 0-63 (representing 2020-2083)
} unit;
uint32_t reg; // the bit-packed value as expected by the RTC peripheral's CLOCK register.
} rtc_date_time_t;
typedef enum rtc_alarm_match_t {
ALARM_MATCH_DISABLED = 0,
ALARM_MATCH_SS,
ALARM_MATCH_MMSS,
ALARM_MATCH_HHMMSS,
} rtc_alarm_match_t;
typedef void (*rtc_cb_t)(uint16_t intflag);
/** @brief Initializes the RTC.
* @details Configures the RTC for 24-hour clock / calendar mode, with a 1 Hz
* tick derived from the 1024 Hz clock on GCLK3 (for SAM D devices)
* or OSC32KCTRL's most accurate 1024 Hz output (for SAM L devices).
*/
void rtc_init(void);
/** @brief Enables the RTC.
*/
void rtc_enable(void);
/** @brief Checks if the RTC is enabled.
* @return true if the RTC is enabled; false if not.
*/
bool rtc_is_enabled(void);
/** @brief Sets the date and time.
* @param date_time The date and time you wish to set, with a year value from 0-63 representing 2020-2083.
* @note The RTC stores the year as six bits representing a value from 0 to 63. It treats this as a year
* offset from a reference year, which must be a leap year. Since 2020 was a leap year, and it allows
* useful dates through 2083, it is assumed that apps will use 2020 as the reference year; thus
* 1 means 2021, 2 means 2022, etc. **You will be responsible for handling this offset in your code**,
* if the calendar year is needed for timestamp calculation logic or display purposes.
*/
void rtc_set_date_time(rtc_date_time_t date_time);
/** @brief Returns the date and time.
* @return A rtc_date_time_t with the current date and time, with a year value from 0-63 representing 2020-2083.
* @see rtc_set_date_time for notes about how the year is stored.
*/
rtc_date_time_t rtc_get_date_time(void);
/** @brief Enables the alarm interrupt.
* @param alarm_time The time that you wish to match. The date is currently ignored.
* @param mask One of the values in rtc_alarm_match_t indicating which values to check.
*/
void rtc_enable_alarm_interrupt(rtc_date_time_t alarm_time, rtc_alarm_match_t mask);
/** @brief Disables the alarm callback.
*/
void rtc_disable_alarm_interrupt(void);
/** @brief Configures the RTC alarm callback.
* @param callback The function to call when an RTC interrupt occurs. The callback
* will be passed a bitmask of the interrupt flags, the full contents
* of the RTC peripheral's INTFLAG register.
*/
void rtc_configure_callback(rtc_cb_t callback);

View File

@ -0,0 +1,12 @@
#include "sercom.h"
#include "system.h"
void _sercom_clock_setup(uint8_t sercom) {
}
void _sercom_enable(uint8_t sercom) {
}
void _sercom_disable(uint8_t sercom) {
}

View File

@ -0,0 +1,42 @@
/**
* @file sercom.h
* @brief Private functions for helping with SERCOM management.
*/
/*
* MIT License
*
* Copyright (c) 2023 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
/* Routines for interacting with SPI devices. */
#include <stdint.h>
#include <stdbool.h>
#include <stddef.h>
#include "system.h"
void _sercom_clock_setup(uint8_t sercom);
void _sercom_enable(uint8_t sercom);
void _sercom_disable(uint8_t sercom);

71
dummy/peripherals/slcd.c Normal file
View File

@ -0,0 +1,71 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include "slcd.h"
#ifdef SLCD
static void _slcd_sync(uint32_t reg) {
}
void slcd_init(uint64_t lcd_pins, slcd_bias_value_t bias, slcd_duty_value_t duty, slcd_clocksource_value_t clocksource, slcd_prescaler_value_t prescaler, slcd_clockdiv_value_t clkdiv) {
}
void slcd_set_contrast(uint8_t contrast) {
}
void slcd_enable(void) {
}
void slcd_clear(void) {
}
void slcd_set_segment(uint8_t com, uint8_t seg) {
}
void slcd_clear_segment(uint8_t com, uint8_t seg) {
}
void slcd_configure_frame_counter(uint8_t fc, uint8_t overflow_count, bool prescale) {
}
void slcd_set_frame_counter_enabled(uint8_t fc, bool enabled) {
}
void slcd_configure_blink(bool blink_all, uint8_t bss0, uint8_t bss1, uint8_t fc) {
}
void slcd_set_blink_enabled(bool enabled) {
}
void slcd_configure_circular_shift_animation(uint16_t initial_value, uint8_t size, slcd_csrshift_value_t shift_dir, uint8_t fc) {
}
void slcd_set_circular_shift_animation_enabled(bool enabled) {
}
void slcd_disable(void) {
}
#endif // SLCD

236
dummy/peripherals/slcd.h Normal file
View File

@ -0,0 +1,236 @@
/**
* @file slcd.h
* @brief Segment Liquid Crystal Display (SLCD) peripheral driver (SAM L22 only)
*/
/*
* MIT License
*
* Copyright (c) 2023 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
#include <stddef.h>
#include "system.h"
#ifdef SLCD
typedef enum {
SLCD_BIAS_STATIC = 0,
SLCD_BIAS_HALF = 1,
SLCD_BIAS_THIRD = 2,
SLCD_BIAS_FOURTH = 3,
} slcd_bias_value_t;
typedef enum {
SLCD_DUTY_1_COMMON = 0,
SLCD_DUTY_2_COMMON = 1,
SLCD_DUTY_3_COMMON = 2,
SLCD_DUTY_4_COMMON = 3,
SLCD_DUTY_6_COMMON = 4,
SLCD_DUTY_8_COMMON = 5,
} slcd_duty_value_t;
typedef enum {
SLCD_PRESCALER_DIV16 = 0,
SLCD_PRESCALER_DIV32 = 1,
SLCD_PRESCALER_DIV64 = 2,
SLCD_PRESCALER_DIV128 = 3,
} slcd_prescaler_value_t;
typedef enum {
SLCD_CLOCKSOURCE_ULP = 0,
SLCD_CLOCKSOURCE_XOSC = 1,
} slcd_clocksource_value_t;
typedef enum {
SLCD_CLOCKDIV_1 = 0,
SLCD_CLOCKDIV_2 = 1,
SLCD_CLOCKDIV_3 = 2,
SLCD_CLOCKDIV_4 = 3,
SLCD_CLOCKDIV_5 = 4,
SLCD_CLOCKDIV_6 = 5,
SLCD_CLOCKDIV_7 = 6,
SLCD_CLOCKDIV_8 = 7,
} slcd_clockdiv_value_t;
typedef enum {
SLCD_CSRSHIFT_LEFT = 0,
SLCD_CSRSHIFT_RIGHT = 1,
} slcd_csrshift_value_t;
/**
* @brief Initializes the SLCD peripheral, but does not enable it.
* @details This function sets up the SLCD peripheral with some defaults:
* * LCD runs in standby
* * Clocked with the ultra low power 32kHz oscillator
* * Lowest possible contrast level (2.45 volts)
* * Uses the low power waveform
* * Charge pump refresh at 250Hz (slowest option)
* * Reference Refresh at 62.5Hz (slowest option)
* * Bias buffer enabled (side note / TODO: does turning this off save power?)
*
* You will need to specify the remaining configuration options.
* Duty and bias are easy, but prescaler, clock divider and number of COM lines
* will combine to determine the frame rate of the display according to
* this formula: 32768/(prescaler * clock_divider * number_of_common_lines)
* @param lcd_pins A 64-bit mask of the pins to use for the SLCD, as numbered in the pin
* mux table in the data sheet (SLCD/LP[n]). For example, PB08 is SLCD/LP[2]
* and PA05 is SLCD/LP[5], so the mask for using both of these pins would be
* (1 << 2) | (1 << 5). The lowest pins are always used as the common lines,
* so for a 1/2 duty LCD using pins 2, 5, 6, 7, 30 and 35, pins 2 and 5 would
* be the COM0 and COM1, and the rest would be segment lines SEG0-SEG3.
* @param bias The bias configuration for the SLCD. Valid options are:
* * SLCD_BIAS_STATIC for a static display (0V, VLCD)
* * SLCD_BIAS_HALF for 1/2 bias (0V, 1/2 VLCD, VLCD)
* * SLCD_BIAS_THIRD for 1/3 bias (0V, 1/3 VLCD, 2/3 VLCD, VLCD)
* * SLCD_BIAS_FOURTH for 1/4 bias (0V, 1/4 VLCD, 1/2 VLCD, 3/4 VLCD, VLCD)
* @param duty The duty cycle for the SLCD, aka the number of common lines.
* Valid options are:
* * SLCD_DUTY_1_COMMON for a static display
* * SLCD_DUTY_2_COMMON for two common lines and a 1/2 duty cycle
* * SLCD_DUTY_3_COMMON for three common lines and a 1/3 duty cycle
* * SLCD_DUTY_4_COMMON for four common lines and a 1/4 duty cycle
* * SLCD_DUTY_6_COMMON for six common lines and a 1/6 duty cycle
* * SLCD_DUTY_8_COMMON for eight common lines and a 1/8 duty cycle
* @param clocksource The clock source for the SLCD.
* Valid options are:
* * SLCD_CLOCKSOURCE_ULP for the low-accuracy, low-power internal 32kHz oscillator
* * SLCD_CLOCKSOURCE_XOSC for an external 32kHz crystal oscillator
* @param prescaler The prescaler factor, which initially divides the 32kHz clock.
* Valid options are:
* * SLCD_CTRLA_PRESC_PRESC16_Val - Divide by 16
* * SLCD_CTRLA_PRESC_PRESC32_Val - Divide by 32
* * SLCD_CTRLA_PRESC_PRESC64_Val - Divide by 64
* * SLCD_CTRLA_PRESC_PRESC128_Val - Divide by 128
* @param clock_divider The clock divider, which divides the prescaled clock.
* Valid options areL
* * SLCD_CLOCKDIV_1 for no division
* * SLCD_CLOCKDIV_2 to divide by 2
* * SLCD_CLOCKDIV_3 to divide by 3
* * SLCD_CLOCKDIV_4 to divide by 4
* * SLCD_CLOCKDIV_5 to divide by 5
* * SLCD_CLOCKDIV_6 to divide by 6
* * SLCD_CLOCKDIV_7 to divide by 7
* * SLCD_CLOCKDIV_8 to divide by 8
*/
void slcd_init(uint64_t lcd_pins, slcd_bias_value_t bias, slcd_duty_value_t duty, slcd_clocksource_value_t clocksource, slcd_prescaler_value_t prescaler, slcd_clockdiv_value_t clkdiv);
/**
* @brief Sets the contrast level for the display. Valid values are from 0-15.
* @param contrast The contrast configuration for the SLCD
* @details In internal supply mode, VLCD is in the range of 2.45V (contrast 0)
* to 3.45V (contrast 15).
* @note You can set the contrast level at any time, without disabling the SLCD.
*/
void slcd_set_contrast(uint8_t contrast);
/**
* @brief Enables the SLCD peripheral
*/
void slcd_enable(void);
/**
* @brief Clears all display memory
*/
void slcd_clear(void);
/**
* @brief Sets a segment in the display memory
* @param com The common line to set. Valid options are 0-7.
* @param seg The segment to set. Valid options are 0-39.
*/
void slcd_set_segment(uint8_t com, uint8_t seg);
/**
* @brief Clears a segment in the display memory
* @param com The common line to clear. Valid options are 0-7.
* @param seg The segment to clear. Valid options are 0-39.
*/
void slcd_clear_segment(uint8_t com, uint8_t seg);
/**
* @brief Configures one of the three frame counters.
* @note SLCD must be disabled to configure frame counters.
* @param fc The frame counter to enable. Valid options are 0, 1, or 2.
* @param overflow_count The number of frames to count before the overflow fires.
* Maximum value is 32 frames.
* @param prescale If true, the frame counter will count every 8th frame instead of every frame.
* This will let you count up to 256 frames in increments of 8.
*/
void slcd_configure_frame_counter(uint8_t fc, uint8_t overflow_count, bool prescale);
/**
* @brief Enables or disables one of the three frame counters.
* @note You can enable a frame counter at any time; there is no need to disable the SLCD first.
* @param fc The frame counter to enable. Valid options are 0, 1, or 2.
* @param enabled If true, the frame counter is enabled. If false, the frame counter is disabled.
*/
void slcd_set_frame_counter_enabled(uint8_t fc, bool enabled);
/**
* @brief Configures the blink mode, but does not start blinking.
* @note SLCD must be disabled to configure the blinking mode.
* @param blink_all If true, all segments will blink. If false, only the segments
* specified in the next two masks will blink.
* @param bss0 Blink segment select 0. A 1 in any bit position (n) will cause the (COMn, SEG0)
* segment to blink. Ignored if blink_all is true.
* @param bss1 Blink segment select 1. A 1 in any bit position (n) will cause the (COMn, SEG1)
* segment to blink. Ignored if blink_all is true.
* @param fc The frame counter to use for blinking. Valid options are 0, 1, or 2.
*/
void slcd_configure_blink(bool blink_all, uint8_t bss0, uint8_t bss1, uint8_t fc);
/**
* @brief Enables or disables blinking according to the configuration set by slcd_configure_blink.
* @note You can enable blinking at any time; there is no need to disable the SLCD first.
* @param enabled If true, blinking is enabled. If false, blinking is disabled.
*/
void slcd_set_blink_enabled(bool enabled);
/**
* @brief Configures the Circular Shift Register animation, but does not start it.
* This is pretty obscure and you should consult the datasheet for more information.
* @note SLCD must be disabled to configure the circular shift register.
* @param initial_value 16 bits. The initial value of the circular shift register.
* @param size The size of the circular shift register. Valid options are 2 through 16.
* @param shift_dir The direction of the shift. Valid options are SLCD_CSRSHIFT_LEFT or SLCD_CSRSHIFT_RIGHT.
* @param fc The frame counter to use for shifting. Valid options are 0, 1, or 2.
*/
void slcd_configure_circular_shift_animation(uint16_t initial_value, uint8_t size, slcd_csrshift_value_t shift_dir, uint8_t fc);
/**
* @brief Enables or disables circular shift register animation according to the configuration set
* by slcd_configure_circular_shift_animation.
* @note You can enable the CSR animation at any time; there is no need to disable the SLCD first.
* @param enabled If true, the CSR animation is enabled. If false, the CSR animation is disabled.
*/
void slcd_set_circular_shift_animation_enabled(bool enabled);
/**
* @brief Disables the SLCD peripheral
*/
void slcd_disable(void);
#endif // SLCD

42
dummy/peripherals/spi.c Normal file
View File

@ -0,0 +1,42 @@
/*
Cribbed from the Castor & Pollux Gemini firmware:
https://github.com/wntrblm/Castor_and_Pollux/
Copyright (c) 2021 Alethea Katherine Flowers.
Published under the standard MIT License.
Full text available at: https://opensource.org/licenses/MIT
*/
#include "pins.h"
#include "system.h"
#include "sercom.h"
#include "spi.h"
#if defined(SPI_SERCOM)
void spi_init(spi_mode_t mode, uint32_t baud) {
}
void spi_enable(void) {
}
uint8_t spi_transfer(uint8_t data) {
return 0;
}
void spi_disable(void) {
}
#endif
void spi_init_instance(uint8_t sercom, spi_dopo_t dopo, spi_dipo_t dipo, spi_mode_t mode, uint32_t baud) {
}
void spi_enable_instance(uint8_t sercom) {
}
uint8_t spi_transfer_instance(uint8_t sercom, uint8_t data) {
return 0;
}
void spi_disable_instance(uint8_t sercom) {
}

57
dummy/peripherals/spi.h Normal file
View File

@ -0,0 +1,57 @@
/**
* @file spi.h
* @brief SPI Peripheral
*/
/*
Cribbed from the Castor & Pollux Gemini firmware:
https://github.com/wntrblm/Castor_and_Pollux/
Copyright (c) 2021 Alethea Katherine Flowers.
Published under the standard MIT License.
Full text available at: https://opensource.org/licenses/MIT
*/
#pragma once
/* Routines for interacting with SPI devices. */
#include <stdint.h>
#include <stdbool.h>
#include <stddef.h>
typedef enum {
SPI_MODE_0 = 0,
SPI_MODE_1,
SPI_MODE_2,
SPI_MODE_3,
} spi_mode_t;
typedef enum {
SPI_DOPO_0_SCK_1 = 0,
SPI_DOPO_2_SCK_3,
SPI_DOPO_3_SCK_1,
SPI_DOPO_0_SCK_3,
} spi_dopo_t;
typedef enum {
SPI_DIPO_0 = 0,
SPI_DIPO_1,
SPI_DIPO_2,
SPI_DIPO_3,
SPI_DIPO_NONE = 0xff
} spi_dipo_t;
void spi_init(spi_mode_t mode, uint32_t baud);
void spi_enable(void);
uint8_t spi_transfer(uint8_t data);
void spi_disable(void);
void spi_init_instance(uint8_t sercom, spi_dopo_t dopo, spi_dipo_t dipo, spi_mode_t mode, uint32_t baud);
void spi_enable_instance(uint8_t sercom);
uint8_t spi_transfer_instance(uint8_t sercom, uint8_t data);
void spi_disable_instance(uint8_t sercom);

108
dummy/peripherals/tc.c Normal file
View File

@ -0,0 +1,108 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include "pins.h"
#include "tc.h"
#include "sam.h"
static void tc_sync(uint8_t instance) {
}
bool tc_init(uint8_t instance, generic_clock_generator_t clocksource, tc_prescaler_value_t prescaler) {
return false;
}
void tc_set_counter_mode(uint8_t instance, tc_counter_mode_t mode) {
}
void tc_set_run_in_standby(uint8_t instance, bool runStandby) {
}
void tc_set_wavegen(uint8_t instance, tc_wavegen_t mode) {
}
void tc_set_channel_polarity(uint8_t instance, uint8_t channel, tc_channel_polarity_t polarity) {
}
void tc_enable(uint8_t instance) {
}
bool tc_is_enabled(uint8_t instance) {
return false;
}
void tc_count8_set_period(uint8_t instance, uint8_t period) {
}
uint8_t tc_count8_get_period(uint8_t instance) {
return 0;
}
void tc_count8_set_cc(uint8_t instance, uint8_t channel, uint8_t value) {
}
void tc_count16_set_cc(uint8_t instance, uint8_t channel, uint16_t value) {
}
void tc_count32_set_cc(uint8_t instance, uint8_t channel, uint32_t value) {
}
void tc_count8_set_count(uint8_t instance, uint8_t value) {
}
void tc_count16_set_count(uint8_t instance, uint16_t value) {
}
void tc_count32_set_count(uint8_t instance, uint32_t value) {
}
static void _tc_request_read_count(uint8_t instance) {
}
uint8_t tc_count8_get_count(uint8_t instance) {
return 0;
}
uint16_t tc_count16_get_count(uint8_t instance) {
return 0;
}
uint32_t tc_count32_get_count(uint8_t instance) {
return 0;
}
void tc_stop(uint8_t instance) {
}
void tc_retrigger(uint8_t instance) {
}
void tc_disable(uint8_t instance) {
}
// TODO: every peripheral should have a deinit function, make public when that's done
/*
void tc_deinit(uint8_t instance) {
}
*/

275
dummy/peripherals/tc.h Normal file
View File

@ -0,0 +1,275 @@
/**
* @file tc.h
* @brief Timer/Counter Peripheral
*/
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
#include "system.h"
#include "sam.h"
typedef enum {
TC_PRESCALER_DIV1 = 0,
TC_PRESCALER_DIV2 = 1,
TC_PRESCALER_DIV4 = 2,
TC_PRESCALER_DIV8 = 3,
TC_PRESCALER_DIV16 = 4,
TC_PRESCALER_DIV64 = 5,
TC_PRESCALER_DIV256 = 6,
TC_PRESCALER_DIV1024 = 7
} tc_prescaler_value_t;
typedef enum {
TC_COUNTER_MODE_16BIT = 0,
TC_COUNTER_MODE_8BIT = 1,
TC_COUNTER_MODE_32BIT = 2,
} tc_counter_mode_t;
typedef enum {
TC_WAVEGEN_NORMAL_FREQUENCY = 0,
TC_WAVEGEN_MATCH_FREQUENCY = 1,
TC_WAVEGEN_NORMAL_PWM = 2,
TC_WAVEGEN_MATCH_PWM = 3,
} tc_wavegen_t;
typedef enum {
TC_CHANNEL_POLARITY_NORMAL = 0,
TC_CHANNEL_POLARITY_INVERTED = 1,
} tc_channel_polarity_t;
/** @brief Enables the peripheral clock for the TC and clocks it with the selected
* clock source. Also resets the TC to its starting configuration, which
* is COUNT16 mode.
* @details This just sets up the TC in its reset state. You are still responsible
* for configuring it with the options you need for waveform output.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param clocksource The generic clock source to use as the TC clock.
* @param prescaler The prescaler factor, which divides the clock source by a factor:
* * TC_PRESCALER_DIV1 - clock source unchanged
* * TC_PRESCALER_DIV2 - clock source divided by 2
* * TC_PRESCALER_DIV4 - clock source divided by 4
* * TC_PRESCALER_DIV8 - clock source divided by 8
* * TC_PRESCALER_DIV16 - clock source divided by 16
* * TC_PRESCALER_DIV64 - clock source divided by 64
* * TC_PRESCALER_DIV256 - clock source divided by 256
* * TC_PRESCALER_DIV102 - clock source divided by 1024
* @return true if the TC was set up, false if instance was out of range (i.e. you
* asked for TC3, but the microcontroller only has two TCs).
* @note if this function returns false, you shouldn't interact with this TC instance
* with any other functions; they don't do the bounds check that this does.
*/
bool tc_init(uint8_t instance, generic_clock_generator_t clocksource, tc_prescaler_value_t prescaler);
/**
* @brief Sets the TC's counting mode (an 8, 16 or 32-bit counter),
* @details In addition to setting the maximum value the counter can count to (MAX),
* this mode also affects the the available registers and the register layout.
* As a result, you must use the correctly prefixed function calls to set CC
* and PER values, depending on the mode set here.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param mode The counting mode to set:
* * TC_MODE_16 is the default and has a MAX value of 65,535. The CC0 and
* CC1 registers can accept values from 0-65535, and can be set using the
* tc_count16_set_cc function.
* * TC_COUNTER_MODE_8BIT has a MAX value of 255. The CC0 and CC1 registers can
* accept values from 0-255, and can be set using the tc_count8_set_cc
* function. This mode also gives you access to a PER register that can set
* the period. The PER register can be set using tc_count8_set_period.
* * TC_COUNTER_MODE_32BIT has a MAX value of 4294967295, and is more complex as it
* involves ganging the TC with an adjacent TC. This mode is not fully
* supported or tested, and may require additional setup.
*/
void tc_set_counter_mode(uint8_t instance, tc_counter_mode_t mode);
/**
* @brief Sets the TC's run-in-standby mode.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param runStandby true if the TC should keep running in standby mode, false if not.
*/
void tc_set_run_in_standby(uint8_t instance, bool runStandby);
/**
* @brief Sets the TC's waveform generation mode.
* @details This function influences how the waveform is generated by determining what
* happens when the counter matches and overflows.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param mode The waveform generation mode to set:
* * TC_WAVEGEN_NORMAL_FREQUENCY - Normal frequency generation. The TOP value is
* either PER (in 8-bit mode) or MAX (in 16-bit mode). Waveform output WO[0] /
* WO[1] toggles on a match with CC0 / CC1, and the counter resets at TOP.
* * TC_WAVEGEN_MATCH_FREQUENCY - Match frequency generation. The TOP value is CC0.
* WO[0] toggles on a match with TOP / CC0 and the counter resets. This results
* in a square wave with a 50% duty cycle whose frequency depends on CC0.
* It is also useful for creating a timer that overflows at a specific frequency
* for generating interrupts or triggering DMA requests.
* * TC_WAVEGEN_NORMAL_PWM - Normal pulse-width modulation. The TOP value is either
* PER (in 8-bit mode) or MAX (in 16-bit mode). Waveform output WO[0] / WO[1] is
* set on a match with CC0 / CC1, and cleared on a match with TOP. This results
* in a pair of square waves whose duty cycles are determined by CC0 / CC1.
* * TC_WAVEGEN_MATCH_PWM - Match pulse-width modulation. The TOP value is CC0.
* WO[1] toggles on a match with CC1, and WO[0] emits a one-clock-wide pulse on
* every overflow (i.e. when the counter matches CC0 and loops). This results in
* a square wave on WO[1] whose period depends on CC0 and whose duty cycle depends
* on CC1, and a series of pulses on WO[0] that occurs at the same period.
*/
void tc_set_wavegen(uint8_t instance, tc_wavegen_t mode);
/**
* @brief Sets the polarity of one of the waveform output channels.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param channel The waveform output channel. 0 or 1
* @param polarity The polarity to set. One of:
* * TCC_CHANNEL_POLARITY_NORMAL - The output is high when WO[n] is set.
* * TCC_CHANNEL_POLARITY_INVERTED - The output is low when WO[n] is set.
* @details This function can be used to invert one or both of the waveform outputs. Inverting
* one of the waveform outputs is useful to drive a device with a differential signal;
* inverting both outputs can be useful if you are driving something whose polarity is
* reversed, like a common anode LED.
*/
void tc_set_channel_polarity(uint8_t instance, uint8_t channel, tc_channel_polarity_t polarity);
/** @brief Enables the TC. Make sure to call tc_init first to set it up.
* @param instance The TC peripheral instance as numbered in the data sheet, or 0.
*/
void tc_enable(uint8_t instance);
/** @brief Checks whether the TC is enabled.
* @param instance The TC peripheral instance as numbered in the data sheet, or 0.
* @return true if the TC is enabled, false if instance is disabled.
*/
bool tc_is_enabled(uint8_t instance);
/**
* @brief Sets the TC's period or PER register in 8-bit mode.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param period The period to set. This value must be between 0 and 255, inclusive.
* Used above as described in `tc_set_wavegen`.
*/
void tc_count8_set_period(uint8_t instance, uint8_t period);
/**
* @brief Gets the TC's period or PER register in 8-bit mode.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @return The current period value.
*/
uint8_t tc_count8_get_period(uint8_t instance);
/**
* @brief Sets the TC's compare channel CC0 or CC1 register in 8-bit mode.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param channel The compare channel whose value set. This value must be 0 or 1.
* @param value The value to set. This value must be between 0 and 255, inclusive.
* Used above as described in `tc_set_wavegen`.
*/
void tc_count8_set_cc(uint8_t instance, uint8_t channel, uint8_t value);
/**
* @brief Sets the TC's compare channel CC0 or CC1 register in 16-bit mode.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param channel The compare channel whose value set. This value must be 0 or 1.
* @param value The value to set. This value must be between 0 and 65535, inclusive.
* Used above as described in `tc_set_wavegen`.
*/
void tc_count16_set_cc(uint8_t instance, uint8_t channel, uint16_t value);
/**
* @brief Sets the TC's compare channel CC0 or CC1 register in 32-bit mode.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param channel The compare channel whose value set. This value must be 0 or 1.
* @param value The value to set.
*/
void tc_count32_set_cc(uint8_t instance, uint8_t channel, uint32_t value);
/**
* @brief Sets the TC's counter value in 8-bit mode.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param value The value to set.
*/
void tc_count8_set_count(uint8_t instance, uint8_t value);
/**
* @brief Sets the TC's counter value in 16-bit mode.
* @details It is possible to change the counter value when the counter is stopped
* or when it is running.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param value The value to set.
*/
void tc_count16_set_count(uint8_t instance, uint16_t value);
/**
* @brief Sets the TC's counter value in 32-bit mode.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param value The value to set.
*/
void tc_count32_set_count(uint8_t instance, uint32_t value);
/**
* @brief Gets the TC's current counter value in 8-bit mode.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param value The value to set.
*/
uint8_t tc_count8_get_count(uint8_t instance);
/**
* @brief Gets the TC's current counter value in 16-bit mode.
* @details It is possible to change the counter value when the counter is stopped
* or when it is running.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param value The value to set.
*/
uint16_t tc_count16_get_count(uint8_t instance);
/**
* @brief Gets the TC's current counter value in 32-bit mode.
* @param instance The TC peripheral instance as numbered in the data sheet.
* @param value The value to set.
*/
uint32_t tc_count32_get_count(uint8_t instance);
/**
* @brief Issues a STOP command to the TC.
* @details When a Stop is detected while the counter is running, the counter will
* retain its current value. All waveforms are cleared and the Stop bit in
* the Status register is set (STATUS.STOP).
* @param instance The TC peripheral instance as numbered in the data sheet.
*/
void tc_stop(uint8_t instance);
/**
* @brief Issues a RETRIGGER command to the TC.
* @details When the command is detected during counting operation, the counter will
* be reset. When the re-trigger command is detected while the counter is
* stopped, the counter will resume counting from its current value.
* @param instance The TC peripheral instance as numbered in the data sheet.
*/
void tc_retrigger(uint8_t instance);
/** @brief Disables the TC, but retains all its settings.
* @param instance The TC peripheral instance as numbered in the data sheet, or 0.
*/
void tc_disable(uint8_t instance);

88
dummy/peripherals/tcc.c Normal file
View File

@ -0,0 +1,88 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include "pins.h"
#include "system.h"
#include "tcc.h"
static void tcc_sync(uint8_t instance) {
}
bool tcc_init(uint8_t instance, generic_clock_generator_t clocksource, tcc_prescaler_value_t prescaler) {
return 0;
}
void tcc_set_run_in_standby(uint8_t instance, bool runStandby) {
}
void tcc_set_wavegen(uint8_t instance, tcc_wavegen_t mode) {
}
void tcc_set_output_matrix(uint8_t instance, tcc_output_matrix_t mode) {
}
void tcc_set_channel_polarity(uint8_t instance, uint8_t channel, tcc_channel_polarity_t polarity) {
}
void tcc_enable(uint8_t instance) {
}
bool tcc_is_enabled(uint8_t instance) {
return false;
}
void tcc_set_period(uint8_t instance, uint32_t period, bool buffered) {
}
uint32_t tcc_get_period(uint8_t instance) {
return 0;
}
void tcc_set_cc(uint8_t instance, uint8_t channel, uint32_t value, bool buffered) {
}
void tcc_set_count(uint8_t instance, uint32_t value) {
}
uint32_t tcc_get_count(uint8_t instance) {
return 0;
}
void tcc_stop(uint8_t instance) {
}
void tcc_retrigger(uint8_t instance) {
}
void tcc_update(uint8_t instance) {
}
void tcc_disable(uint8_t instance) {
}
// TODO: every peripheral should have a deinit function, make public when that's done
/*
void tcc_deinit(uint8_t instance) {
}
*/

235
dummy/peripherals/tcc.h Normal file
View File

@ -0,0 +1,235 @@
/**
* @file tcc.h
* @brief Timer/Counter for Control Applications (TCC) Peripheral
*/
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
#include "sam.h"
typedef enum {
TCC_PRESCALER_DIV1 = 0,
TCC_PRESCALER_DIV2 = 1,
TCC_PRESCALER_DIV4 = 2,
TCC_PRESCALER_DIV8 = 3,
TCC_PRESCALER_DIV16 = 4,
TCC_PRESCALER_DIV64 = 5,
TCC_PRESCALER_DIV256 = 6,
TCC_PRESCALER_DIV1024 = 7
} tcc_prescaler_value_t;
typedef enum {
TCC_WAVEGEN_NORMAL_FREQUENCY = 0,
TCC_WAVEGEN_MATCH_FREQUENCY = 1,
TCC_WAVEGEN_NORMAL_PWM = 2,
// These modes may be supported in the future, but I don't have a use for them right now.
// TCC_WAVEGEN_DUAL_SLOPE_TOP = 7,
// TCC_WAVEGEN_DUAL_SLOPE_BOTTOM = 5,
// TCC_WAVEGEN_DUAL_SLOPE_BOTH = 6,
// TCC_WAVEGEN_DUAL_SLOPE_CRITICAL = 4,
} tcc_wavegen_t;
typedef enum {
TCC_OUTPUT_MATRIX_MODULO_4 = 0,
TCC_OUTPUT_MATRIX_MODULO_2 = 1,
TCC_OUTPUT_MATRIX_ALL_CC0 = 2,
TCC_OUTPUT_MATRIX_WO0_CC0_OTHERS_CC1 = 3,
} tcc_output_matrix_t;
typedef enum {
TCC_CHANNEL_POLARITY_NORMAL = 0,
TCC_CHANNEL_POLARITY_INVERTED = 1,
} tcc_channel_polarity_t;
/** @brief Enables the peripheral clock for the TCC and clocks it with the selected
* clock source. Also resets the TCC to its starting configuration.
* @details This just sets up the TCC in its reset state. You are still responsible
* for configuring it with the options you need for waveform output.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @param clocksource The clock source to use for the TCC.
* @param prescaler The prescaler factor, which divides the clock source by a factor:
* * TCC_PRESCALER_DIV1 - clock source unchanged
* * TCC_PRESCALER_DIV2 - clock source divided by 2
* * TCC_PRESCALER_DIV4 - clock source divided by 4
* * TCC_PRESCALER_DIV8 - clock source divided by 8
* * TCC_PRESCALER_DIV16 - clock source divided by 16
* * TCC_PRESCALER_DIV64 - clock source divided by 64
* * TCC_PRESCALER_DIV256 - clock source divided by 256
* * TCC_PRESCALER_DIV102 - clock source divided by 1024
* @return true if the TCC was set up, false if instance was out of range (i.e. you
* asked for TCC2, but the microcontroller only has one TCC).
* @note if this function returns false, you shouldn't interact with this TCC instance
* with any other functions; they don't do the bounds check that this does.
*/
bool tcc_init(uint8_t instance, generic_clock_generator_t clocksource, tcc_prescaler_value_t prescaler);
/**
* @brief Sets whether the TCC should run in standby mode.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @param runStandby true if the TCC should run in standby mode, false otherwise.
*/
void tcc_set_run_in_standby(uint8_t instance, bool runStandby);
/**
* @brief Sets the waveform generation mode for the TCC.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @param mode The waveform generation mode to use. One of:
* * TCC_WAVEGEN_NORMAL_FREQUENCY - Normal frequency generation. The TOP value is
* PER, and waveform output WO[n] toggles on a match with a compare channel (n % 4
* by default; @see `tcc_set_output_matrix` for other options). This mode results
* in a square wave with a frequency dependent on the PER register, and a duty
* cycle that depends on the CCn register.
* * TCC_WAVEGEN_MATCH_FREQUENCY - Match frequency generation. The TOP value is CC0.
* WO[0] toggles on a match with TOP / CC0 and the counter resets. This results
* in a square wave with a 50% duty cycle whose frequency depends on CC0.
* * TCC_WAVEGEN_NORMAL_PWM - Normal pulse-width modulation. The TOP value is PER.
* Waveform output WO[n] is set at the start of the period and cleared on a match
* with a compare channel (n % 4 by default; @see `tcc_set_output_matrix` for other
* options). This mode results in a square wave with a frequency defined by the
* PER register, and a duty cycle defined by the CCn register.
*/
void tcc_set_wavegen(uint8_t instance, tcc_wavegen_t mode);
/**
* @brief Sets the output matrix for the TCC.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @param mode The output matrix mode to use. One of:
* * TCC_OUTPUT_MATRIX_MODULO_4 - Compare channels CC0-CC3 are distributed across
* waveform outputs WO[0]-WO[7] in a modulo 4 fashion, such that CC0 controls WO[0]
* and WO[4], CC1 controls WO[1] and WO[5], CC2 controls WO[2] and WO[6], and CC3
* controls WO[3] and WO[7].
* * TCC_OUTPUT_MATRIX_MODULO_2 - Compare channels CC0-CC1 are distributed across
* waveform outputs WO[0]-WO[7] in a modulo 2 fashion, such that CC0 controls WO0,
* WO2, WO4, and WO6, and CC1 controls WO1, WO3, WO5, and WO7.
* * TCC_OUTPUT_MATRIX_ALL_CC0 - Compare channel CC0 controls all waveform outputs.
* * TCC_OUTPUT_MATRIX_WO0_CC0_OTHERS_CC1 - Compare channel CC0 controls waveform
* output WO0, and compare channel CC1 controls all other waveform outputs.
*/
void tcc_set_output_matrix(uint8_t instance, tcc_output_matrix_t mode);
/**
* @brief Sets the polarity of a channel.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @param channel The waveform output channel from 0 to 7.
* @param polarity The polarity to set. One of:
* * TCC_CHANNEL_POLARITY_NORMAL - The output is high when WO[n] is set.
* * TCC_CHANNEL_POLARITY_INVERTED - The output is low when WO[n] is set.
* @details Inverting one of the waveform outputs is useful to drive a device with a differential
* signal; inverting several outputs can be useful if you are driving something whose
* polarity is reversed, like a common anode LED.
*/
void tcc_set_channel_polarity(uint8_t instance, uint8_t channel, tcc_channel_polarity_t polarity);
/** @brief Enables the TCC. Make sure to call tcc_init first to set it up.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
*/
void tcc_enable(uint8_t instance);
/** @brief Checks whether the TCC is enabled.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @return true if the TCC is enabled, false if instance is disabled.
*/
bool tcc_is_enabled(uint8_t instance);
/**
* @brief Sets the period of the TCC.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @param period The period to set.
* @param buffered If true, sets the period in the buffered register, which will be loaded
* at the next UPDATE condition. If false, sets the period directly.
* Note that double buffering is not available on the SAM D11 and SAM D21,
* and a value of true on those platforms will be ignored.
* @details The period is the value that the counter counts up to before resetting. The
* frequency of the timer is determined by the period and the prescaler value.
*/
void tcc_set_period(uint8_t instance, uint32_t period, bool buffered);
/**
* @brief Gets the period of the TCC.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @return The current period of value.
*/
uint32_t tcc_get_period(uint8_t instance);
/**
* @brief Sets the value of a compare channel.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @param channel The compare channel to set, from 0 to 3 (or 0-1 on some TCCs; check
* the data sheet)
* @param buffered If true, sets the CC value in the buffered register, which will be
* loaded at the next UPDATE condition. If false, sets the period directly.
* Note that double buffering is not available on the SAM D11 and SAM D21,
* and a value of true on those platforms will be ignored.
* @param value The value to set the compare channel to. Max 24 bits (16,777,215).
*/
void tcc_set_cc(uint8_t instance, uint8_t channel, uint32_t value, bool buffered);
/**
* @brief Sets the value of the counter.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @param value The value to set the counter to. Max 24 bits (16,777,215).
*/
void tcc_set_count(uint8_t instance, uint32_t value);
/**
* @brief Gets the current value of the counter.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @return The current value of the counter.
*/
uint32_t tcc_get_count(uint8_t instance);
/**
* @brief Issues a STOP command to the TCC.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
* @details When a stop is detected while the counter is running, the counter will
* maintain its current value, and the Stop bit in the Status register
* will be set (STATUS.STOP).
* @note There is a more complex way to set what happens to the waveform outputs
* in a stop condition: you can set values for each waveform in the DRVCTRL's
* Non-Recoverable State Output Enable (DRVCTRL.NREx) and Non- Recoverable State
* Output Value (DRVCTRL.NRVx) bits. This is not currently implemented; see
* the data sheet for more information.
*/
void tcc_stop(uint8_t instance);
/**
* @brief Issues a RETRIGGER command to the TCC.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
*/
void tcc_retrigger(uint8_t instance);
/**
* @brief Issues an UPDATE command to the TCC.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
*/
void tcc_update(uint8_t instance);
/** @brief Disables the TCC, but retains all its settings.
* @param instance The TCC peripheral instance as numbered in the data sheet, or 0.
*/
void tcc_disable(uint8_t instance);

67
dummy/peripherals/uart.c Normal file
View File

@ -0,0 +1,67 @@
/*
Bits cribbed from Alex Taradov's BSD-3 licensed UART peripheral,
Copyright (c) 2017-2023, Alex Taradov <alex@taradov.com>. All rights reserved.
Full text available at: https://opensource.org/licenses/BSD-3
Other stuff is MIT-licensed by me, Joey Castillo.
Copyright 2023 Joey Castillo for Oddly Specific Objects.
Published under the standard MIT License.
Full text available at: https://opensource.org/licenses/MIT
*/
#include "pins.h"
#include "system.h"
#include "sercom.h"
#include "uart.h"
#if defined(UART_SERCOM)
bool uart_read_byte(uint8_t *byte) {
return false;
}
void uart_init(uint32_t baud) {
}
void uart_set_run_in_standby(bool run_in_standby) {
}
void uart_enable(void) {
}
void uart_write(uint8_t *data, size_t length) {
}
size_t uart_read(uint8_t *data, size_t max_length) {
return 0;
}
void uart_disable(void) {
}
#endif
void uart_init_instance(uint8_t sercom, uart_txpo_t txpo, uart_rxpo_t rxpo, uint32_t baud) {
}
void uart_set_run_in_standby_instance(uint8_t sercom, bool run_in_standby) {
}
void uart_enable_instance(uint8_t sercom) {
}
void uart_write_instance(uint8_t sercom, uint8_t *data, size_t length) {
}
size_t uart_read_instance(uint8_t sercom, uint8_t *data, size_t max_length) {
return 0;
}
bool uart_read_byte_instance(uint8_t sercom, uint8_t *byte) {
return false;
}
void uart_disable_instance(uint8_t sercom) {
}
void uart_irq_handler(uint8_t sercom) {
}

65
dummy/peripherals/uart.h Normal file
View File

@ -0,0 +1,65 @@
/**
* @file uart.h
* @brief UART Peripheral
*/
#pragma once
#include <stdint.h>
#include <stdbool.h>
#include <stddef.h>
typedef enum {
UART_TXPO_0 = 0,
UART_TXPO_2,
UART_TXPO_0_FLOW_CONTROL,
UART_TXPO_NONE = 0xff
} uart_txpo_t;
typedef enum {
UART_RXPO_0 = 0,
UART_RXPO_1,
UART_RXPO_2,
UART_RXPO_3,
UART_RXPO_NONE = 0xff
} uart_rxpo_t;
void uart_init(uint32_t baud);
void uart_enable(void);
void uart_set_run_in_standby(bool run_in_standby);
void uart_write(uint8_t *data, size_t length);
size_t uart_read(uint8_t *data, size_t max_length);
bool uart_read_byte(uint8_t *byte);
void uart_disable(void);
void uart_init_instance(uint8_t sercom, uart_txpo_t txpo, uart_rxpo_t rxpo, uint32_t baud);
void uart_set_run_in_standby_instance(uint8_t sercom, bool run_in_standby);
void uart_enable_instance(uint8_t sercom);
void uart_write_instance(uint8_t sercom, uint8_t *data, size_t length);
size_t uart_read_instance(uint8_t sercom, uint8_t *data, size_t max_length);
bool uart_read_byte_instance(uint8_t sercom, uint8_t *byte);
void uart_disable_instance(uint8_t sercom);
/**
* @brief UART IRQ handler
* @details Call this function from the IRQ handler for the UART SERCOM.
* For example, if you are using SERCOM5, you would do this:
* `void irq_handler_sercom5(void) { uart_irq_handler(5); }`
* UART transmssion and reception are interrupt driven, and
* nothing will work if this function is not called.
* @param sercom SERCOM number
* @todo Really need to refactor this so it's called from the HAL, not the app.
*/
void uart_irq_handler(uint8_t sercom);

49
dummy/peripherals/usb.c Normal file
View File

@ -0,0 +1,49 @@
/*
* MIT License
*
* Copyright (c) 2022 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
#include "pins.h"
#include "system.h"
#include "usb.h"
#include "tc.h"
#ifdef APP_USES_TINYUSB
void usb_init(void) {
}
void usb_enable(void) {
}
bool usb_is_enabled(void) {
return false;
}
void usb_disable(void) {
}
void irq_handler_usb(void);
void irq_handler_usb(void) {
}
#endif

75
dummy/peripherals/usb.h Normal file
View File

@ -0,0 +1,75 @@
/*
* MIT License
*
* Copyright (c) 2023 Joey Castillo
*
* Permission is hereby granted, free of charge, to any person obtaining a copy
* of this software and associated documentation files (the "Software"), to deal
* in the Software without restriction, including without limitation the rights
* to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
* copies of the Software, and to permit persons to whom the Software is
* furnished to do so, subject to the following conditions:
*
* The above copyright notice and this permission notice shall be included in all
* copies or substantial portions of the Software.
*
* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
* AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
* OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
* SOFTWARE.
*/
// WORK IN PROGRESS, not yet functional.
#ifdef APP_USES_TINYUSB
#pragma once
#include <stdint.h>
#include <stdbool.h>
#include "tusb.h"
/** @brief Initializes the USB preipheral, and assigns the USB pins to their
* relevant functions. In the process, this function also sets up the
* 48 MHz DFLL clock on GCLK1.
*/
void usb_init(void);
/**
* @brief Initializes the TinyUSB stack and enables the USB peripheral.
* @details In order to make use of the tinyUSB stack, there are two additional
* setup steps you must take:
* 1. In your Makefile, set the type and number of TinyUSB device
* classes you intend to use. For example, if you want to use a USB
* mass storage class, you would add `TINYUSB_MSC=1` to your app's
* Makefile. You can also add more than one class, e.g. for two CDC
* interfaces, you would add `TINYUSB_CDC=2`. Available TinyUSB
* classes are:
* * TINYUSB_CDC
* * TINYUSB_MSC
* * TINYUSB_HID
* * TINYUSB_MIDI
* * TINYUSB_VENDOR
* 2. You must also set up your USB device descriptor. This is
* typically done in a `usb_descriptors.c` file. See the usb app
* for an example of how to do this.
* 3. Depending on which classes you enable, you may need to do some
* additional setup. Check out tinyusb's examples for more info.
*/
void usb_enable(void);
/**
* @brief Checks if the USB peripheral is enabled.
* @return true if the USB peripheral is enabled, false otherwise.
*/
bool usb_is_enabled(void);
/**
* @brief Disables the USB peripheral.
* @note Has not been extensively tested, TinyUSB may not like this.
*/
void usb_disable(void);
#endif

43
make.mk
View File

@ -39,6 +39,7 @@ ifeq ($(DETECTED_OS), WINDOWS)
MAKEFLAGS += -j $(NUMBER_OF_PROCESSORS)
endif
ifndef EMSCRIPTEN
CC = arm-none-eabi-gcc
OBJCOPY = arm-none-eabi-objcopy
SIZE = arm-none-eabi-size
@ -64,14 +65,11 @@ LIBS += -lm
INCLUDES += \
-I$(GOSSAMER_PATH)/common/ \
-I$(GOSSAMER_PATH)/peripherals/ \
-I$(GOSSAMER_PATH)/drivers/ \
-I$(GOSSAMER_PATH)/boards/$(BOARD)/ \
-I$(GOSSAMER_PATH)/chips/$(CHIP)/include/ \
SRCS += \
$(GOSSAMER_PATH)/chips/$(CHIP)/startup_$(CHIP).c \
$(GOSSAMER_PATH)/chips/$(CHIP)/system_$(CHIP).c \
$(GOSSAMER_PATH)/main.c \
$(GOSSAMER_PATH)/common/delay.c \
$(GOSSAMER_PATH)/peripherals/adc.c \
$(GOSSAMER_PATH)/peripherals/dac.c \
@ -88,6 +86,45 @@ SRCS += \
$(GOSSAMER_PATH)/peripherals/tc.c \
$(GOSSAMER_PATH)/peripherals/tcc.c \
$(GOSSAMER_PATH)/peripherals/uart.c \
else
BUILD = ./build-sim
CC = emcc
INCLUDES += \
-I$(GOSSAMER_PATH)/dummy/common/ \
-I$(GOSSAMER_PATH)/dummy/peripherals/ \
-I$(GOSSAMER_PATH)/dummy/chips/$(CHIP)/include/ \
SRCS += \
$(GOSSAMER_PATH)/dummy/chips/$(CHIP)/startup_$(CHIP).c \
$(GOSSAMER_PATH)/dummy/chips/$(CHIP)/system_$(CHIP).c \
$(GOSSAMER_PATH)/dummy/common/delay.c \
$(GOSSAMER_PATH)/dummy/peripherals/adc.c \
$(GOSSAMER_PATH)/dummy/peripherals/dac.c \
$(GOSSAMER_PATH)/dummy/peripherals/dma.c \
$(GOSSAMER_PATH)/dummy/peripherals/eic.c \
$(GOSSAMER_PATH)/dummy/peripherals/i2c.c \
$(GOSSAMER_PATH)/dummy/peripherals/i2s.c \
$(GOSSAMER_PATH)/dummy/peripherals/opamp.c \
$(GOSSAMER_PATH)/dummy/peripherals/ptc.c \
$(GOSSAMER_PATH)/dummy/peripherals/rtc.c \
$(GOSSAMER_PATH)/dummy/peripherals/sercom.c \
$(GOSSAMER_PATH)/dummy/peripherals/slcd.c \
$(GOSSAMER_PATH)/dummy/peripherals/spi.c \
$(GOSSAMER_PATH)/dummy/peripherals/tc.c \
$(GOSSAMER_PATH)/dummy/peripherals/tcc.c \
$(GOSSAMER_PATH)/dummy/peripherals/uart.c \
endif
INCLUDES += \
-I$(GOSSAMER_PATH)/drivers/ \
-I$(GOSSAMER_PATH)/boards/$(BOARD)/ \
SRCS += \
$(GOSSAMER_PATH)/main.c \
$(GOSSAMER_PATH)/drivers/gfx/gfx.c \
$(GOSSAMER_PATH)/drivers/gfx/sh1107.c \

View File

@ -6,12 +6,16 @@ SUBMODULES = tinyusb
COBRA = cobra -f
ifndef EMSCRIPTEN
ifeq ($(DFU), 1)
all: $(BUILD)/$(BIN).elf $(BUILD)/$(BIN).hex $(BUILD)/$(BIN).bin $(BUILD)/$(BIN).dfu size
else
all: $(BUILD)/$(BIN).elf $(BUILD)/$(BIN).hex $(BUILD)/$(BIN).bin $(BUILD)/$(BIN).uf2 size
endif
endif
$(BUILD)/$(BIN).elf: $(OBJS)
@echo LD $@
@$(CC) $(LDFLAGS) $(OBJS) $(LIBS) -o $@