- Added support for the IAR compiler on target ARMCM3_EFM32, including demos.
- Added timer deinit call to ARMCM3 demo programs before the bootloader is activated. git-svn-id: https://svn.code.sf.net/p/openblt/code/trunk@31 5dc33758-31d5-4daf-9ae8-b24bf3d40d73
This commit is contained in:
parent
c6d56ca038
commit
89bf013a7b
Binary file not shown.
|
@ -1069,9 +1069,9 @@ FLASH 0x00000000 0x00004000 xr
|
|||
|
||||
Linker script and memory map
|
||||
|
||||
0x00002cc4 __do_debug_operation = __do_debug_operation_bkpt
|
||||
0x00001fe8 __vfprintf = __vfprintf_int
|
||||
0x00002754 __vfscanf = __vfscanf_int
|
||||
0x00002d54 __do_debug_operation = __do_debug_operation_bkpt
|
||||
0x00002078 __vfprintf = __vfprintf_int
|
||||
0x000027e4 __vfscanf = __vfscanf_int
|
||||
0xe000e000 __CM3_System_Control_Space_segment_start__ = 0xe000e000
|
||||
0xe000f000 __CM3_System_Control_Space_segment_end__ = 0xe000f000
|
||||
0x20000000 __RAM_segment_start__ = 0x20000000
|
||||
|
@ -1118,7 +1118,7 @@ Linker script and memory map
|
|||
0x00000001 . = ASSERT (((__init_end__ >= __FLASH_segment_start__) && (__init_end__ <= (__FLASH_segment_start__ + 0x20000))), error: .init is too large to fit in FLASH memory segment)
|
||||
0x0000027c __text_load_start__ = ALIGN (__init_end__, 0x4)
|
||||
|
||||
.text 0x0000027c 0x2a68
|
||||
.text 0x0000027c 0x2af8
|
||||
0x0000027c __text_start__ = .
|
||||
*(.text .text.* .glue_7t .glue_7 .gnu.linkonce.t.* .gcc_except_table .ARM.extab* .gnu.linkonce.armextab.*)
|
||||
.glue_7 0x00000000 0x0 linker stubs
|
||||
|
@ -1335,59 +1335,59 @@ Linker script and memory map
|
|||
.text.SYSTEM_ChipRevisionGet
|
||||
0x00001dcc 0x24 THUMB Flash Debug/../../obj/efm32_system.o
|
||||
0x00001dcc SYSTEM_ChipRevisionGet
|
||||
.text.main 0x00001df0 0x1f8 THUMB Flash Debug/../../obj/main.o
|
||||
.text.main 0x00001df0 0x288 THUMB Flash Debug/../../obj/main.o
|
||||
0x00001df0 main
|
||||
.text.libc.__vfprintf_int
|
||||
0x00001fe8 0x5d0 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfprintf_int.o)
|
||||
0x00001fe8 __vfprintf_int
|
||||
0x00002078 0x5d0 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfprintf_int.o)
|
||||
0x00002078 __vfprintf_int
|
||||
.text.libc.__ungetc
|
||||
0x000025b8 0x20 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
0x00002648 0x20 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
.text.libc.rd_int
|
||||
0x000025d8 0x17c C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
0x00002668 0x17c C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
.text.libc.__vfscanf_int
|
||||
0x00002754 0x3ec C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
0x00002754 __vfscanf_int
|
||||
0x000027e4 0x3ec C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
0x000027e4 __vfscanf_int
|
||||
.text.libc.__getc
|
||||
0x00002b40 0x28 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002b40 __getc
|
||||
0x00002bd0 0x28 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002bd0 __getc
|
||||
.text.libc.__putc
|
||||
0x00002b68 0x38 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002b68 __putc
|
||||
0x00002bf8 0x38 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002bf8 __putc
|
||||
.text.libc.__print_padding
|
||||
0x00002ba0 0x24 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002ba0 __print_padding
|
||||
0x00002c30 0x24 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002c30 __print_padding
|
||||
.text.libc.__pre_padding
|
||||
0x00002bc4 0x1c C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002bc4 __pre_padding
|
||||
0x00002c54 0x1c C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002c54 __pre_padding
|
||||
.text.libc.isupper
|
||||
0x00002be0 0x10 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002be0 isupper
|
||||
0x00002c70 0x10 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002c70 isupper
|
||||
.text.libc.islower
|
||||
0x00002bf0 0x10 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002bf0 islower
|
||||
0x00002c80 0x10 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002c80 islower
|
||||
.text.libc.isdigit
|
||||
0x00002c00 0x10 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002c00 isdigit
|
||||
0x00002c90 0x10 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002c90 isdigit
|
||||
.text.libc.__digit
|
||||
0x00002c10 0x3c C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002c10 __digit
|
||||
0x00002ca0 0x3c C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002ca0 __digit
|
||||
.text.libc.isspace
|
||||
0x00002c4c 0x18 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002c4c isspace
|
||||
0x00002cdc 0x18 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002cdc isspace
|
||||
.text.libc.strlen
|
||||
0x00002c64 0x60 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2_asm.o)
|
||||
0x00002c64 strlen
|
||||
0x00002cf4 0x60 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2_asm.o)
|
||||
0x00002cf4 strlen
|
||||
.text.libdebugio_bkpt.__do_debug_operation_bkpt
|
||||
0x00002cc4 0x18 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libdebugio_v7m_t_le.a(libdebugio_asm.o)
|
||||
0x00002cc4 __do_debug_operation_bkpt
|
||||
0x00002d54 0x18 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libdebugio_v7m_t_le.a(libdebugio_asm.o)
|
||||
0x00002d54 __do_debug_operation_bkpt
|
||||
.text.libc.__debug_io_lock
|
||||
0x00002cdc 0x4 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
0x00002cdc __debug_io_lock
|
||||
0x00002d6c 0x4 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
0x00002d6c __debug_io_lock
|
||||
.text.libc.__debug_io_unlock
|
||||
0x00002ce0 0x4 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
0x00002ce0 __debug_io_unlock
|
||||
0x00002ce4 __text_end__ = (__text_start__ + SIZEOF (.text))
|
||||
0x00002ce4 __text_load_end__ = __text_end__
|
||||
0x00002d70 0x4 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
0x00002d70 __debug_io_unlock
|
||||
0x00002d74 __text_end__ = (__text_start__ + SIZEOF (.text))
|
||||
0x00002d74 __text_load_end__ = __text_end__
|
||||
|
||||
.vfp11_veneer 0x00000000 0x0
|
||||
.vfp11_veneer 0x00000000 0x0 linker stubs
|
||||
|
@ -1395,81 +1395,81 @@ Linker script and memory map
|
|||
.v4_bx 0x00000000 0x0
|
||||
.v4_bx 0x00000000 0x0 linker stubs
|
||||
0x00000001 . = ASSERT (((__text_end__ >= __FLASH_segment_start__) && (__text_end__ <= (__FLASH_segment_start__ + 0x20000))), error: .text is too large to fit in FLASH memory segment)
|
||||
0x00002ce4 __dtors_load_start__ = ALIGN (__text_end__, 0x4)
|
||||
0x00002d74 __dtors_load_start__ = ALIGN (__text_end__, 0x4)
|
||||
|
||||
.dtors 0x00002ce4 0x0
|
||||
0x00002ce4 __dtors_start__ = .
|
||||
.dtors 0x00002d74 0x0
|
||||
0x00002d74 __dtors_start__ = .
|
||||
*(SORT(.dtors.*))
|
||||
*(.dtors)
|
||||
*(.fini_array .fini_array.*)
|
||||
0x00002ce4 __dtors_end__ = (__dtors_start__ + SIZEOF (.dtors))
|
||||
0x00002ce4 __dtors_load_end__ = __dtors_end__
|
||||
0x00002d74 __dtors_end__ = (__dtors_start__ + SIZEOF (.dtors))
|
||||
0x00002d74 __dtors_load_end__ = __dtors_end__
|
||||
0x00000001 . = ASSERT (((__dtors_end__ >= __FLASH_segment_start__) && (__dtors_end__ <= (__FLASH_segment_start__ + 0x20000))), error: .dtors is too large to fit in FLASH memory segment)
|
||||
0x00002ce4 __ctors_load_start__ = ALIGN (__dtors_end__, 0x4)
|
||||
0x00002d74 __ctors_load_start__ = ALIGN (__dtors_end__, 0x4)
|
||||
|
||||
.ctors 0x00002ce4 0x0
|
||||
0x00002ce4 __ctors_start__ = .
|
||||
.ctors 0x00002d74 0x0
|
||||
0x00002d74 __ctors_start__ = .
|
||||
*(SORT(.ctors.*))
|
||||
*(.ctors)
|
||||
*(.init_array .init_array.*)
|
||||
0x00002ce4 __ctors_end__ = (__ctors_start__ + SIZEOF (.ctors))
|
||||
0x00002ce4 __ctors_load_end__ = __ctors_end__
|
||||
0x00002d74 __ctors_end__ = (__ctors_start__ + SIZEOF (.ctors))
|
||||
0x00002d74 __ctors_load_end__ = __ctors_end__
|
||||
0x00000001 . = ASSERT (((__ctors_end__ >= __FLASH_segment_start__) && (__ctors_end__ <= (__FLASH_segment_start__ + 0x20000))), error: .ctors is too large to fit in FLASH memory segment)
|
||||
0x00002ce4 __rodata_load_start__ = ALIGN (__ctors_end__, 0x4)
|
||||
0x00002d74 __rodata_load_start__ = ALIGN (__ctors_end__, 0x4)
|
||||
|
||||
.rodata 0x00002ce4 0x20c
|
||||
0x00002ce4 __rodata_start__ = .
|
||||
.rodata 0x00002d74 0x20c
|
||||
0x00002d74 __rodata_start__ = .
|
||||
*(.rodata .rodata.* .gnu.linkonce.r.*)
|
||||
.rodata.str1.4
|
||||
0x00002ce4 0x98 THUMB Flash Debug/../../obj/vectors.o
|
||||
0x00002d74 0x98 THUMB Flash Debug/../../obj/vectors.o
|
||||
.rodata.flashLayout
|
||||
0x00002d7c 0xa8 THUMB Flash Debug/../../obj/flash.o
|
||||
.rodata 0x00002e24 0x18 THUMB Flash Debug/../../obj/uart.o
|
||||
0x00002e0c 0xa8 THUMB Flash Debug/../../obj/flash.o
|
||||
.rodata 0x00002eb4 0x18 THUMB Flash Debug/../../obj/uart.o
|
||||
.rodata.str1.4
|
||||
0x00002e3c 0x8c THUMB Flash Debug/../../obj/uart.o
|
||||
0x00002ecc 0x8c THUMB Flash Debug/../../obj/uart.o
|
||||
.rodata.xcpStationId
|
||||
0x00002ec8 0x8 THUMB Flash Debug/../../obj/xcp.o
|
||||
0x00002f58 0x8 THUMB Flash Debug/../../obj/xcp.o
|
||||
.rodata.libc.__hex_lc
|
||||
0x00002ed0 0x10 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002ed0 __hex_lc
|
||||
0x00002f60 0x10 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002f60 __hex_lc
|
||||
.rodata.libc.__hex_uc
|
||||
0x00002ee0 0x10 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002ee0 __hex_uc
|
||||
0x00002ef0 __rodata_end__ = (__rodata_start__ + SIZEOF (.rodata))
|
||||
0x00002ef0 __rodata_load_end__ = __rodata_end__
|
||||
0x00002f70 0x10 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
0x00002f70 __hex_uc
|
||||
0x00002f80 __rodata_end__ = (__rodata_start__ + SIZEOF (.rodata))
|
||||
0x00002f80 __rodata_load_end__ = __rodata_end__
|
||||
0x00000001 . = ASSERT (((__rodata_end__ >= __FLASH_segment_start__) && (__rodata_end__ <= (__FLASH_segment_start__ + 0x20000))), error: .rodata is too large to fit in FLASH memory segment)
|
||||
0x00002ef0 __ARM.exidx_load_start__ = ALIGN (__rodata_end__, 0x4)
|
||||
0x00002f80 __ARM.exidx_load_start__ = ALIGN (__rodata_end__, 0x4)
|
||||
|
||||
.ARM.exidx 0x00002ef0 0x0
|
||||
0x00002ef0 __ARM.exidx_start__ = .
|
||||
0x00002ef0 __exidx_start = __ARM.exidx_start__
|
||||
.ARM.exidx 0x00002f80 0x0
|
||||
0x00002f80 __ARM.exidx_start__ = .
|
||||
0x00002f80 __exidx_start = __ARM.exidx_start__
|
||||
*(.ARM.exidx .ARM.exidx.*)
|
||||
0x00002ef0 __ARM.exidx_end__ = (__ARM.exidx_start__ + SIZEOF (.ARM.exidx))
|
||||
0x00002ef0 __exidx_end = __ARM.exidx_end__
|
||||
0x00002ef0 __ARM.exidx_load_end__ = __ARM.exidx_end__
|
||||
0x00002f80 __ARM.exidx_end__ = (__ARM.exidx_start__ + SIZEOF (.ARM.exidx))
|
||||
0x00002f80 __exidx_end = __ARM.exidx_end__
|
||||
0x00002f80 __ARM.exidx_load_end__ = __ARM.exidx_end__
|
||||
0x00000001 . = ASSERT (((__ARM.exidx_end__ >= __FLASH_segment_start__) && (__ARM.exidx_end__ <= (__FLASH_segment_start__ + 0x20000))), error: .ARM.exidx is too large to fit in FLASH memory segment)
|
||||
0x00002ef0 __fast_load_start__ = ALIGN (__ARM.exidx_end__, 0x4)
|
||||
0x00002f80 __fast_load_start__ = ALIGN (__ARM.exidx_end__, 0x4)
|
||||
|
||||
.fast 0x20000000 0x214 load address 0x00002ef0
|
||||
.fast 0x20000000 0x214 load address 0x00002f80
|
||||
0x20000000 __fast_start__ = .
|
||||
*(.fast .fast.*)
|
||||
.fast 0x20000000 0x214 THUMB Flash Debug/../../obj/efm32_msc.o
|
||||
0x20000000 MSC_ErasePage
|
||||
0x200000c4 MSC_WriteWord
|
||||
0x20000214 __fast_end__ = (__fast_start__ + SIZEOF (.fast))
|
||||
0x00003104 __fast_load_end__ = (__fast_load_start__ + SIZEOF (.fast))
|
||||
0x00003194 __fast_load_end__ = (__fast_load_start__ + SIZEOF (.fast))
|
||||
0x00000001 . = ASSERT ((((__fast_load_start__ + SIZEOF (.fast)) >= __FLASH_segment_start__) && ((__fast_load_start__ + SIZEOF (.fast)) <= (__FLASH_segment_start__ + 0x20000))), error: .fast is too large to fit in FLASH memory segment)
|
||||
|
||||
.fast_run 0x20000000 0x214 load address 0x00002ef0
|
||||
.fast_run 0x20000000 0x214 load address 0x00002f80
|
||||
0x20000000 __fast_run_start__ = .
|
||||
0x20000214 . = MAX ((__fast_run_start__ + SIZEOF (.fast)), .)
|
||||
*fill* 0x20000000 0x214 00
|
||||
0x20000214 __fast_run_end__ = (__fast_run_start__ + SIZEOF (.fast_run))
|
||||
0x20000214 __fast_run_load_end__ = __fast_run_end__
|
||||
0x00000001 . = ASSERT (((__fast_run_end__ >= __RAM_segment_start__) && (__fast_run_end__ <= (__RAM_segment_start__ + 0x4000))), error: .fast_run is too large to fit in RAM memory segment)
|
||||
0x00003104 __data_load_start__ = ALIGN ((__fast_load_start__ + SIZEOF (.fast)), 0x4)
|
||||
0x00003194 __data_load_start__ = ALIGN ((__fast_load_start__ + SIZEOF (.fast)), 0x4)
|
||||
|
||||
.data 0x20000214 0x8 load address 0x00003104
|
||||
.data 0x20000214 0x8 load address 0x00003194
|
||||
0x20000214 __data_start__ = .
|
||||
*(.data .data.* .gnu.linkonce.d.*)
|
||||
.data.SystemLFXOClock
|
||||
|
@ -1477,10 +1477,10 @@ Linker script and memory map
|
|||
.data.SystemHFXOClock
|
||||
0x20000218 0x4 THUMB Flash Debug/../../obj/system_efm32.o
|
||||
0x2000021c __data_end__ = (__data_start__ + SIZEOF (.data))
|
||||
0x0000310c __data_load_end__ = (__data_load_start__ + SIZEOF (.data))
|
||||
0x0000319c __data_load_end__ = (__data_load_start__ + SIZEOF (.data))
|
||||
0x00000001 . = ASSERT ((((__data_load_start__ + SIZEOF (.data)) >= __FLASH_segment_start__) && ((__data_load_start__ + SIZEOF (.data)) <= (__FLASH_segment_start__ + 0x20000))), error: .data is too large to fit in FLASH memory segment)
|
||||
|
||||
.data_run 0x20000214 0x8 load address 0x00003104
|
||||
.data_run 0x20000214 0x8 load address 0x00003194
|
||||
0x20000214 __data_run_start__ = .
|
||||
0x2000021c . = MAX ((__data_run_start__ + SIZEOF (.data)), .)
|
||||
*fill* 0x20000214 0x8 00
|
||||
|
@ -1576,14 +1576,14 @@ Linker script and memory map
|
|||
0x20000894 __tbss_end__ = (__tbss_start__ + SIZEOF (.tbss))
|
||||
0x20000894 __tbss_load_end__ = __tbss_end__
|
||||
0x00000001 . = ASSERT (((__tbss_end__ >= __RAM_segment_start__) && (__tbss_end__ <= (__RAM_segment_start__ + 0x4000))), error: .tbss is too large to fit in RAM memory segment)
|
||||
0x0000310c __tdata_load_start__ = ALIGN ((__data_load_start__ + SIZEOF (.data)), 0x4)
|
||||
0x0000319c __tdata_load_start__ = ALIGN ((__data_load_start__ + SIZEOF (.data)), 0x4)
|
||||
|
||||
.tdata 0x20000894 0x0 load address 0x0000310c
|
||||
.tdata 0x20000894 0x0 load address 0x0000319c
|
||||
0x20000894 __tdata_start__ = .
|
||||
*(.tdata .tdata.*)
|
||||
0x20000894 __tdata_end__ = (__tdata_start__ + SIZEOF (.tdata))
|
||||
0x0000310c __tdata_load_end__ = (__tdata_load_start__ + SIZEOF (.tdata))
|
||||
0x0000310c __FLASH_segment_used_end__ = (ALIGN ((__data_load_start__ + SIZEOF (.data)), 0x4) + SIZEOF (.tdata))
|
||||
0x0000319c __tdata_load_end__ = (__tdata_load_start__ + SIZEOF (.tdata))
|
||||
0x0000319c __FLASH_segment_used_end__ = (ALIGN ((__data_load_start__ + SIZEOF (.data)), 0x4) + SIZEOF (.tdata))
|
||||
0x00000001 . = ASSERT ((((__tdata_load_start__ + SIZEOF (.tdata)) >= __FLASH_segment_start__) && ((__tdata_load_start__ + SIZEOF (.tdata)) <= (__FLASH_segment_start__ + 0x20000))), error: .tdata is too large to fit in FLASH memory segment)
|
||||
|
||||
.tdata_run 0x20000894 0x0
|
||||
|
@ -1812,160 +1812,160 @@ OUTPUT(THUMB Flash Debug/../../bin/openbtl_olimex_efm32g880.elf elf32-littlearm)
|
|||
.comment 0x00000000 0x12 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
.comment 0x00000000 0x12 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
|
||||
.debug_line 0x00000000 0x8c64
|
||||
.debug_line 0x00000000 0x8c72
|
||||
.debug_line 0x00000000 0x170 THUMB Flash Debug/../../obj/cstart.o
|
||||
.debug_line 0x00000170 0x157 THUMB Flash Debug/../../obj/vectors.o
|
||||
.debug_line 0x000002c7 0xfc THUMB Flash Debug/../../obj/cpu.o
|
||||
.debug_line 0x000003c3 0x3e2 THUMB Flash Debug/../../obj/flash.o
|
||||
.debug_line 0x000007a5 0x117 THUMB Flash Debug/../../obj/nvm.o
|
||||
.debug_line 0x000008bc 0x115 THUMB Flash Debug/../../obj/timer.o
|
||||
.debug_line 0x000009d1 0x3a0 THUMB Flash Debug/../../obj/uart.o
|
||||
.debug_line 0x00000d71 0x145 THUMB Flash Debug/../../obj/assert.o
|
||||
.debug_line 0x00000eb6 0x15b THUMB Flash Debug/../../obj/backdoor.o
|
||||
.debug_line 0x00001011 0xc5 THUMB Flash Debug/../../obj/boot.o
|
||||
.debug_line 0x000010d6 0x1c0 THUMB Flash Debug/../../obj/com.o
|
||||
.debug_line 0x00001296 0xbd THUMB Flash Debug/../../obj/cop.o
|
||||
.debug_line 0x00001353 0x23e THUMB Flash Debug/../../obj/xcp.o
|
||||
.debug_line 0x00001591 0x1d THUMB Flash Debug/../../obj/core_cm3.o
|
||||
.debug_line 0x000015ae 0x28f THUMB Flash Debug/../../obj/system_efm32.o
|
||||
.debug_line 0x0000183d 0x3a8 THUMB Flash Debug/../../obj/efm32_acmp.o
|
||||
.debug_line 0x00001be5 0x3cb THUMB Flash Debug/../../obj/efm32_adc.o
|
||||
.debug_line 0x00001fb0 0xb4a THUMB Flash Debug/../../obj/efm32_aes.o
|
||||
.debug_line 0x00002afa 0x0 THUMB Flash Debug/../../obj/efm32_assert.o
|
||||
.debug_line 0x00002afa 0x68d THUMB Flash Debug/../../obj/efm32_cmu.o
|
||||
.debug_line 0x00003187 0x38a THUMB Flash Debug/../../obj/efm32_dac.o
|
||||
.debug_line 0x00003511 0x311 THUMB Flash Debug/../../obj/efm32_dbg.o
|
||||
.debug_line 0x00003822 0x4af THUMB Flash Debug/../../obj/efm32_dma.o
|
||||
.debug_line 0x00003cd1 0x412 THUMB Flash Debug/../../obj/efm32_ebi.o
|
||||
.debug_line 0x000040e3 0x3be THUMB Flash Debug/../../obj/efm32_emu.o
|
||||
.debug_line 0x000044a1 0x412 THUMB Flash Debug/../../obj/efm32_gpio.o
|
||||
.debug_line 0x000048b3 0x481 THUMB Flash Debug/../../obj/efm32_i2c.o
|
||||
.debug_line 0x00004d34 0x213 THUMB Flash Debug/../../obj/efm32_int.o
|
||||
.debug_line 0x00004f47 0x430 THUMB Flash Debug/../../obj/efm32_lcd.o
|
||||
.debug_line 0x00005377 0x107 THUMB Flash Debug/../../obj/efm32_lesense.o
|
||||
.debug_line 0x0000547e 0x3d7 THUMB Flash Debug/../../obj/efm32_letimer.o
|
||||
.debug_line 0x00005855 0x40e THUMB Flash Debug/../../obj/efm32_leuart.o
|
||||
.debug_line 0x00005c63 0x23a THUMB Flash Debug/../../obj/efm32_mpu.o
|
||||
.debug_line 0x00005e9d 0x36c THUMB Flash Debug/../../obj/efm32_msc.o
|
||||
.debug_line 0x00006209 0x107 THUMB Flash Debug/../../obj/efm32_opamp.o
|
||||
.debug_line 0x00006310 0x447 THUMB Flash Debug/../../obj/efm32_pcnt.o
|
||||
.debug_line 0x00006757 0x2cf THUMB Flash Debug/../../obj/efm32_prs.o
|
||||
.debug_line 0x00006a26 0x331 THUMB Flash Debug/../../obj/efm32_rmu.o
|
||||
.debug_line 0x00006d57 0x38c THUMB Flash Debug/../../obj/efm32_rtc.o
|
||||
.debug_line 0x000070e3 0x308 THUMB Flash Debug/../../obj/efm32_system.o
|
||||
.debug_line 0x000073eb 0x36e THUMB Flash Debug/../../obj/efm32_timer.o
|
||||
.debug_line 0x00007759 0x49f THUMB Flash Debug/../../obj/efm32_usart.o
|
||||
.debug_line 0x00007bf8 0x32f THUMB Flash Debug/../../obj/efm32_vcmp.o
|
||||
.debug_line 0x00007f27 0x34f THUMB Flash Debug/../../obj/efm32_wdog.o
|
||||
.debug_line 0x00008276 0x1d THUMB Flash Debug/../../obj/hooks.o
|
||||
.debug_line 0x00008293 0x325 THUMB Flash Debug/../../obj/main.o
|
||||
.debug_line 0x000085b8 0x75 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfprintf_int.o)
|
||||
.debug_line 0x0000862d 0x74 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
.debug_line 0x000086a1 0x54f C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
.debug_line 0x00008bf0 0x74 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
.debug_line 0x000003c3 0x3e6 THUMB Flash Debug/../../obj/flash.o
|
||||
.debug_line 0x000007a9 0x117 THUMB Flash Debug/../../obj/nvm.o
|
||||
.debug_line 0x000008c0 0x115 THUMB Flash Debug/../../obj/timer.o
|
||||
.debug_line 0x000009d5 0x3a0 THUMB Flash Debug/../../obj/uart.o
|
||||
.debug_line 0x00000d75 0x145 THUMB Flash Debug/../../obj/assert.o
|
||||
.debug_line 0x00000eba 0x15b THUMB Flash Debug/../../obj/backdoor.o
|
||||
.debug_line 0x00001015 0xc5 THUMB Flash Debug/../../obj/boot.o
|
||||
.debug_line 0x000010da 0x1c0 THUMB Flash Debug/../../obj/com.o
|
||||
.debug_line 0x0000129a 0xbd THUMB Flash Debug/../../obj/cop.o
|
||||
.debug_line 0x00001357 0x23e THUMB Flash Debug/../../obj/xcp.o
|
||||
.debug_line 0x00001595 0x1d THUMB Flash Debug/../../obj/core_cm3.o
|
||||
.debug_line 0x000015b2 0x28f THUMB Flash Debug/../../obj/system_efm32.o
|
||||
.debug_line 0x00001841 0x3a8 THUMB Flash Debug/../../obj/efm32_acmp.o
|
||||
.debug_line 0x00001be9 0x3cb THUMB Flash Debug/../../obj/efm32_adc.o
|
||||
.debug_line 0x00001fb4 0xb4a THUMB Flash Debug/../../obj/efm32_aes.o
|
||||
.debug_line 0x00002afe 0x0 THUMB Flash Debug/../../obj/efm32_assert.o
|
||||
.debug_line 0x00002afe 0x68d THUMB Flash Debug/../../obj/efm32_cmu.o
|
||||
.debug_line 0x0000318b 0x38a THUMB Flash Debug/../../obj/efm32_dac.o
|
||||
.debug_line 0x00003515 0x311 THUMB Flash Debug/../../obj/efm32_dbg.o
|
||||
.debug_line 0x00003826 0x4af THUMB Flash Debug/../../obj/efm32_dma.o
|
||||
.debug_line 0x00003cd5 0x412 THUMB Flash Debug/../../obj/efm32_ebi.o
|
||||
.debug_line 0x000040e7 0x3be THUMB Flash Debug/../../obj/efm32_emu.o
|
||||
.debug_line 0x000044a5 0x412 THUMB Flash Debug/../../obj/efm32_gpio.o
|
||||
.debug_line 0x000048b7 0x481 THUMB Flash Debug/../../obj/efm32_i2c.o
|
||||
.debug_line 0x00004d38 0x213 THUMB Flash Debug/../../obj/efm32_int.o
|
||||
.debug_line 0x00004f4b 0x430 THUMB Flash Debug/../../obj/efm32_lcd.o
|
||||
.debug_line 0x0000537b 0x107 THUMB Flash Debug/../../obj/efm32_lesense.o
|
||||
.debug_line 0x00005482 0x3d7 THUMB Flash Debug/../../obj/efm32_letimer.o
|
||||
.debug_line 0x00005859 0x40e THUMB Flash Debug/../../obj/efm32_leuart.o
|
||||
.debug_line 0x00005c67 0x23a THUMB Flash Debug/../../obj/efm32_mpu.o
|
||||
.debug_line 0x00005ea1 0x36c THUMB Flash Debug/../../obj/efm32_msc.o
|
||||
.debug_line 0x0000620d 0x107 THUMB Flash Debug/../../obj/efm32_opamp.o
|
||||
.debug_line 0x00006314 0x447 THUMB Flash Debug/../../obj/efm32_pcnt.o
|
||||
.debug_line 0x0000675b 0x2cf THUMB Flash Debug/../../obj/efm32_prs.o
|
||||
.debug_line 0x00006a2a 0x331 THUMB Flash Debug/../../obj/efm32_rmu.o
|
||||
.debug_line 0x00006d5b 0x38c THUMB Flash Debug/../../obj/efm32_rtc.o
|
||||
.debug_line 0x000070e7 0x308 THUMB Flash Debug/../../obj/efm32_system.o
|
||||
.debug_line 0x000073ef 0x36e THUMB Flash Debug/../../obj/efm32_timer.o
|
||||
.debug_line 0x0000775d 0x49f THUMB Flash Debug/../../obj/efm32_usart.o
|
||||
.debug_line 0x00007bfc 0x32f THUMB Flash Debug/../../obj/efm32_vcmp.o
|
||||
.debug_line 0x00007f2b 0x34f THUMB Flash Debug/../../obj/efm32_wdog.o
|
||||
.debug_line 0x0000827a 0x1d THUMB Flash Debug/../../obj/hooks.o
|
||||
.debug_line 0x00008297 0x32f THUMB Flash Debug/../../obj/main.o
|
||||
.debug_line 0x000085c6 0x75 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfprintf_int.o)
|
||||
.debug_line 0x0000863b 0x74 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
.debug_line 0x000086af 0x54f C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
.debug_line 0x00008bfe 0x74 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
|
||||
.debug_info 0x00000000 0xf371
|
||||
.debug_info 0x00000000 0xf367
|
||||
.debug_info 0x00000000 0x120 THUMB Flash Debug/../../obj/cstart.o
|
||||
.debug_info 0x00000120 0xf1 THUMB Flash Debug/../../obj/vectors.o
|
||||
.debug_info 0x00000211 0x13a THUMB Flash Debug/../../obj/cpu.o
|
||||
.debug_info 0x0000034b 0x67d THUMB Flash Debug/../../obj/flash.o
|
||||
.debug_info 0x000009c8 0x15e THUMB Flash Debug/../../obj/nvm.o
|
||||
.debug_info 0x00000b26 0x144 THUMB Flash Debug/../../obj/timer.o
|
||||
.debug_info 0x00000c6a 0x6ba THUMB Flash Debug/../../obj/uart.o
|
||||
.debug_info 0x00001324 0xe4 THUMB Flash Debug/../../obj/assert.o
|
||||
.debug_info 0x00001408 0xa4 THUMB Flash Debug/../../obj/backdoor.o
|
||||
.debug_info 0x000014ac 0x88 THUMB Flash Debug/../../obj/boot.o
|
||||
.debug_info 0x00001534 0x1b4 THUMB Flash Debug/../../obj/com.o
|
||||
.debug_info 0x000016e8 0x86 THUMB Flash Debug/../../obj/cop.o
|
||||
.debug_info 0x0000176e 0x60b THUMB Flash Debug/../../obj/xcp.o
|
||||
.debug_info 0x00001d79 0x5a THUMB Flash Debug/../../obj/core_cm3.o
|
||||
.debug_info 0x00001dd3 0x429 THUMB Flash Debug/../../obj/system_efm32.o
|
||||
.debug_info 0x000021fc 0x5f6 THUMB Flash Debug/../../obj/efm32_acmp.o
|
||||
.debug_info 0x000027f2 0xa5b THUMB Flash Debug/../../obj/efm32_adc.o
|
||||
.debug_info 0x0000324d 0x156e THUMB Flash Debug/../../obj/efm32_aes.o
|
||||
.debug_info 0x000047bb 0xf7b THUMB Flash Debug/../../obj/efm32_cmu.o
|
||||
.debug_info 0x00005736 0x809 THUMB Flash Debug/../../obj/efm32_dac.o
|
||||
.debug_info 0x00005f3f 0x410 THUMB Flash Debug/../../obj/efm32_dbg.o
|
||||
.debug_info 0x0000634f 0x10f7 THUMB Flash Debug/../../obj/efm32_dma.o
|
||||
.debug_info 0x00007446 0x913 THUMB Flash Debug/../../obj/efm32_ebi.o
|
||||
.debug_info 0x00007d59 0x680 THUMB Flash Debug/../../obj/efm32_emu.o
|
||||
.debug_info 0x000083d9 0x7cc THUMB Flash Debug/../../obj/efm32_gpio.o
|
||||
.debug_info 0x00008ba5 0x84a THUMB Flash Debug/../../obj/efm32_i2c.o
|
||||
.debug_info 0x000093ef 0xb0 THUMB Flash Debug/../../obj/efm32_int.o
|
||||
.debug_info 0x0000949f 0xad2 THUMB Flash Debug/../../obj/efm32_lcd.o
|
||||
.debug_info 0x00009f71 0x86 THUMB Flash Debug/../../obj/efm32_lesense.o
|
||||
.debug_info 0x00009ff7 0x613 THUMB Flash Debug/../../obj/efm32_letimer.o
|
||||
.debug_info 0x0000a60a 0x7d4 THUMB Flash Debug/../../obj/efm32_leuart.o
|
||||
.debug_info 0x0000adde 0x33f THUMB Flash Debug/../../obj/efm32_mpu.o
|
||||
.debug_info 0x0000b11d 0x2b3 THUMB Flash Debug/../../obj/efm32_msc.o
|
||||
.debug_info 0x0000b3d0 0x86 THUMB Flash Debug/../../obj/efm32_opamp.o
|
||||
.debug_info 0x0000b456 0x86a THUMB Flash Debug/../../obj/efm32_pcnt.o
|
||||
.debug_info 0x0000bcc0 0x1bf THUMB Flash Debug/../../obj/efm32_prs.o
|
||||
.debug_info 0x0000be7f 0x2f4 THUMB Flash Debug/../../obj/efm32_rmu.o
|
||||
.debug_info 0x0000c173 0x3b9 THUMB Flash Debug/../../obj/efm32_rtc.o
|
||||
.debug_info 0x0000c52c 0x242 THUMB Flash Debug/../../obj/efm32_system.o
|
||||
.debug_info 0x0000c76e 0x700 THUMB Flash Debug/../../obj/efm32_timer.o
|
||||
.debug_info 0x0000ce6e 0xafb THUMB Flash Debug/../../obj/efm32_usart.o
|
||||
.debug_info 0x0000d969 0x2fc THUMB Flash Debug/../../obj/efm32_vcmp.o
|
||||
.debug_info 0x0000dc65 0x39a THUMB Flash Debug/../../obj/efm32_wdog.o
|
||||
.debug_info 0x0000dfff 0x5a THUMB Flash Debug/../../obj/hooks.o
|
||||
.debug_info 0x0000e059 0x5d8 THUMB Flash Debug/../../obj/main.o
|
||||
.debug_info 0x0000e631 0x36 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfprintf_int.o)
|
||||
.debug_info 0x0000e667 0x65 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
.debug_info 0x0000e6cc 0xbd8 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
.debug_info 0x0000f2a4 0xcd C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
.debug_info 0x0000034b 0x673 THUMB Flash Debug/../../obj/flash.o
|
||||
.debug_info 0x000009be 0x15e THUMB Flash Debug/../../obj/nvm.o
|
||||
.debug_info 0x00000b1c 0x144 THUMB Flash Debug/../../obj/timer.o
|
||||
.debug_info 0x00000c60 0x6ba THUMB Flash Debug/../../obj/uart.o
|
||||
.debug_info 0x0000131a 0xe4 THUMB Flash Debug/../../obj/assert.o
|
||||
.debug_info 0x000013fe 0xa4 THUMB Flash Debug/../../obj/backdoor.o
|
||||
.debug_info 0x000014a2 0x88 THUMB Flash Debug/../../obj/boot.o
|
||||
.debug_info 0x0000152a 0x1b4 THUMB Flash Debug/../../obj/com.o
|
||||
.debug_info 0x000016de 0x86 THUMB Flash Debug/../../obj/cop.o
|
||||
.debug_info 0x00001764 0x60b THUMB Flash Debug/../../obj/xcp.o
|
||||
.debug_info 0x00001d6f 0x5a THUMB Flash Debug/../../obj/core_cm3.o
|
||||
.debug_info 0x00001dc9 0x429 THUMB Flash Debug/../../obj/system_efm32.o
|
||||
.debug_info 0x000021f2 0x5f6 THUMB Flash Debug/../../obj/efm32_acmp.o
|
||||
.debug_info 0x000027e8 0xa5b THUMB Flash Debug/../../obj/efm32_adc.o
|
||||
.debug_info 0x00003243 0x156e THUMB Flash Debug/../../obj/efm32_aes.o
|
||||
.debug_info 0x000047b1 0xf7b THUMB Flash Debug/../../obj/efm32_cmu.o
|
||||
.debug_info 0x0000572c 0x809 THUMB Flash Debug/../../obj/efm32_dac.o
|
||||
.debug_info 0x00005f35 0x410 THUMB Flash Debug/../../obj/efm32_dbg.o
|
||||
.debug_info 0x00006345 0x10f7 THUMB Flash Debug/../../obj/efm32_dma.o
|
||||
.debug_info 0x0000743c 0x913 THUMB Flash Debug/../../obj/efm32_ebi.o
|
||||
.debug_info 0x00007d4f 0x680 THUMB Flash Debug/../../obj/efm32_emu.o
|
||||
.debug_info 0x000083cf 0x7cc THUMB Flash Debug/../../obj/efm32_gpio.o
|
||||
.debug_info 0x00008b9b 0x84a THUMB Flash Debug/../../obj/efm32_i2c.o
|
||||
.debug_info 0x000093e5 0xb0 THUMB Flash Debug/../../obj/efm32_int.o
|
||||
.debug_info 0x00009495 0xad2 THUMB Flash Debug/../../obj/efm32_lcd.o
|
||||
.debug_info 0x00009f67 0x86 THUMB Flash Debug/../../obj/efm32_lesense.o
|
||||
.debug_info 0x00009fed 0x613 THUMB Flash Debug/../../obj/efm32_letimer.o
|
||||
.debug_info 0x0000a600 0x7d4 THUMB Flash Debug/../../obj/efm32_leuart.o
|
||||
.debug_info 0x0000add4 0x33f THUMB Flash Debug/../../obj/efm32_mpu.o
|
||||
.debug_info 0x0000b113 0x2b3 THUMB Flash Debug/../../obj/efm32_msc.o
|
||||
.debug_info 0x0000b3c6 0x86 THUMB Flash Debug/../../obj/efm32_opamp.o
|
||||
.debug_info 0x0000b44c 0x86a THUMB Flash Debug/../../obj/efm32_pcnt.o
|
||||
.debug_info 0x0000bcb6 0x1bf THUMB Flash Debug/../../obj/efm32_prs.o
|
||||
.debug_info 0x0000be75 0x2f4 THUMB Flash Debug/../../obj/efm32_rmu.o
|
||||
.debug_info 0x0000c169 0x3b9 THUMB Flash Debug/../../obj/efm32_rtc.o
|
||||
.debug_info 0x0000c522 0x242 THUMB Flash Debug/../../obj/efm32_system.o
|
||||
.debug_info 0x0000c764 0x700 THUMB Flash Debug/../../obj/efm32_timer.o
|
||||
.debug_info 0x0000ce64 0xafb THUMB Flash Debug/../../obj/efm32_usart.o
|
||||
.debug_info 0x0000d95f 0x2fc THUMB Flash Debug/../../obj/efm32_vcmp.o
|
||||
.debug_info 0x0000dc5b 0x39a THUMB Flash Debug/../../obj/efm32_wdog.o
|
||||
.debug_info 0x0000dff5 0x5a THUMB Flash Debug/../../obj/hooks.o
|
||||
.debug_info 0x0000e04f 0x5d8 THUMB Flash Debug/../../obj/main.o
|
||||
.debug_info 0x0000e627 0x36 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfprintf_int.o)
|
||||
.debug_info 0x0000e65d 0x65 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
.debug_info 0x0000e6c2 0xbd8 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
.debug_info 0x0000f29a 0xcd C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
|
||||
.debug_abbrev 0x00000000 0x4163
|
||||
.debug_abbrev 0x00000000 0x4172
|
||||
.debug_abbrev 0x00000000 0x14 THUMB Flash Debug/../../obj/cstart.o
|
||||
.debug_abbrev 0x00000014 0xbe THUMB Flash Debug/../../obj/vectors.o
|
||||
.debug_abbrev 0x000000d2 0xaf THUMB Flash Debug/../../obj/cpu.o
|
||||
.debug_abbrev 0x00000181 0x24e THUMB Flash Debug/../../obj/flash.o
|
||||
.debug_abbrev 0x000003cf 0xa3 THUMB Flash Debug/../../obj/nvm.o
|
||||
.debug_abbrev 0x00000472 0xdf THUMB Flash Debug/../../obj/timer.o
|
||||
.debug_abbrev 0x00000551 0x1aa THUMB Flash Debug/../../obj/uart.o
|
||||
.debug_abbrev 0x000006fb 0x7c THUMB Flash Debug/../../obj/assert.o
|
||||
.debug_abbrev 0x00000777 0x5b THUMB Flash Debug/../../obj/backdoor.o
|
||||
.debug_abbrev 0x000007d2 0x3f THUMB Flash Debug/../../obj/boot.o
|
||||
.debug_abbrev 0x00000811 0xe0 THUMB Flash Debug/../../obj/com.o
|
||||
.debug_abbrev 0x000008f1 0x3f THUMB Flash Debug/../../obj/cop.o
|
||||
.debug_abbrev 0x00000930 0x1ba THUMB Flash Debug/../../obj/xcp.o
|
||||
.debug_abbrev 0x00000aea 0x1d THUMB Flash Debug/../../obj/core_cm3.o
|
||||
.debug_abbrev 0x00000b07 0x1a5 THUMB Flash Debug/../../obj/system_efm32.o
|
||||
.debug_abbrev 0x00000cac 0x1c2 THUMB Flash Debug/../../obj/efm32_acmp.o
|
||||
.debug_abbrev 0x00000e6e 0x20a THUMB Flash Debug/../../obj/efm32_adc.o
|
||||
.debug_abbrev 0x00001078 0x291 THUMB Flash Debug/../../obj/efm32_aes.o
|
||||
.debug_abbrev 0x00001309 0x1 THUMB Flash Debug/../../obj/efm32_assert.o
|
||||
.debug_abbrev 0x0000130a 0x359 THUMB Flash Debug/../../obj/efm32_cmu.o
|
||||
.debug_abbrev 0x00001663 0x21c THUMB Flash Debug/../../obj/efm32_dac.o
|
||||
.debug_abbrev 0x0000187f 0x17f THUMB Flash Debug/../../obj/efm32_dbg.o
|
||||
.debug_abbrev 0x000019fe 0x300 THUMB Flash Debug/../../obj/efm32_dma.o
|
||||
.debug_abbrev 0x00001cfe 0x222 THUMB Flash Debug/../../obj/efm32_ebi.o
|
||||
.debug_abbrev 0x00001f20 0x1c1 THUMB Flash Debug/../../obj/efm32_emu.o
|
||||
.debug_abbrev 0x000020e1 0x235 THUMB Flash Debug/../../obj/efm32_gpio.o
|
||||
.debug_abbrev 0x00002316 0x28d THUMB Flash Debug/../../obj/efm32_i2c.o
|
||||
.debug_abbrev 0x000025a3 0x64 THUMB Flash Debug/../../obj/efm32_int.o
|
||||
.debug_abbrev 0x00002607 0x288 THUMB Flash Debug/../../obj/efm32_lcd.o
|
||||
.debug_abbrev 0x0000288f 0x42 THUMB Flash Debug/../../obj/efm32_lesense.o
|
||||
.debug_abbrev 0x000028d1 0x25c THUMB Flash Debug/../../obj/efm32_letimer.o
|
||||
.debug_abbrev 0x00002b2d 0x21e THUMB Flash Debug/../../obj/efm32_leuart.o
|
||||
.debug_abbrev 0x00002d4b 0xf3 THUMB Flash Debug/../../obj/efm32_mpu.o
|
||||
.debug_abbrev 0x00002e3e 0x13a THUMB Flash Debug/../../obj/efm32_msc.o
|
||||
.debug_abbrev 0x00002f78 0x42 THUMB Flash Debug/../../obj/efm32_opamp.o
|
||||
.debug_abbrev 0x00002fba 0x29b THUMB Flash Debug/../../obj/efm32_pcnt.o
|
||||
.debug_abbrev 0x00003255 0xe8 THUMB Flash Debug/../../obj/efm32_prs.o
|
||||
.debug_abbrev 0x0000333d 0x1c6 THUMB Flash Debug/../../obj/efm32_rmu.o
|
||||
.debug_abbrev 0x00003503 0x227 THUMB Flash Debug/../../obj/efm32_rtc.o
|
||||
.debug_abbrev 0x0000372a 0x110 THUMB Flash Debug/../../obj/efm32_system.o
|
||||
.debug_abbrev 0x0000383a 0x16b THUMB Flash Debug/../../obj/efm32_timer.o
|
||||
.debug_abbrev 0x000039a5 0x1e0 THUMB Flash Debug/../../obj/efm32_usart.o
|
||||
.debug_abbrev 0x00003b85 0x16b THUMB Flash Debug/../../obj/efm32_vcmp.o
|
||||
.debug_abbrev 0x00003cf0 0x1b4 THUMB Flash Debug/../../obj/efm32_wdog.o
|
||||
.debug_abbrev 0x00003ea4 0x28 THUMB Flash Debug/../../obj/hooks.o
|
||||
.debug_abbrev 0x00003ecc 0x16a THUMB Flash Debug/../../obj/main.o
|
||||
.debug_abbrev 0x00004036 0x25 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfprintf_int.o)
|
||||
.debug_abbrev 0x0000405b 0x43 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
.debug_abbrev 0x0000409e 0xa0 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
.debug_abbrev 0x0000413e 0x25 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
.debug_abbrev 0x00000181 0x25d THUMB Flash Debug/../../obj/flash.o
|
||||
.debug_abbrev 0x000003de 0xa3 THUMB Flash Debug/../../obj/nvm.o
|
||||
.debug_abbrev 0x00000481 0xdf THUMB Flash Debug/../../obj/timer.o
|
||||
.debug_abbrev 0x00000560 0x1aa THUMB Flash Debug/../../obj/uart.o
|
||||
.debug_abbrev 0x0000070a 0x7c THUMB Flash Debug/../../obj/assert.o
|
||||
.debug_abbrev 0x00000786 0x5b THUMB Flash Debug/../../obj/backdoor.o
|
||||
.debug_abbrev 0x000007e1 0x3f THUMB Flash Debug/../../obj/boot.o
|
||||
.debug_abbrev 0x00000820 0xe0 THUMB Flash Debug/../../obj/com.o
|
||||
.debug_abbrev 0x00000900 0x3f THUMB Flash Debug/../../obj/cop.o
|
||||
.debug_abbrev 0x0000093f 0x1ba THUMB Flash Debug/../../obj/xcp.o
|
||||
.debug_abbrev 0x00000af9 0x1d THUMB Flash Debug/../../obj/core_cm3.o
|
||||
.debug_abbrev 0x00000b16 0x1a5 THUMB Flash Debug/../../obj/system_efm32.o
|
||||
.debug_abbrev 0x00000cbb 0x1c2 THUMB Flash Debug/../../obj/efm32_acmp.o
|
||||
.debug_abbrev 0x00000e7d 0x20a THUMB Flash Debug/../../obj/efm32_adc.o
|
||||
.debug_abbrev 0x00001087 0x291 THUMB Flash Debug/../../obj/efm32_aes.o
|
||||
.debug_abbrev 0x00001318 0x1 THUMB Flash Debug/../../obj/efm32_assert.o
|
||||
.debug_abbrev 0x00001319 0x359 THUMB Flash Debug/../../obj/efm32_cmu.o
|
||||
.debug_abbrev 0x00001672 0x21c THUMB Flash Debug/../../obj/efm32_dac.o
|
||||
.debug_abbrev 0x0000188e 0x17f THUMB Flash Debug/../../obj/efm32_dbg.o
|
||||
.debug_abbrev 0x00001a0d 0x300 THUMB Flash Debug/../../obj/efm32_dma.o
|
||||
.debug_abbrev 0x00001d0d 0x222 THUMB Flash Debug/../../obj/efm32_ebi.o
|
||||
.debug_abbrev 0x00001f2f 0x1c1 THUMB Flash Debug/../../obj/efm32_emu.o
|
||||
.debug_abbrev 0x000020f0 0x235 THUMB Flash Debug/../../obj/efm32_gpio.o
|
||||
.debug_abbrev 0x00002325 0x28d THUMB Flash Debug/../../obj/efm32_i2c.o
|
||||
.debug_abbrev 0x000025b2 0x64 THUMB Flash Debug/../../obj/efm32_int.o
|
||||
.debug_abbrev 0x00002616 0x288 THUMB Flash Debug/../../obj/efm32_lcd.o
|
||||
.debug_abbrev 0x0000289e 0x42 THUMB Flash Debug/../../obj/efm32_lesense.o
|
||||
.debug_abbrev 0x000028e0 0x25c THUMB Flash Debug/../../obj/efm32_letimer.o
|
||||
.debug_abbrev 0x00002b3c 0x21e THUMB Flash Debug/../../obj/efm32_leuart.o
|
||||
.debug_abbrev 0x00002d5a 0xf3 THUMB Flash Debug/../../obj/efm32_mpu.o
|
||||
.debug_abbrev 0x00002e4d 0x13a THUMB Flash Debug/../../obj/efm32_msc.o
|
||||
.debug_abbrev 0x00002f87 0x42 THUMB Flash Debug/../../obj/efm32_opamp.o
|
||||
.debug_abbrev 0x00002fc9 0x29b THUMB Flash Debug/../../obj/efm32_pcnt.o
|
||||
.debug_abbrev 0x00003264 0xe8 THUMB Flash Debug/../../obj/efm32_prs.o
|
||||
.debug_abbrev 0x0000334c 0x1c6 THUMB Flash Debug/../../obj/efm32_rmu.o
|
||||
.debug_abbrev 0x00003512 0x227 THUMB Flash Debug/../../obj/efm32_rtc.o
|
||||
.debug_abbrev 0x00003739 0x110 THUMB Flash Debug/../../obj/efm32_system.o
|
||||
.debug_abbrev 0x00003849 0x16b THUMB Flash Debug/../../obj/efm32_timer.o
|
||||
.debug_abbrev 0x000039b4 0x1e0 THUMB Flash Debug/../../obj/efm32_usart.o
|
||||
.debug_abbrev 0x00003b94 0x16b THUMB Flash Debug/../../obj/efm32_vcmp.o
|
||||
.debug_abbrev 0x00003cff 0x1b4 THUMB Flash Debug/../../obj/efm32_wdog.o
|
||||
.debug_abbrev 0x00003eb3 0x28 THUMB Flash Debug/../../obj/hooks.o
|
||||
.debug_abbrev 0x00003edb 0x16a THUMB Flash Debug/../../obj/main.o
|
||||
.debug_abbrev 0x00004045 0x25 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfprintf_int.o)
|
||||
.debug_abbrev 0x0000406a 0x43 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(__vfscanf_int.o)
|
||||
.debug_abbrev 0x000040ad 0xa0 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_v7m_t_le.a(libc2.o)
|
||||
.debug_abbrev 0x0000414d 0x25 C:/Program Files (x86)/Rowley Associates Limited/CrossWorks for ARM 2.1/lib/libc_user_libc_v7m_t_le.a(user_libc.o)
|
||||
|
||||
.debug_aranges 0x00000000 0x1148
|
||||
.debug_aranges
|
||||
|
@ -2198,65 +2198,65 @@ OUTPUT(THUMB Flash Debug/../../bin/openbtl_olimex_efm32g880.elf elf32-littlearm)
|
|||
0x139 (size before relaxing)
|
||||
.debug_str 0x00000109 0xeb THUMB Flash Debug/../../obj/cpu.o
|
||||
0x15d (size before relaxing)
|
||||
.debug_str 0x000001f4 0x347 THUMB Flash Debug/../../obj/flash.o
|
||||
0x403 (size before relaxing)
|
||||
.debug_str 0x0000053b 0xbd THUMB Flash Debug/../../obj/nvm.o
|
||||
.debug_str 0x000001f4 0x334 THUMB Flash Debug/../../obj/flash.o
|
||||
0x3f0 (size before relaxing)
|
||||
.debug_str 0x00000528 0xbd THUMB Flash Debug/../../obj/nvm.o
|
||||
0x155 (size before relaxing)
|
||||
.debug_str 0x000005f8 0xf0 THUMB Flash Debug/../../obj/timer.o
|
||||
.debug_str 0x000005e5 0xf0 THUMB Flash Debug/../../obj/timer.o
|
||||
0x172 (size before relaxing)
|
||||
.debug_str 0x000006e8 0x729 THUMB Flash Debug/../../obj/uart.o
|
||||
.debug_str 0x000006d5 0x729 THUMB Flash Debug/../../obj/uart.o
|
||||
0x829 (size before relaxing)
|
||||
.debug_str 0x00000e11 0xbe THUMB Flash Debug/../../obj/assert.o
|
||||
.debug_str 0x00000dfe 0xbe THUMB Flash Debug/../../obj/assert.o
|
||||
0x13a (size before relaxing)
|
||||
.debug_str 0x00000ecf 0xa9 THUMB Flash Debug/../../obj/backdoor.o
|
||||
.debug_str 0x00000ebc 0xa9 THUMB Flash Debug/../../obj/backdoor.o
|
||||
0x119 (size before relaxing)
|
||||
.debug_str 0x00000f78 0x8f THUMB Flash Debug/../../obj/boot.o
|
||||
.debug_str 0x00000f65 0x8f THUMB Flash Debug/../../obj/boot.o
|
||||
0xf6 (size before relaxing)
|
||||
.debug_str 0x00001007 0x12b THUMB Flash Debug/../../obj/com.o
|
||||
.debug_str 0x00000ff4 0x12b THUMB Flash Debug/../../obj/com.o
|
||||
0x1c5 (size before relaxing)
|
||||
.debug_str 0x00001132 0x8f THUMB Flash Debug/../../obj/cop.o
|
||||
.debug_str 0x0000111f 0x8f THUMB Flash Debug/../../obj/cop.o
|
||||
0xf6 (size before relaxing)
|
||||
.debug_str 0x000011c1 0x274 THUMB Flash Debug/../../obj/xcp.o
|
||||
.debug_str 0x000011ae 0x274 THUMB Flash Debug/../../obj/xcp.o
|
||||
0x318 (size before relaxing)
|
||||
.debug_str 0x00001435 0x8b THUMB Flash Debug/../../obj/core_cm3.o
|
||||
.debug_str 0x00001422 0x8b THUMB Flash Debug/../../obj/core_cm3.o
|
||||
0x10e (size before relaxing)
|
||||
.debug_str 0x000014c0 0x253 THUMB Flash Debug/../../obj/system_efm32.o
|
||||
.debug_str 0x000014ad 0x253 THUMB Flash Debug/../../obj/system_efm32.o
|
||||
0x32f (size before relaxing)
|
||||
.debug_str 0x00001713 0x470 THUMB Flash Debug/../../obj/efm32_acmp.o
|
||||
.debug_str 0x00001700 0x470 THUMB Flash Debug/../../obj/efm32_acmp.o
|
||||
0x534 (size before relaxing)
|
||||
.debug_str 0x00001b83 0x752 THUMB Flash Debug/../../obj/efm32_adc.o
|
||||
.debug_str 0x00001b70 0x752 THUMB Flash Debug/../../obj/efm32_adc.o
|
||||
0xa27 (size before relaxing)
|
||||
.debug_str 0x000022d5 0x1ba THUMB Flash Debug/../../obj/efm32_aes.o
|
||||
.debug_str 0x000022c2 0x1ba THUMB Flash Debug/../../obj/efm32_aes.o
|
||||
0x2a9 (size before relaxing)
|
||||
.debug_str 0x0000248f 0x44d THUMB Flash Debug/../../obj/efm32_cmu.o
|
||||
.debug_str 0x0000247c 0x44d THUMB Flash Debug/../../obj/efm32_cmu.o
|
||||
0x95e (size before relaxing)
|
||||
.debug_str 0x000028dc 0x311 THUMB Flash Debug/../../obj/efm32_dac.o
|
||||
.debug_str 0x000028c9 0x311 THUMB Flash Debug/../../obj/efm32_dac.o
|
||||
0x6cb (size before relaxing)
|
||||
.debug_str 0x00002bed 0x136 THUMB Flash Debug/../../obj/efm32_dbg.o
|
||||
.debug_str 0x00002bda 0x136 THUMB Flash Debug/../../obj/efm32_dbg.o
|
||||
0x40e (size before relaxing)
|
||||
.debug_str 0x00002d23 0x7f5 THUMB Flash Debug/../../obj/efm32_dma.o
|
||||
.debug_str 0x00002d10 0x7f5 THUMB Flash Debug/../../obj/efm32_dma.o
|
||||
0xb39 (size before relaxing)
|
||||
.debug_str 0x00003518 0x359 THUMB Flash Debug/../../obj/efm32_ebi.o
|
||||
.debug_str 0x00003505 0x359 THUMB Flash Debug/../../obj/efm32_ebi.o
|
||||
0x439 (size before relaxing)
|
||||
.debug_str 0x00003871 0x18f THUMB Flash Debug/../../obj/efm32_emu.o
|
||||
.debug_str 0x0000385e 0x18f THUMB Flash Debug/../../obj/efm32_emu.o
|
||||
0x360 (size before relaxing)
|
||||
.debug_str 0x00003a00 0x211 THUMB Flash Debug/../../obj/efm32_gpio.o
|
||||
.debug_str 0x000039ed 0x211 THUMB Flash Debug/../../obj/efm32_gpio.o
|
||||
0x544 (size before relaxing)
|
||||
.debug_str 0x00003c11 0x366 THUMB Flash Debug/../../obj/efm32_i2c.o
|
||||
.debug_str 0x00003bfe 0x366 THUMB Flash Debug/../../obj/efm32_i2c.o
|
||||
0x68f (size before relaxing)
|
||||
.debug_str 0x00003f77 0x8f THUMB Flash Debug/../../obj/efm32_int.o
|
||||
.debug_str 0x00003f64 0x8f THUMB Flash Debug/../../obj/efm32_int.o
|
||||
0x130 (size before relaxing)
|
||||
.debug_str 0x00004006 0x63e THUMB Flash Debug/../../obj/efm32_lcd.o
|
||||
.debug_str 0x00003ff3 0x63e THUMB Flash Debug/../../obj/efm32_lcd.o
|
||||
0x73d (size before relaxing)
|
||||
.debug_str 0x00004644 0x87 THUMB Flash Debug/../../obj/efm32_lesense.o
|
||||
.debug_str 0x00004631 0x87 THUMB Flash Debug/../../obj/efm32_lesense.o
|
||||
0x11f (size before relaxing)
|
||||
.debug_str 0x000046cb 0x29b THUMB Flash Debug/../../obj/efm32_letimer.o
|
||||
.debug_str 0x000046b8 0x29b THUMB Flash Debug/../../obj/efm32_letimer.o
|
||||
0x39a (size before relaxing)
|
||||
.debug_str 0x00004966 0x157 THUMB Flash Debug/../../obj/efm32_leuart.o
|
||||
.debug_str 0x00004953 0x157 THUMB Flash Debug/../../obj/efm32_leuart.o
|
||||
0x612 (size before relaxing)
|
||||
.debug_str 0x00004abd 0x3dc THUMB Flash Debug/../../obj/efm32_mpu.o
|
||||
.debug_str 0x00004aaa 0x3dc THUMB Flash Debug/../../obj/efm32_mpu.o
|
||||
0x49a (size before relaxing)
|
||||
.debug_str 0x00004e99 0xe4 THUMB Flash Debug/../../obj/efm32_msc.o
|
||||
.debug_str 0x00004e86 0xf7 THUMB Flash Debug/../../obj/efm32_msc.o
|
||||
0x253 (size before relaxing)
|
||||
.debug_str 0x00004f7d 0x85 THUMB Flash Debug/../../obj/efm32_opamp.o
|
||||
0x11d (size before relaxing)
|
||||
|
|
|
@ -33,14 +33,14 @@ S11301D800208646EC4600200021254A9047FEE789
|
|||
S11301E8884207D0521A05D0037801300B700131C8
|
||||
S11301F8013AF9D17047884202D002700130FAE717
|
||||
S11302087047000008ED00E000000000940800209A
|
||||
S113021894080020940800200431000014020020EF
|
||||
S11302281C0200207C0200007C020000E42C000078
|
||||
S1130238F02E00000000002014020020E42C00002E
|
||||
S1130248E42C0000E42C0000E42C0000E42C000062
|
||||
S1130258E42C0000E42C0000E42C0000F02E000044
|
||||
S1130218940800209408002094310000140200205F
|
||||
S11302281C0200207C0200007C020000742D0000E7
|
||||
S1130238802F00000000002014020020742D00000C
|
||||
S1130248742D0000742D0000742D0000742D00001E
|
||||
S1130258742D0000742D0000742D0000802F000000
|
||||
S11302681C02002014070020140700209407002013
|
||||
S1070278F11D000070
|
||||
S113027C00B542F6E440C0F200004FF03C0140F6F9
|
||||
S113027C00B542F67450C0F200004FF03C0140F659
|
||||
S113028CFD33C0F2000398475DF804FB00B540F65B
|
||||
S113029C6103C0F20003984778B140F66953C0F289
|
||||
S11302AC000398474EF60853CEF200034FF48042F5
|
||||
|
@ -49,14 +49,14 @@ S11302CCF0B50F4692B28AB1064600F1010002F174
|
|||
S11302DCFF3292B2851840F6AD54C0F2000417F800
|
||||
S11302EC013B06F8013BA047AE42F8D1F0BD00BF7C
|
||||
S11302FC00B540F25513C0F2000398475DF804FBB7
|
||||
S113030CF0B5064642F67C55C0F200054FF00004E9
|
||||
S113030CF0B5064642F60C65C0F200054FF0000449
|
||||
S113031C40F6AD57C0F20007B8472B68B3420DD86E
|
||||
S113032C69685B189E4209D242F67C53C0F2000302
|
||||
S113032C69685B189E4209D242F60C63C0F2000362
|
||||
S113033C04EB440203EB8203187AF0BD04F10104CC
|
||||
S113034C05F10C050E2CE7D14FF0FF00F0BD00BFFA
|
||||
S113035CF0B5C7B242F67C54C0F200044FF000066C
|
||||
S113035CF0B5C7B242F60C64C0F200044FF00006CC
|
||||
S113036C40F6AD55C0F20005A847237ABB4208D12C
|
||||
S113037C42F67C53C0F2000306EB460253F822000B
|
||||
S113037C42F60C63C0F2000306EB460253F822006B
|
||||
S113038CF0BD06F1010604F10C040E2EECD14FF075
|
||||
S113039CFF30F0BD2DE9F04381B00546006840F212
|
||||
S11303AC0D33C0F200039847FF2808BF002027D064
|
||||
|
@ -64,7 +64,7 @@ S11303BC4FF0000440F6AD58C0F2000840F2C509F5
|
|||
S11303CCC2F200092E68A71904F10403EB58009338
|
||||
S11303DCC047384669464FF00402C84758B9A25979
|
||||
S11303EC009B9A420AD104F10404B4F5007FE9D1CC
|
||||
S11303FC4FF0010004E04FF0010001E04FF0010068
|
||||
S11303FC4FF0010004E04FF0000001E04FF000006A
|
||||
S113040C01B0BDE8F08300BF00B54FEAC1534FEA19
|
||||
S113041CD3537BB903688B4210D040F8041B4FF4C0
|
||||
S113042C007240F2CD23C0F2000398474FF0010054
|
||||
|
@ -103,9 +103,9 @@ S113062CC0F6E07393F80090B9F1490F14BF00239E
|
|||
S113063C0123B9F1470F08BF43F00103B9F1480F87
|
||||
S113064C14BF4FF400694FF480590BB14FF4007987
|
||||
S113065C304640F25D35C0F20005A84707462046F7
|
||||
S113066CA847824642F67C54C0F200044FF00006C0
|
||||
S113066CA847824642F60C64C0F200044FF0000620
|
||||
S113067C40F6AD55C0F20005A847237A434509D18D
|
||||
S113068C42F67C53C0F2000306EB460203EB8203F2
|
||||
S113068C42F60C63C0F2000306EB460203EB820352
|
||||
S113069C5D6807E006F1010604F10C040E2EEBD1A3
|
||||
S11306AC4FF00005C7EB0A0A5544B5FBF9F5ADB29A
|
||||
S11306BC1DB34FF0000440F6AD56C0F2000640F2F4
|
||||
|
@ -156,7 +156,7 @@ S113097C00039847A36813F0100F12D140F6AD553D
|
|||
S113098CC0F200054FF48844C4F20804A847A368D5
|
||||
S113099C13F0100FFAD04FF0010030BD4FF00000EF
|
||||
S11309AC30BD4FF0010030BD30B586B06C4642F618
|
||||
S11309BC2465C0F200050FCD0FC495E8030084E84C
|
||||
S11309BCB465C0F200050FCD0FC495E8030084E8BC
|
||||
S11309CC03004FF44240C0F202004FF0010141F227
|
||||
S11309DC7964C0F20004A0474FF002004FF0060106
|
||||
S11309EC4FF004024FF0010341F68535C0F20005C7
|
||||
|
@ -171,12 +171,12 @@ S1130A6CFD43C0F200039847204629464FF4165222
|
|||
S1130A7C41F65D43C0F2000398474FF003036365EE
|
||||
S1130A8C4FF00403636320464FF0050141F6C14364
|
||||
S1130A9CC0F20003984706B030BD00BF2DE9F04307
|
||||
S1130AAC0546CCB2402C0AD942F63C60C0F2000098
|
||||
S1130AAC0546CCB2402C0AD942F6CC60C0F2000008
|
||||
S1130ABC4FF0680140F6FD33C0F20003984720461E
|
||||
S1130ACC40F65913C0F20003984701280AD042F6A5
|
||||
S1130ADC3C60C0F200004FF06B0140F6FD33C0F2F5
|
||||
S1130ADCCC60C0F200004FF06B0140F6FD33C0F265
|
||||
S1130AEC000398472646FCB14FF0000440F6AD577E
|
||||
S1130AFCC0F2000740F65918C0F2000842F63C69EF
|
||||
S1130AFCC0F2000740F65918C0F2000842F6CC695F
|
||||
S1130B0CB847285DC047012809D04846C0F2000008
|
||||
S1130B1C4FF0730140F6FD33C0F20003984704F123
|
||||
S1130B2C0104A3B2B342EBD3BDE8F08310B5044681
|
||||
|
@ -257,7 +257,7 @@ S1130FCCD2B2013BF9D140F2BC63C2F200034FF040
|
|||
S1130FDC0001DA714FEA1220C0B218724FEA1240C3
|
||||
S1130FECC0B258724FEA12629A724FF001021A712F
|
||||
S1130FFC597199714FF00802A3F844200DE140F2A5
|
||||
S113100CBC63C2F200034FF0FF02DA7042F6C8620E
|
||||
S113100CBC63C2F200034FF0FF02DA7042F658726E
|
||||
S113101CC0F200029A644FF000021A715A719A716C
|
||||
S113102C4FF00701D9711A725A729A724FF0080272
|
||||
S113103CA3F84420F1E04FF0000040F6C153C0F295
|
||||
|
@ -503,288 +503,297 @@ S1131F2CC4F2000211601A6822F490421A604FF055
|
|||
S1131F3C00004FF001010A4641F6C913C0F2000338
|
||||
S1131F4C98474FF40043C4F20C031A6C42F00F028E
|
||||
S1131F5C1A645A6C6FEA12426FEA02425A644FF4E2
|
||||
S1131F6C3340C0F206004FF0000141F27964C0F234
|
||||
S1131F7C0004A0474FF44850C0F202004FF0000197
|
||||
S1131F8CA0474FF47245C0F2020528464FF00001F9
|
||||
S1131F9CA04728464FF00001A0474FF001004FF036
|
||||
S1131FAC09014FF00502034641F68534C0F20004E2
|
||||
S1131FBCA0474FF001004FF0020141F66933C0F223
|
||||
S1131FCC0003984740F69D43C0F20003984740F63F
|
||||
S1131FDCCD44C0F20004A047FDE700BF2DE9F04F4B
|
||||
S1131FEC87B007460C4603924FF00003036042F699
|
||||
S1131FFCD06BC0F2000B42F6E063C0F20003029314
|
||||
S113200CC1E204F10104252904BF2346002603D0B0
|
||||
S113201C384600F0A3FDB6E2194613F8010B1C4632
|
||||
S113202CA0F12002102A1CD8DFE802F0091B1B0CBB
|
||||
S113203C1B1B1B0F1B1B1B121B151B1B180046F019
|
||||
S113204C4006E9E746F08006E6E746F40046E3E797
|
||||
S113205C46F02006E0E746F01006DDE746F400768D
|
||||
S113206CDAE72A2808D0A0F13002D2B2092A88BFB4
|
||||
S113207C4FF0000A11D920E0039B03F104000390F4
|
||||
S113208CD3F800A0BAF1000FBCBFCAF1000A46F0A5
|
||||
S113209C1006487801F102040FE04FF0000A0AEB35
|
||||
S11320AC8A0AA0F1300000EB4A0A13F8010B1C4613
|
||||
S11320BCA0F13002D2B2092AF1D92AEAEA7A2E28FE
|
||||
S11320CC18BF4FF000082DD120782A280AD004F12B
|
||||
S11320DC0104A0F13003DBB2092B88BF4FF00008D8
|
||||
S11320EC0AD91DE0039B03F104020392D3F8008088
|
||||
S11320FC607804F1020410E023464FF0000808EB6A
|
||||
S113210C8808A0F1300000EB480813F8010B1C46BA
|
||||
S113211CA0F13002D2B2092AF1D9B8F1000F01DBD7
|
||||
S113212C46F4807668280AD12078682803BF46F0E4
|
||||
S113213C080660780234013418BF46F00406782887
|
||||
S113214C7AD8DFE810F02E02790079007900790052
|
||||
S113215C79007900790079007900790079007900A7
|
||||
S113216C7900790079007900790079007900790097
|
||||
S113217C7900790079007900790079007900790087
|
||||
S113218C7900790079007900790079007900790077
|
||||
S113219C8A00790079007900790079007900790056
|
||||
S11321AC7900790079007900790079007900790057
|
||||
S11321BC7900790079007900790079007900790047
|
||||
S11321CC7900790079007900790079007900790037
|
||||
S11321DC7900790079007900790079007900790027
|
||||
S1131F6C4070C0F204004FF0000141F27964C0F2F9
|
||||
S1131F7C0004A0474FF49850C0F204004FF0000145
|
||||
S1131F8CA0474FF44C50C0F204004FF00001A0479E
|
||||
S1131F9C4FF42240C0F202004FF00001A0474FF46E
|
||||
S1131FAC0070C0F202004FF00001A0474FF49050B3
|
||||
S1131FBCC0F202004FF00001A0474FF40850C0F2E9
|
||||
S1131FCC02004FF00001A0474FF44850C0F2020049
|
||||
S1131FDC4FF00001A0474FF4E440C0F202004FF070
|
||||
S1131FEC0001A0474FF40240C0F202004FF0000180
|
||||
S1131FFCA0474FF43240C0F202004FF00001A0475A
|
||||
S113200C4FF46240C0F202004FF00001A0474FF4BD
|
||||
S113201C7240C0F202004FF00001A0474FF452404E
|
||||
S113202CC0F202004FF00001A0474FF001004FF046
|
||||
S113203C09014FF00502034641F68534C0F2000451
|
||||
S113204CA0474FF001004FF0020141F66933C0F292
|
||||
S113205C0003984740F69D43C0F20003984740F6AE
|
||||
S113206CCD44C0F20004A047FDE700BF2DE9F04FBA
|
||||
S113207C87B007460C4603924FF00003036042F608
|
||||
S113208C607BC0F2000B42F67073C0F20003029343
|
||||
S113209CC1E204F10104252904BF2346002603D020
|
||||
S11320AC384600F0A3FDB6E2194613F8010B1C46A2
|
||||
S11320BCA0F12002102A1CD8DFE802F0091B1B0C2B
|
||||
S11320CC1B1B1B0F1B1B1B121B151B1B180046F089
|
||||
S11320DC4006E9E746F08006E6E746F40046E3E707
|
||||
S11320EC46F02006E0E746F01006DDE746F40076FD
|
||||
S11320FCDAE72A2808D0A0F13002D2B2092A88BF24
|
||||
S113210C4FF0000A11D920E0039B03F10400039063
|
||||
S113211CD3F800A0BAF1000FBCBFCAF1000A46F014
|
||||
S113212C1006487801F102040FE04FF0000A0AEBA4
|
||||
S113213C8A0AA0F1300000EB4A0A13F8010B1C4682
|
||||
S113214CA0F13002D2B2092AF1D92AEAEA7A2E286D
|
||||
S113215C18BF4FF000082DD120782A280AD004F19A
|
||||
S113216C0104A0F13003DBB2092B88BF4FF0000847
|
||||
S113217C0AD91DE0039B03F104020392D3F80080F7
|
||||
S113218C607804F1020410E023464FF0000808EBD9
|
||||
S113219C8808A0F1300000EB480813F8010B1C462A
|
||||
S11321ACA0F13002D2B2092AF1D9B8F1000F01DB47
|
||||
S11321BC46F4807668280AD12078682803BF46F054
|
||||
S11321CC080660780234013418BF46F004067828F7
|
||||
S11321DC7AD8DFE810F02E027900790079007900C2
|
||||
S11321EC7900790079007900790079007900790017
|
||||
S11321FC790079007900EE00790079007900790092
|
||||
S113220C79007900790079007900790090001A013D
|
||||
S113221C79007900790079001A0179007900790044
|
||||
S113222C7900AB000201DB0079007900B70079007A
|
||||
S113223C110179007900F00040F21073C2F200032E
|
||||
S113224C1D68002D00F09F81CDF8008003AB019335
|
||||
S113225C394632465346A84795E138464FF0250196
|
||||
S113226C00F07CFC8FE1039B03F1040203921D78C4
|
||||
S113227C0AF1FF3A304651463A4600F09DFC384686
|
||||
S113228C294600F06BFC16F0100F00F07C814FF027
|
||||
S113229C200051463A4600F07DFC74E116F0080F1C
|
||||
S11322AC039B03F1040203921B683A6814BF1A706F
|
||||
S11322BC1A6068E1039B03F104020392D3F80090C3
|
||||
S11322CC484600F0C9FC05468045ACBF00230123F9
|
||||
S11322DC03EA1623002B18BF4546C5EB0A0A304601
|
||||
S11322EC51463A4600F068FC002DCCD019F8011B7D
|
||||
S11322FC384600F033FC013DF8D1C4E7039B03F1ED
|
||||
S113230C040203921B6806F08009B9F1000F14BF94
|
||||
S113231C4FF023094FF0000946F480764FF008087B
|
||||
S113232C69E046F4005643F2780343F258097828DE
|
||||
S113233C08BF994616F0800F08BF4FF0000916F439
|
||||
S113234C807F18BF26F400761EE006F08009B9F1F0
|
||||
S113235C000F14BF4FF030094FF0000916F4807FC2
|
||||
S113236C18BF26F400760FE016F4807F1CBF26F409
|
||||
S113237C00764FF0000907D104E046F480464FF094
|
||||
S113238C000901E04FF0000916F4804F1DD0039BA7
|
||||
S113239C03F1040203921B6816F0040F18BF1BB25E
|
||||
S11323AC03D116F0080F18BFDBB2002BBCBF5B4285
|
||||
S11323BC4FF02D091ADB06F04002002A18BF4FF02B
|
||||
S11323CC200916F0200F11D00EE0039B03F1040238
|
||||
S11323DC03921B6816F0040F18BF9BB206D116F0BB
|
||||
S11323EC080F18BFDBB201E04FF02B0916F4807F05
|
||||
S11323FC04D026F4007616F4807F01D14FF0010846
|
||||
S113240CA0F15800202870D8DFE800F0196F6F6F26
|
||||
S113241C6F6F6F6F6F6F6F6F156F6F6F6F156F6F70
|
||||
S113242C6F6F6F11196F6F6F6F156F6F19004FF01E
|
||||
S113243C00050BBB5BE04FF0000553BB57E04FF0BE
|
||||
S113244C0005002B53D04FF0000506F40052DDF8C4
|
||||
S113245C08E032B103F00F011EF8010004A968541E
|
||||
S113246C05E003F00F011BF8010004A9685405F101
|
||||
S113247C01051B09EDD13AE04FF0000503F007010B
|
||||
S113248C01F1300104AAA95405F10105DB08F5D1C9
|
||||
S113249C2DE04FF0000506F4004C4CF6CD4ECCF676
|
||||
S11324ACCC4E6246A446144654B105F00302032AEA
|
||||
S11324BC01BF07A842192C2102F80C1C08BF0135D6
|
||||
S11324CC07AA5119AEFB03024FEAD20202EB8200B7
|
||||
S11324DCA3EB400303F1300301F80C3C05F10105B7
|
||||
S11324EC1346002AE0D1644601E04FF00005C5EB29
|
||||
S11324FC080828EAE878C8EB0A0AC5EB0A0AB9F115
|
||||
S113250CFF0F88BF0AF1FF3AB9F1000F01D00AF1AD
|
||||
S113251CFF3A16F4007F06D1304651463A4600F095
|
||||
S113252C4BFB4FF0000AB9F1FF0F04D9C9F3072193
|
||||
S113253C384600F013FBB9F1000F04D05FFA89F1AF
|
||||
S113254C384600F00BFB304651463A4600F034FB5B
|
||||
S113255C4FF0300041463A4600F01CFB012D09D4E3
|
||||
S113256C0DF11008454415F8011D384600F0F6FA33
|
||||
S113257C4545F8D116F0100F05D04FF02000514608
|
||||
S113258C3A4600F007FB217800297FF43AADBB688A
|
||||
S113259C2BB13A6879688A423CBF00219954386857
|
||||
S11325AC01E04FF0FF3007B0BDE8F08F10B50446E2
|
||||
S11325BC0B783BB1B0F1FF3F06D04B6803F1FF330E
|
||||
S11325CC4B6001E08B689847204610BD2DE9F04F15
|
||||
S11325DC82468B4617469846099E4FF0FF3900E019
|
||||
S11325ECA94609F10105504600F0A4FA044600F08E
|
||||
S11325FC27FB0028F4D12346B4F1FF3F08BF4FF06A
|
||||
S113260CFF3500F09C8027F4C067002E4EDD17F0D8
|
||||
S113261C800F0DD02B2C03D02D2C09D147F48067BF
|
||||
S113262C09F10205504600F085FA044606F1FF361E
|
||||
S113263C302C14BF00230123002ED4BF002303F03D
|
||||
S113264C0103002B32D047F4007706F1FF3605F175
|
||||
S113265C0109504600F06EFA0446002E20DD58287D
|
||||
S113266C14BF00230123782808BF43F00103BBB136
|
||||
S113267CB8F1100F14BF00230123B8F1000F08BFE9
|
||||
S113268C43F0010363B127F4007706F1FF3605F13B
|
||||
S113269C0209504600F04EFA04464FF0100851E07F
|
||||
S11326ACB8F1000F08BF4FF008084BE0B8F1000F69
|
||||
S11326BC08BF4FF00A08002ED8BF4FF000090EDCFB
|
||||
S11326CC15E047F4007706F1FF3608FB090905F11C
|
||||
S11326DC0105504600F02EFA044616B907E04FF0F7
|
||||
S11326EC00092046414600F08DFA0028E9DA20461C
|
||||
S11326FC5146FFF75BFF17F4007F08BF6FF001052D
|
||||
S113270C1DD017F0010F1AD1DBF8003003F10402CD
|
||||
S113271CCBF800201B6807F49062B2F5906F08BFE9
|
||||
S113272CC9F1000917F0100F18BF83F8009006D1F7
|
||||
S113273C17F0080F14BFA3F80090C3F800902846B4
|
||||
S113274CBDE8F08F4D46B6E72DE9F04F85B001900A
|
||||
S113275C8A4604924FF0000BCDF808B04CF6CC49E5
|
||||
S113276CC0F6CC49544614F8015B002D00F0DE8110
|
||||
S113277C252D3BD0284600F063FA08B918E02C4606
|
||||
S113278C04F10105207800F05BFA0028F7D101E090
|
||||
S113279C0BF1010B019800F0CDF9054600F050FA4D
|
||||
S11327AC0028F5D128460199FFF700FFA246D9E786
|
||||
S11327BC019800F0BFF90646A84203D10BF1010BB6
|
||||
S11327CCA246CFE70199FFF7F1FE029AD2F1010379
|
||||
S11327DC38BF0023B6F1FF3F14BF002603F00106F7
|
||||
S11327EC002E18BF4FF0FF3202929FE19AF801308D
|
||||
S11327FC2A2B06BF0AF102044FF001084FF000081F
|
||||
S113280C4FF000050CE04D4500F3908105EB850578
|
||||
S113281CA6F1300616EB450500F1888148F0200836
|
||||
S113282C274604F101043E78A246304600F0E2F952
|
||||
S113283C0028E8D1414608F02002002A08BF6FF0B6
|
||||
S113284C00454C2E05D17E7807F1020A48F0440865
|
||||
S113285C0EE0682E0CD17E78682E03BF48F0100869
|
||||
S113286CBE7807F1030A07F1020A18BF41F0080801
|
||||
S113287CA6F12506532E00F25981DFE816F0540018
|
||||
S113288C5701570157015701570157015701570178
|
||||
S113289C5701570157015701570157015701570168
|
||||
S11328AC5701570157015701570157015701570158
|
||||
S11328BC5701570157015701570157015701570148
|
||||
S11328CC5701570157015701570157015701570138
|
||||
S11328DC5701570157015701570157015701570128
|
||||
S11328EC570157013301570157015701570157013C
|
||||
S11328FC5701570157015701570170009F005701A9
|
||||
S113290C570157015701AA005701570157015701A5
|
||||
S113291CB500CD00D80057015701E3005701280139
|
||||
S113292C570157013301019800F004F90446252896
|
||||
S113293C02D10BF1010B15E70199FFF737FE029A4F
|
||||
S113294C131C18BF0123B4F1FF3F0CBF1C4643F00A
|
||||
S113295C0104002C08BF4FF0FF320292E6E008F0AD
|
||||
S113296C2003002B08BF012518F0010401BF049BB0
|
||||
S113297C1A1D04921E6818BF0026002D00F0D68084
|
||||
S113298C002D13DD019800F0D5F8B0F1FF3F06D10E
|
||||
S113299C029B002B08BF4FF0FF330293C6E00CB927
|
||||
S11329AC06F8010B0BF1010B013DEBD1002C7FF46C
|
||||
S11329BCD9AE029B03F101030293D3E648F08002E3
|
||||
S11329CC0095019804A94FF00A03FFF7FFFD044694
|
||||
S11329DC92E048F080020095019804A94FF000039E
|
||||
S11329ECFFF7F4FD044687E018F0010F7FF4BAAE4C
|
||||
S11329FC049B03F1040204921B6818F0100F18BF17
|
||||
S1132A0C83F800B07FF4AEAE18F0080F14BFA3F82F
|
||||
S1132A1C00B0C3F800B0A5E648F080020095019818
|
||||
S1132A2C04A94FF00803FFF7D1FD044664E028F035
|
||||
S1132A3C1E020095019804A94FF01003FFF7C6FD80
|
||||
S1132A4C044659E04FF0FF3404F10104019800F0FE
|
||||
S1132A5C71F8064600F0F4F80028F5D1B6F1FF3F02
|
||||
S1132A6C08BF4FF0FF3447D018F0010701BF049B97
|
||||
S1132A7C1A1D04921B680EBF039300220392002DAF
|
||||
S1132A8C16DC1AE005F1FF351FB9039B03F8016B43
|
||||
S1132A9C039304F10104019800F04CF80646431C1E
|
||||
S1132AAC18BF0123002DD4BF002303F0010323B16D
|
||||
S1132ABC304600F0C5F80028E4D030460199FFF701
|
||||
S1132ACC75FDCFB94FF00002039B1A7014E048F067
|
||||
S1132ADC80020095019804A94FF00A03FFF776FDD4
|
||||
S1132AEC044609E048F080020095019804A94FF0CF
|
||||
S1132AFC1003FFF76BFD0446002C0FDA029A131C2B
|
||||
S1132B0C18BF0123B4F1FF3F0CBF1C4643F0010472
|
||||
S1132B1C002C08BF4FF0FF32029207E018F0010FAF
|
||||
S1132B2C02BF029B01330293A3441BE6029805B037
|
||||
S1132B3CBDE8F08F00B5034602783AB142681078CC
|
||||
S1132B4C40B102F101025A605DF804FB43689847F6
|
||||
S1132B5C5DF804FB4FF0FF305DF804FB30B5044620
|
||||
S1132B6CC8B2A16849B12368626803F101059542B2
|
||||
S1132B7C08BF0020934238BFC854E3682BB12168C6
|
||||
S1132B8C6268914201D221469847236803F10103FC
|
||||
S1132B9C236030BDF0B5154601290BD40E464FF019
|
||||
S1132BAC0004C7B228463946FFF7D8FF04F10104E4
|
||||
S1132BBCB442F7D1F0BD00BF00B510F0100F07D12F
|
||||
S1132BCC00F4007000280CBF20203020FFF7E2FF37
|
||||
S1132BDC5DF804FBA0F1410019288CBF00200120F2
|
||||
S1132BEC704700BFA0F1610019288CBF00200120A0
|
||||
S1132BFC704700BFA0F1300009288CBF00200120D1
|
||||
S1132C0C704700BF30B504460D46FFF7F3FF10B113
|
||||
S1132C1CA4F130000FE02046FFF7E4FF10B1A4F15B
|
||||
S1132C2C570008E02046FFF7D5FF10B1A4F1370098
|
||||
S1132C3C01E04FF0FF30A842A8BF4FF0FF3030BD89
|
||||
S1132C4CA0F10903202814BF00200120042B98BFF5
|
||||
S1132C5C40F00100704700BF00F1010110F0030FB8
|
||||
S1132C6C11D010F8012B002A23D010F0030F0AD036
|
||||
S1132C7C10F8012B002A1CD010F0030F03D010F80D
|
||||
S1132C8C012B002A15D02DE970004FF001324FF0C2
|
||||
S1132C9C803350F8044BA4EB020525EA04051D40CF
|
||||
S1132CAC00D1F6E7A0F1040070BC10F8012B002A47
|
||||
S1132CBCFBD1A0EB0100704700B503B400F008F899
|
||||
S1132CCC03BC02B4694609BE00F004F801BC00BDA3
|
||||
S10B2CDC704700BF704700BF00
|
||||
S1132CE4443A2F7573722F6665617365722F736F1F
|
||||
S1132CF46674776172652F4F70656E424C542F541D
|
||||
S1132D0461726765742F44656D6F2F41524D434D55
|
||||
S1132D14335F45464D33325F4F6C696D65785F456B
|
||||
S1132D244D3332473838304631323853544B5F438D
|
||||
S1132D34726F7373776F726B732F426F6F742F6933
|
||||
S1132D4464652F2E2E2F2E2E2F2E2E2F2E2E2F5304
|
||||
S1132D546F757263652F41524D434D335F45464D44
|
||||
S1132D6433322F43726F7373776F726B732F76657D
|
||||
S1132D7463746F72732E630000400000002000002F
|
||||
S1132D8402000000006000000020000003000000B6
|
||||
S1132D9400800000002000000400000000A00000E7
|
||||
S1132DA4002000000500000000C000000020000016
|
||||
S1132DB40600000000E000000020000007000000FE
|
||||
S1132DC400000100002000000800000000200100B1
|
||||
S1132DD40020000009000000004001000020000061
|
||||
S1132DE40A00000000600100002000000B00000045
|
||||
S1132DF400800100002000000C00000000A001007D
|
||||
S1132E04002000000D00000000C0010000200000AC
|
||||
S1132E140E00000000E00100002000000F0000008C
|
||||
S1132E2405000000000000008025000000000000F0
|
||||
S1132E340000000000000000443A2F7573722F66EE
|
||||
S1132E4465617365722F736F6674776172652F4F52
|
||||
S1132E5470656E424C542F5461726765742F4465D7
|
||||
S1132E646D6F2F41524D434D335F45464D33325FB1
|
||||
S1132E744F6C696D65785F454D3332473838304659
|
||||
S1132E8431323853544B5F43726F7373776F726B81
|
||||
S1132E94732F426F6F742F6964652F2E2E2F2E2E7D
|
||||
S1132EA42F2E2E2F2E2E2F536F757263652F4152A2
|
||||
S1132EB44D434D335F45464D33322F756172742E45
|
||||
S1132EC4630000004F70656E424C5400303132335D
|
||||
S1132ED43435363738396162636465663031323388
|
||||
S10F2EE434353637383941424344454602
|
||||
S1132EF04FF00003C4F20C039A6842F001029A6096
|
||||
S1132F0018614FF00102DA60DB6913F0040F0AD094
|
||||
S1132F104FF00003C4F20C039A6822F001029A6095
|
||||
S1132F204FF0FF3070474FF00003C4F20C03DB692D
|
||||
S1132F3013F0020F0AD04FF00003C4F20C039A6896
|
||||
S1132F4022F001029A606FF0010070474FF0000315
|
||||
S1132F50C4F20C034FF00202DA60DB6913F0010FD4
|
||||
S1132F601CD049F28063C0F298034FF00001C4F210
|
||||
S1132F700C0103F1FF33CA6912F0010F02D0002BD8
|
||||
S1132F80F7D100E053B94FF00003C4F20C039A6880
|
||||
S1132F9022F001029A606FF0020070474FF00003C4
|
||||
S1132FA0C4F20C039A6822F001029A604FF0000008
|
||||
S1132FB0704700BF2DE9F0074FF00003C4F20C0383
|
||||
S1132FC09C6844F001049C604FEAA207002F40F380
|
||||
S1132FD08C8080464FF00003C4F20C0318614FF05C
|
||||
S1132FE00102DA60DB6913F0040F21D14FF0000312
|
||||
S1132FF0C4F20C03DB6913F0020F33D14FF0040465
|
||||
S11330004FF0000A55465246C4F20C0249F280665B
|
||||
S1133010C0F298064FF0080C4FF001091BE004EBD6
|
||||
S113302008031361C2F80C90D36913F0040F0AD09B
|
||||
S11330304FF00003C4F20C039A6822F001029A6074
|
||||
S11330404FF0FF305BE0D36904F1040013F0020F8A
|
||||
S113305008D1A2460446D36913F0080F08BF3346CB
|
||||
S11330600BD01FE04FF00003C4F20C039A6822F067
|
||||
S113307001029A606FF0010041E003F1FF33D0696F
|
||||
S113308010F0080F02D1002BF7D100E053B94FF034
|
||||
S11330900003C4F20C039A6822F001029A606FF0F4
|
||||
S11330A002002CE051F80A309361C2F80CC0D369D5
|
||||
S11330B013F0010F15D0334603F1FF33D06910F03C
|
||||
S11330C0010F02D0002BF7D100E053B94FF00003F9
|
||||
S11330D0C4F20C039A6822F001029A606FF00200B5
|
||||
S11330E00DE005F10105BD4299D14FF00003C4F292
|
||||
S11330F00C039A6822F001029A604FF00000BDE8C8
|
||||
S1073100F007704719
|
||||
S10B3104008000000048E8010E
|
||||
S11321FC7900790079007900790079007900790007
|
||||
S113220C79007900790079007900790079007900F6
|
||||
S113221C79007900790079007900790079007900E6
|
||||
S113222C8A007900790079007900790079007900C5
|
||||
S113223C79007900790079007900790079007900C6
|
||||
S113224C79007900790079007900790079007900B6
|
||||
S113225C79007900790079007900790079007900A6
|
||||
S113226C7900790079007900790079007900790096
|
||||
S113227C7900790079007900790079007900790086
|
||||
S113228C790079007900EE00790079007900790001
|
||||
S113229C79007900790079007900790090001A01AD
|
||||
S11322AC79007900790079001A01790079007900B4
|
||||
S11322BC7900AB000201DB0079007900B7007900EA
|
||||
S11322CC110179007900F00040F21073C2F200039E
|
||||
S11322DC1D68002D00F09F81CDF8008003AB0193A5
|
||||
S11322EC394632465346A84795E138464FF0250106
|
||||
S11322FC00F07CFC8FE1039B03F1040203921D7834
|
||||
S113230C0AF1FF3A304651463A4600F09DFC3846F5
|
||||
S113231C294600F06BFC16F0100F00F07C814FF096
|
||||
S113232C200051463A4600F07DFC74E116F0080F8B
|
||||
S113233C039B03F1040203921B683A6814BF1A70DE
|
||||
S113234C1A6068E1039B03F104020392D3F8009032
|
||||
S113235C484600F0C9FC05468045ACBF0023012368
|
||||
S113236C03EA1623002B18BF4546C5EB0A0A304670
|
||||
S113237C51463A4600F068FC002DCCD019F8011BEC
|
||||
S113238C384600F033FC013DF8D1C4E7039B03F15C
|
||||
S113239C040203921B6806F08009B9F1000F14BF04
|
||||
S11323AC4FF023094FF0000946F480764FF00808EB
|
||||
S11323BC69E046F4005643F2780343F2580978284E
|
||||
S11323CC08BF994616F0800F08BF4FF0000916F4A9
|
||||
S11323DC807F18BF26F400761EE006F08009B9F160
|
||||
S11323EC000F14BF4FF030094FF0000916F4807F32
|
||||
S11323FC18BF26F400760FE016F4807F1CBF26F479
|
||||
S113240C00764FF0000907D104E046F480464FF003
|
||||
S113241C000901E04FF0000916F4804F1DD0039B16
|
||||
S113242C03F1040203921B6816F0040F18BF1BB2CD
|
||||
S113243C03D116F0080F18BFDBB2002BBCBF5B42F4
|
||||
S113244C4FF02D091ADB06F04002002A18BF4FF09A
|
||||
S113245C200916F0200F11D00EE0039B03F10402A7
|
||||
S113246C03921B6816F0040F18BF9BB206D116F02A
|
||||
S113247C080F18BFDBB201E04FF02B0916F4807F74
|
||||
S113248C04D026F4007616F4807F01D14FF00108B5
|
||||
S113249CA0F15800202870D8DFE800F0196F6F6F96
|
||||
S11324AC6F6F6F6F6F6F6F6F156F6F6F6F156F6FE0
|
||||
S11324BC6F6F6F11196F6F6F6F156F6F19004FF08E
|
||||
S11324CC00050BBB5BE04FF0000553BB57E04FF02E
|
||||
S11324DC0005002B53D04FF0000506F40052DDF834
|
||||
S11324EC08E032B103F00F011EF8010004A968548E
|
||||
S11324FC05E003F00F011BF8010004A9685405F171
|
||||
S113250C01051B09EDD13AE04FF0000503F007017A
|
||||
S113251C01F1300104AAA95405F10105DB08F5D138
|
||||
S113252C2DE04FF0000506F4004C4CF6CD4ECCF6E5
|
||||
S113253CCC4E6246A446144654B105F00302032A59
|
||||
S113254C01BF07A842192C2102F80C1C08BF013545
|
||||
S113255C07AA5119AEFB03024FEAD20202EB820026
|
||||
S113256CA3EB400303F1300301F80C3C05F1010526
|
||||
S113257C1346002AE0D1644601E04FF00005C5EB98
|
||||
S113258C080828EAE878C8EB0A0AC5EB0A0AB9F184
|
||||
S113259CFF0F88BF0AF1FF3AB9F1000F01D00AF11D
|
||||
S11325ACFF3A16F4007F06D1304651463A4600F005
|
||||
S11325BC4BFB4FF0000AB9F1FF0F04D9C9F3072103
|
||||
S11325CC384600F013FBB9F1000F04D05FFA89F11F
|
||||
S11325DC384600F00BFB304651463A4600F034FBCB
|
||||
S11325EC4FF0300041463A4600F01CFB012D09D453
|
||||
S11325FC0DF11008454415F8011D384600F0F6FAA3
|
||||
S113260C4545F8D116F0100F05D04FF02000514677
|
||||
S113261C3A4600F007FB217800297FF43AADBB68F9
|
||||
S113262C2BB13A6879688A423CBF002199543868C6
|
||||
S113263C01E04FF0FF3007B0BDE8F08F10B5044651
|
||||
S113264C0B783BB1B0F1FF3F06D04B6803F1FF337D
|
||||
S113265C4B6001E08B689847204610BD2DE9F04F84
|
||||
S113266C82468B4617469846099E4FF0FF3900E088
|
||||
S113267CA94609F10105504600F0A4FA044600F0FD
|
||||
S113268C27FB0028F4D12346B4F1FF3F08BF4FF0D9
|
||||
S113269CFF3500F09C8027F4C067002E4EDD17F048
|
||||
S11326AC800F0DD02B2C03D02D2C09D147F480672F
|
||||
S11326BC09F10205504600F085FA044606F1FF368E
|
||||
S11326CC302C14BF00230123002ED4BF002303F0AD
|
||||
S11326DC0103002B32D047F4007706F1FF3605F1E5
|
||||
S11326EC0109504600F06EFA0446002E20DD5828ED
|
||||
S11326FC14BF00230123782808BF43F00103BBB1A6
|
||||
S113270CB8F1100F14BF00230123B8F1000F08BF58
|
||||
S113271C43F0010363B127F4007706F1FF3605F1AA
|
||||
S113272C0209504600F04EFA04464FF0100851E0EE
|
||||
S113273CB8F1000F08BF4FF008084BE0B8F1000FD8
|
||||
S113274C08BF4FF00A08002ED8BF4FF000090EDC6A
|
||||
S113275C15E047F4007706F1FF3608FB090905F18B
|
||||
S113276C0105504600F02EFA044616B907E04FF066
|
||||
S113277C00092046414600F08DFA0028E9DA20468B
|
||||
S113278C5146FFF75BFF17F4007F08BF6FF001059C
|
||||
S113279C1DD017F0010F1AD1DBF8003003F104023D
|
||||
S11327ACCBF800201B6807F49062B2F5906F08BF59
|
||||
S11327BCC9F1000917F0100F18BF83F8009006D167
|
||||
S11327CC17F0080F14BFA3F80090C3F80090284624
|
||||
S11327DCBDE8F08F4D46B6E72DE9F04F85B001907A
|
||||
S11327EC8A4604924FF0000BCDF808B04CF6CC4955
|
||||
S11327FCC0F6CC49544614F8015B002D00F0DE8180
|
||||
S113280C252D3BD0284600F063FA08B918E02C4675
|
||||
S113281C04F10105207800F05BFA0028F7D101E0FF
|
||||
S113282C0BF1010B019800F0CDF9054600F050FABC
|
||||
S113283C0028F5D128460199FFF700FFA246D9E7F5
|
||||
S113284C019800F0BFF90646A84203D10BF1010B25
|
||||
S113285CA246CFE70199FFF7F1FE029AD2F10103E8
|
||||
S113286C38BF0023B6F1FF3F14BF002603F0010666
|
||||
S113287C002E18BF4FF0FF3202929FE19AF80130FC
|
||||
S113288C2A2B06BF0AF102044FF001084FF000088E
|
||||
S113289C4FF000050CE04D4500F3908105EB8505E8
|
||||
S11328ACA6F1300616EB450500F1888148F02008A6
|
||||
S11328BC274604F101043E78A246304600F0E2F9C2
|
||||
S11328CC0028E8D1414608F02002002A08BF6FF026
|
||||
S11328DC00454C2E05D17E7807F1020A48F04408D5
|
||||
S11328EC0EE0682E0CD17E78682E03BF48F01008D9
|
||||
S11328FCBE7807F1030A07F1020A18BF41F0080871
|
||||
S113290CA6F12506532E00F25981DFE816F0540087
|
||||
S113291C57015701570157015701570157015701E7
|
||||
S113292C57015701570157015701570157015701D7
|
||||
S113293C57015701570157015701570157015701C7
|
||||
S113294C57015701570157015701570157015701B7
|
||||
S113295C57015701570157015701570157015701A7
|
||||
S113296C5701570157015701570157015701570197
|
||||
S113297C57015701330157015701570157015701AB
|
||||
S113298C5701570157015701570170009F00570118
|
||||
S113299C570157015701AA00570157015701570115
|
||||
S11329ACB500CD00D80057015701E30057012801A9
|
||||
S11329BC570157013301019800F004F90446252806
|
||||
S11329CC02D10BF1010B15E70199FFF737FE029ABF
|
||||
S11329DC131C18BF0123B4F1FF3F0CBF1C4643F07A
|
||||
S11329EC0104002C08BF4FF0FF320292E6E008F01D
|
||||
S11329FC2003002B08BF012518F0010401BF049B20
|
||||
S1132A0C1A1D04921E6818BF0026002D00F0D680F3
|
||||
S1132A1C002D13DD019800F0D5F8B0F1FF3F06D17D
|
||||
S1132A2C029B002B08BF4FF0FF330293C6E00CB996
|
||||
S1132A3C06F8010B0BF1010B013DEBD1002C7FF4DB
|
||||
S1132A4CD9AE029B03F101030293D3E648F0800252
|
||||
S1132A5C0095019804A94FF00A03FFF7FFFD044603
|
||||
S1132A6C92E048F080020095019804A94FF000030D
|
||||
S1132A7CFFF7F4FD044687E018F0010F7FF4BAAEBB
|
||||
S1132A8C049B03F1040204921B6818F0100F18BF86
|
||||
S1132A9C83F800B07FF4AEAE18F0080F14BFA3F89F
|
||||
S1132AAC00B0C3F800B0A5E648F080020095019888
|
||||
S1132ABC04A94FF00803FFF7D1FD044664E028F0A5
|
||||
S1132ACC1E020095019804A94FF01003FFF7C6FDF0
|
||||
S1132ADC044659E04FF0FF3404F10104019800F06E
|
||||
S1132AEC71F8064600F0F4F80028F5D1B6F1FF3F72
|
||||
S1132AFC08BF4FF0FF3447D018F0010701BF049B07
|
||||
S1132B0C1A1D04921B680EBF039300220392002D1E
|
||||
S1132B1C16DC1AE005F1FF351FB9039B03F8016BB2
|
||||
S1132B2C039304F10104019800F04CF80646431C8D
|
||||
S1132B3C18BF0123002DD4BF002303F0010323B1DC
|
||||
S1132B4C304600F0C5F80028E4D030460199FFF770
|
||||
S1132B5C75FDCFB94FF00002039B1A7014E048F0D6
|
||||
S1132B6C80020095019804A94FF00A03FFF776FD43
|
||||
S1132B7C044609E048F080020095019804A94FF03E
|
||||
S1132B8C1003FFF76BFD0446002C0FDA029A131C9A
|
||||
S1132B9C18BF0123B4F1FF3F0CBF1C4643F00104E2
|
||||
S1132BAC002C08BF4FF0FF32029207E018F0010F1F
|
||||
S1132BBC02BF029B01330293A3441BE6029805B0A7
|
||||
S1132BCCBDE8F08F00B5034602783AB1426810783C
|
||||
S1132BDC40B102F101025A605DF804FB4368984766
|
||||
S1132BEC5DF804FB4FF0FF305DF804FB30B5044690
|
||||
S1132BFCC8B2A16849B12368626803F10105954222
|
||||
S1132C0C08BF0020934238BFC854E3682BB1216835
|
||||
S1132C1C6268914201D221469847236803F101036B
|
||||
S1132C2C236030BDF0B5154601290BD40E464FF088
|
||||
S1132C3C0004C7B228463946FFF7D8FF04F1010453
|
||||
S1132C4CB442F7D1F0BD00BF00B510F0100F07D19E
|
||||
S1132C5C00F4007000280CBF20203020FFF7E2FFA6
|
||||
S1132C6C5DF804FBA0F1410019288CBF0020012061
|
||||
S1132C7C704700BFA0F1610019288CBF002001200F
|
||||
S1132C8C704700BFA0F1300009288CBF0020012040
|
||||
S1132C9C704700BF30B504460D46FFF7F3FF10B183
|
||||
S1132CACA4F130000FE02046FFF7E4FF10B1A4F1CB
|
||||
S1132CBC570008E02046FFF7D5FF10B1A4F1370008
|
||||
S1132CCC01E04FF0FF30A842A8BF4FF0FF3030BDF9
|
||||
S1132CDCA0F10903202814BF00200120042B98BF65
|
||||
S1132CEC40F00100704700BF00F1010110F0030F28
|
||||
S1132CFC11D010F8012B002A23D010F0030F0AD0A6
|
||||
S1132D0C10F8012B002A1CD010F0030F03D010F87C
|
||||
S1132D1C012B002A15D02DE970004FF001324FF031
|
||||
S1132D2C803350F8044BA4EB020525EA04051D403E
|
||||
S1132D3C00D1F6E7A0F1040070BC10F8012B002AB6
|
||||
S1132D4CFBD1A0EB0100704700B503B400F008F808
|
||||
S1132D5C03BC02B4694609BE00F004F801BC00BD12
|
||||
S10B2D6C704700BF704700BF6F
|
||||
S1132D74443A2F7573722F6665617365722F736F8E
|
||||
S1132D846674776172652F4F70656E424C542F548C
|
||||
S1132D9461726765742F44656D6F2F41524D434DC5
|
||||
S1132DA4335F45464D33325F4F6C696D65785F45DB
|
||||
S1132DB44D3332473838304631323853544B5F43FD
|
||||
S1132DC4726F7373776F726B732F426F6F742F69A3
|
||||
S1132DD464652F2E2E2F2E2E2F2E2E2F2E2E2F5374
|
||||
S1132DE46F757263652F41524D434D335F45464DB4
|
||||
S1132DF433322F43726F7373776F726B732F7665ED
|
||||
S1132E0463746F72732E630000400000002000009E
|
||||
S1132E140200000000600000002000000300000025
|
||||
S1132E2400800000002000000400000000A0000056
|
||||
S1132E34002000000500000000C000000020000085
|
||||
S1132E440600000000E0000000200000070000006D
|
||||
S1132E540000010000200000080000000020010020
|
||||
S1132E6400200000090000000040010000200000D0
|
||||
S1132E740A00000000600100002000000B000000B4
|
||||
S1132E8400800100002000000C00000000A00100EC
|
||||
S1132E94002000000D00000000C00100002000001C
|
||||
S1132EA40E00000000E00100002000000F000000FC
|
||||
S1132EB40500000000000000802500000000000060
|
||||
S1132EC40000000000000000443A2F7573722F665E
|
||||
S1132ED465617365722F736F6674776172652F4FC2
|
||||
S1132EE470656E424C542F5461726765742F446547
|
||||
S1132EF46D6F2F41524D434D335F45464D33325F21
|
||||
S1132F044F6C696D65785F454D33324738383046C8
|
||||
S1132F1431323853544B5F43726F7373776F726BF0
|
||||
S1132F24732F426F6F742F6964652F2E2E2F2E2EEC
|
||||
S1132F342F2E2E2F2E2E2F536F757263652F415211
|
||||
S1132F444D434D335F45464D33322F756172742EB4
|
||||
S1132F54630000004F70656E424C540030313233CC
|
||||
S1132F6434353637383961626364656630313233F7
|
||||
S10F2F7434353637383941424344454671
|
||||
S1132F804FF00003C4F20C039A6842F001029A6005
|
||||
S1132F9018614FF00102DA60DB6913F0040F0AD004
|
||||
S1132FA04FF00003C4F20C039A6822F001029A6005
|
||||
S1132FB04FF0FF3070474FF00003C4F20C03DB699D
|
||||
S1132FC013F0020F0AD04FF00003C4F20C039A6806
|
||||
S1132FD022F001029A606FF0010070474FF0000385
|
||||
S1132FE0C4F20C034FF00202DA60DB6913F0010F44
|
||||
S1132FF01CD049F28063C0F298034FF00001C4F280
|
||||
S11330000C0103F1FF33CA6912F0010F02D0002B47
|
||||
S1133010F7D100E053B94FF00003C4F20C039A68EF
|
||||
S113302022F001029A606FF0020070474FF0000333
|
||||
S1133030C4F20C039A6822F001029A604FF0000077
|
||||
S1133040704700BF2DE9F0074FF00003C4F20C03F2
|
||||
S11330509C6844F001049C604FEAA207002F40F3EF
|
||||
S11330608C8080464FF00003C4F20C0318614FF0CB
|
||||
S11330700102DA60DB6913F0040F21D14FF0000381
|
||||
S1133080C4F20C03DB6913F0020F33D14FF00404D4
|
||||
S11330904FF0000A55465246C4F20C0249F28066CB
|
||||
S11330A0C0F298064FF0080C4FF001091BE004EB46
|
||||
S11330B008031361C2F80C90D36913F0040F0AD00B
|
||||
S11330C04FF00003C4F20C039A6822F001029A60E4
|
||||
S11330D04FF0FF305BE0D36904F1040013F0020FFA
|
||||
S11330E008D1A2460446D36913F0080F08BF33463B
|
||||
S11330F00BD01FE04FF00003C4F20C039A6822F0D7
|
||||
S113310001029A606FF0010041E003F1FF33D069DE
|
||||
S113311010F0080F02D1002BF7D100E053B94FF0A3
|
||||
S11331200003C4F20C039A6822F001029A606FF063
|
||||
S113313002002CE051F80A309361C2F80CC0D36944
|
||||
S113314013F0010F15D0334603F1FF33D06910F0AB
|
||||
S1133150010F02D0002BF7D100E053B94FF0000368
|
||||
S1133160C4F20C039A6822F001029A606FF0020024
|
||||
S11331700DE005F10105BD4299D14FF00003C4F201
|
||||
S11331800C039A6822F001029A604FF00000BDE837
|
||||
S1073190F007704789
|
||||
S10B3194008000000048E8017E
|
||||
S9030155A6
|
||||
|
|
|
@ -26,7 +26,6 @@
|
|||
<ProjectSessionItem path="EFM32G880_crossworks;openbtl_olimex_efm32g880;Source Files" name="unnamed" />
|
||||
<ProjectSessionItem path="EFM32G880_crossworks;openbtl_olimex_efm32g880;Source Files;Source" name="unnamed" />
|
||||
<ProjectSessionItem path="EFM32G880_crossworks;openbtl_olimex_efm32g880;Source Files;Source;ARMCM3_EFM32" name="unnamed" />
|
||||
<ProjectSessionItem path="EFM32G880_crossworks;openbtl_olimex_efm32g880;Source Files;Source;ARMCM3_EFM32;Crossworks" name="unnamed" />
|
||||
</Project>
|
||||
<Register1>
|
||||
<RegisterWindow openNodes="" binaryNodes="" hiddenNodes="" unsignedNodes="" visibleGroups="" decimalNodes="" octalNodes="" asciiNodes="" />
|
||||
|
@ -58,7 +57,7 @@
|
|||
</Watch4>
|
||||
<Files>
|
||||
<SessionOpenFile useTextEdit="1" useBinaryEdit="0" codecName="Latin1" x="0" debugPath="D:\usr\feaser\software\OpenBLT\Target\Demo\ARMCM3_EFM32_Olimex_EM32G880F128STK_Crossworks\Boot\main.c" y="72" path="D:\usr\feaser\software\OpenBLT\Target\Demo\ARMCM3_EFM32_Olimex_EM32G880F128STK_Crossworks\Boot\main.c" left="0" selected="0" name="unnamed" top="36" />
|
||||
<SessionOpenFile useTextEdit="1" useBinaryEdit="0" codecName="Latin1" x="0" debugPath="D:\usr\feaser\software\OpenBLT\Target\Source\ARMCM3_EFM32\uart.c" y="37" path="D:\usr\feaser\software\OpenBLT\Target\Source\ARMCM3_EFM32\uart.c" left="0" selected="1" name="unnamed" top="15" />
|
||||
<SessionOpenFile useTextEdit="1" useBinaryEdit="0" codecName="Latin1" x="0" debugPath="D:\usr\feaser\software\OpenBLT\Target\Source\ARMCM3_EFM32\uart.c" y="31" path="D:\usr\feaser\software\OpenBLT\Target\Source\ARMCM3_EFM32\uart.c" left="0" selected="1" name="unnamed" top="31" />
|
||||
</Files>
|
||||
<ARMCrossStudioWindow activeProject="openbtl_olimex_efm32g880" autoConnectTarget="Olimex ARM-USB-TINY" debugSearchFileMap="" fileDialogInitialDirectory="D:\usr\feaser\software\OpenBLT\Target\Source\ARMCM3_EFM32\Crossworks" fileDialogDefaultFilter="*.c" autoConnectCapabilities="388991" debugSearchPath="" buildConfiguration="THUMB Flash Debug" />
|
||||
</session>
|
||||
|
|
|
@ -92,10 +92,20 @@ static void Init(void)
|
|||
CMU->HFCORECLKEN0 |= 0x0F;
|
||||
CMU->HFPERCLKEN0 |= 0xFFFF;
|
||||
/* disable clocking of the modules that are not in use */
|
||||
CMU_ClockEnable(cmuClock_AES | cmuClock_DMA | cmuClock_EBI | cmuClock_PRS, false);
|
||||
CMU_ClockEnable(cmuClock_USART0 | cmuClock_USART1 | cmuClock_USART2, false);
|
||||
CMU_ClockEnable(cmuClock_UART0 | cmuClock_ACMP0 | cmuClock_ACMP1, false);
|
||||
CMU_ClockEnable(cmuClock_DAC0 | cmuClock_ADC0 | cmuClock_I2C0 | cmuClock_VCMP, false);
|
||||
CMU_ClockEnable(cmuClock_AES, false);
|
||||
CMU_ClockEnable(cmuClock_DMA, false);
|
||||
CMU_ClockEnable(cmuClock_EBI, false);
|
||||
CMU_ClockEnable(cmuClock_PRS, false);
|
||||
CMU_ClockEnable(cmuClock_USART0, false);
|
||||
CMU_ClockEnable(cmuClock_USART1, false);
|
||||
CMU_ClockEnable(cmuClock_USART2, false);
|
||||
CMU_ClockEnable(cmuClock_UART0, false);
|
||||
CMU_ClockEnable(cmuClock_ACMP0, false);
|
||||
CMU_ClockEnable(cmuClock_ACMP1, false);
|
||||
CMU_ClockEnable(cmuClock_DAC0, false);
|
||||
CMU_ClockEnable(cmuClock_ADC0, false);
|
||||
CMU_ClockEnable(cmuClock_I2C0, false);
|
||||
CMU_ClockEnable(cmuClock_VCMP, false);
|
||||
#if (BOOT_COM_UART_ENABLE > 0)
|
||||
/* enable power to U2 (RS232_PWR_E) */
|
||||
GPIO_PinModeSet(gpioPortB, 9, gpioModePushPullDrive, 1);
|
||||
|
|
Binary file not shown.
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -46,6 +46,8 @@ static void BootActivate(void)
|
|||
{
|
||||
void (*pEntryFromProgFnc)(void);
|
||||
|
||||
/* stop the timer interrupt */
|
||||
TimerDeinit();
|
||||
/* set pointer to the address of function EntryFromProg in the bootloader. note that
|
||||
* 1 is added to this address to enable a switch from Thumb2 to Thumb mode
|
||||
*/
|
||||
|
|
|
@ -56,7 +56,7 @@
|
|||
<Watches active="0" update="Never" />
|
||||
</Watch4>
|
||||
<Files>
|
||||
<SessionOpenFile useTextEdit="1" useBinaryEdit="0" codecName="Latin1" x="0" debugPath="D:\usr\feaser\software\OpenBLT\Target\Demo\ARMCM3_EFM32_Olimex_EM32G880F128STK_Crossworks\Prog\main.c" y="101" path="D:\usr\feaser\software\OpenBLT\Target\Demo\ARMCM3_EFM32_Olimex_EM32G880F128STK_Crossworks\Prog\main.c" left="0" selected="1" name="unnamed" top="51" />
|
||||
<SessionOpenFile useTextEdit="1" useBinaryEdit="0" codecName="Latin1" x="0" debugPath="D:\usr\feaser\software\OpenBLT\Target\Demo\ARMCM3_EFM32_Olimex_EM32G880F128STK_Crossworks\Prog\main.c" y="66" path="D:\usr\feaser\software\OpenBLT\Target\Demo\ARMCM3_EFM32_Olimex_EM32G880F128STK_Crossworks\Prog\main.c" left="0" selected="1" name="unnamed" top="51" />
|
||||
</Files>
|
||||
<ARMCrossStudioWindow activeProject="demoprog_olimex_efm32g880" autoConnectTarget="Olimex ARM-USB-TINY" debugSearchFileMap="" fileDialogInitialDirectory="D:\usr\feaser\software\OpenBLT\Target\Demo\ARMCM3_EFM32_Olimex_EM32G880F128STK_Crossworks\Prog" fileDialogDefaultFilter="*.c" autoConnectCapabilities="388991" debugSearchPath="" buildConfiguration="THUMB Flash Debug" />
|
||||
</session>
|
||||
|
|
|
@ -89,10 +89,20 @@ static void Init(void)
|
|||
CMU->HFCORECLKEN0 |= 0x0F;
|
||||
CMU->HFPERCLKEN0 |= 0xFFFF;
|
||||
/* disable clocking of the modules that are not in use */
|
||||
CMU_ClockEnable(cmuClock_AES | cmuClock_DMA | cmuClock_EBI | cmuClock_PRS, false);
|
||||
CMU_ClockEnable(cmuClock_USART0 | cmuClock_USART1 | cmuClock_USART2, false);
|
||||
CMU_ClockEnable(cmuClock_UART0 | cmuClock_ACMP0 | cmuClock_ACMP1, false);
|
||||
CMU_ClockEnable(cmuClock_DAC0 | cmuClock_ADC0 | cmuClock_I2C0 | cmuClock_VCMP, false);
|
||||
CMU_ClockEnable(cmuClock_AES, false);
|
||||
CMU_ClockEnable(cmuClock_DMA, false);
|
||||
CMU_ClockEnable(cmuClock_EBI, false);
|
||||
CMU_ClockEnable(cmuClock_PRS, false);
|
||||
CMU_ClockEnable(cmuClock_USART0, false);
|
||||
CMU_ClockEnable(cmuClock_USART1, false);
|
||||
CMU_ClockEnable(cmuClock_USART2, false);
|
||||
CMU_ClockEnable(cmuClock_UART0, false);
|
||||
CMU_ClockEnable(cmuClock_ACMP0, false);
|
||||
CMU_ClockEnable(cmuClock_ACMP1, false);
|
||||
CMU_ClockEnable(cmuClock_DAC0, false);
|
||||
CMU_ClockEnable(cmuClock_ADC0, false);
|
||||
CMU_ClockEnable(cmuClock_I2C0, false);
|
||||
CMU_ClockEnable(cmuClock_VCMP, false);
|
||||
#if (BOOT_COM_UART_ENABLE > 0)
|
||||
/* enable power to U2 (RS232_PWR_E) */
|
||||
GPIO_PinModeSet(gpioPortB, 9, gpioModePushPullDrive, 1);
|
||||
|
|
|
@ -57,6 +57,19 @@ void TimerInit(void)
|
|||
} /*** end of TimerInit ***/
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
** NAME: TimerDeinit
|
||||
** PARAMETER: none
|
||||
** RETURN VALUE: none
|
||||
** DESCRIPTION: Stops the timer.
|
||||
**
|
||||
****************************************************************************************/
|
||||
void TimerDeinit(void)
|
||||
{
|
||||
SysTick->CTRL = 0;
|
||||
} /*** end of TimerDeinit ***/
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
** NAME: TimerSet
|
||||
** PARAMETER: timer_value initialize value of the millisecond timer.
|
||||
|
|
|
@ -35,6 +35,7 @@
|
|||
* Function prototypes
|
||||
****************************************************************************************/
|
||||
void TimerInit(void);
|
||||
void TimerDeinit(void);
|
||||
void TimerSet(unsigned long timer_value);
|
||||
unsigned long TimerGet(void);
|
||||
void TimerISRHandler(void);
|
||||
|
|
Binary file not shown.
|
@ -0,0 +1,465 @@
|
|||
S02000006F70656E62746C5F6F6C696D65785F65666D3332673838302E7372656320
|
||||
S113000060070020C10D00004D1B00004D1B0000C7
|
||||
S11300104D1B00004D1B00004D1B00004D1B00003C
|
||||
S11300204D1B00004D1B00004D1B00004D1B00002C
|
||||
S11300304D1B00004D1B00004D1B00004D1B00001C
|
||||
S11300404D1B00004D1B00004D1B00004D1B00000C
|
||||
S11300504D1B00004D1B00004D1B00004D1B0000FC
|
||||
S11300604D1B00004D1B00004D1B00004D1B0000EC
|
||||
S11300704D1B00004D1B00004D1B00004D1B0000DC
|
||||
S11300804D1B00004D1B00004D1B00004D1B0000CC
|
||||
S11300904D1B00004D1B00004D1B00004D1B0000BC
|
||||
S11300A04D1B00004D1B00004D1B00004D1B0000AC
|
||||
S10B00B04D1B00004D1B000074
|
||||
S11300B8044B9D46C046C046C046C04600F069FE93
|
||||
S11300C801F09AF960070020890011EB401010F143
|
||||
S11300D8844002607047DFF89005006810F007015B
|
||||
S11300E80029012903D9891E012905D908E0C00876
|
||||
S11300F8C00050F0010003E0C008C00050F0030045
|
||||
S1130108DFF8641508607047B0FA80F0D0F11F007A
|
||||
S11301187047DFF854150968DFF85025821ADFF8AC
|
||||
S113012850359A420DD211F00702921E012A04D8C2
|
||||
S1130138C908C90051F0030103E0C908C90051F016
|
||||
S11301480101DFF8282590420BD211F00700801E28
|
||||
S1130158012804D8C808C00050F0020101E0C90809
|
||||
S1130168C900DFF8040501607047DFF80805704727
|
||||
S113017880B5DFF8040500F09EF9C0B2072804D062
|
||||
S1130188082805D100F0AFFA03E0FFF7EEFF00E01E
|
||||
S1130198002002BD80B5DFF8E4140968C0B240004D
|
||||
S11301A831FA00F010F0030000280FD0022806D01E
|
||||
S11301B802D3032806D00BE000F0CFFA09E000F0E0
|
||||
S11301C8CFFA06E000F084FA400802E0002000E0DC
|
||||
S11301D8002002BDDFF8A8140968C90704D4DFF8B1
|
||||
S11301E8A41409680142FAD1704710B50C00C0F391
|
||||
S11301F80311012907D0C0F09A80032925D010D310
|
||||
S1130208042967D093E02000FFF77EFF0400DFF89D
|
||||
S113021880040068000900012043DFF874140860B2
|
||||
S113022885E0FFF758FF2000FFF76EFF0400DFF8B2
|
||||
S113023864040068000900012043DFF858140860CA
|
||||
S113024800F046FAFFF765FF71E0DFF84C148842C6
|
||||
S113025808D0DFF84814884215D0DFF848148842DB
|
||||
S113026823D036E00420FFF7B5FF2000FFF74CFF4A
|
||||
S11302780400DFF82C040068000900012043DFF8BB
|
||||
S11302882014086025E00420FFF7A4FF2000FFF7EE
|
||||
S11302983BFF0400DFF80804006830F0F00050EA7F
|
||||
S11302A80410DFF8FC13086013E00420FFF792FF42
|
||||
S11302B82000FFF729FF0400DFF8E403006830F4A6
|
||||
S11302C84070B4F1100150EA0120DFF8D41308603B
|
||||
S11302D8FFE72CE0DFF8D013884204D0DFF8CC1312
|
||||
S11302E8884211D022E04020FFF774FF2000FFF776
|
||||
S11302F80BFF0400DFF8B80300688008800020437F
|
||||
S1130308DFF8AC13086011E04020FFF763FF20001A
|
||||
S1130318FFF7FAFE0400DFF89803006830F03000B5
|
||||
S113032850EA0410DFF888130860FFE7FFE710BD00
|
||||
S113033870B50C000021C0F30322D2B2012A09D0FF
|
||||
S113034829D3032A19D015D3052A1DD018D3062A70
|
||||
S11303581ED020E0DFF83853C0F30436002902D059
|
||||
S11303680800FFF737FFE4B2220031002800FFF746
|
||||
S1130378ABFE70BDDFF83C53EEE7DFF83C53EBE728
|
||||
S1130388DFF838530121E7E7DFF834531021E3E7B6
|
||||
S1130398DFF83053E0E7ECE780B510F47810002874
|
||||
S11303A824D0B0F5003F24D0B0F5802F2AD0B0F582
|
||||
S11303B8C02F2AD0B0F5002F2BD0B0F5202F32D083
|
||||
S11303C8B0F5402F39D0B0F5602F41D0B0F5901F6B
|
||||
S11303D851D0B0F5A01F52D0B0F5B01F59D0B0F528
|
||||
S11303E8C01F60D0B0F5D01F60D062E000F07BF988
|
||||
S11303F860E000F078F9DFF89812096811F00F014D
|
||||
S1130408C84057E000F064F954E00020FFF7C2FE4A
|
||||
S113041850E00020FFF7BEFEDFF88412096811F0EF
|
||||
S11304280F01C84046E00020FFF7B4FEDFF8701261
|
||||
S11304380968C1F30311C8403CE00020FFF7AAFE95
|
||||
S1130448DFF85C120968090A11F00301C84031E0B9
|
||||
S11304580020FFF79FFEDFF848120968090A11F027
|
||||
S11304680301C840DFF86012096811F00701491C4C
|
||||
S1130478B0FBF1F01EE00120FFF78CFE1AE001202A
|
||||
S1130488FFF788FEDFF82812096811F00301C84055
|
||||
S113049810E00120FFF77EFEDFF814120968C1F3AB
|
||||
S11304A80111C84006E0FFF763FE03E0FFF75DFEB5
|
||||
S11304B800E0002002BD012110F00F00012806D041
|
||||
S11304C836D303282DD018D304282FD030E0DFF8F2
|
||||
S11304D8BC01006810F47050B0F5006F09D0B0F595
|
||||
S11304E8805F04D0B0F5005F05D1022104E0032148
|
||||
S11304F802E0042100E005211BE0DFF88001006828
|
||||
S113050810F00300012804D009D3032805D002D32E
|
||||
S113051805E0032104E0022102E0062100E00121B4
|
||||
S113052807E0DFF858010068012102E0072100E034
|
||||
S113053800210800C0B2704738B50324032310F023
|
||||
S11305480F000200521E03D0521E012A27D956E07A
|
||||
S1130558C9B2022906D021D3042919D015D30529F3
|
||||
S113056819D01BE004240023012201211800C0B281
|
||||
S113057800F046F8FFF7AFFD4348046000F00CF9BB
|
||||
S113058800F0A6F8FFF7C5FD39E003240123EBE7E3
|
||||
S113059802240223E8E701240323E5E72FE00228E5
|
||||
S11305A801D1002400E00224C9B2012906D002299D
|
||||
S11305B80FD0032914D0062919D01FE000202F4991
|
||||
S11305C809680322A2409143A04008432B490860CC
|
||||
S11305D815E001220121002000F012F80220EEE7C4
|
||||
S11305E801220121012000F00BF80120E7E7012294
|
||||
S11305F802213148FFF768FD0320E0E7FFE731BD3A
|
||||
S113060810B5C0B2002821D0022813D01AD3042868
|
||||
S113061814D022D2012302240220C9B200291DD0F9
|
||||
S11306282A490B60D2B2002A1AD018490968014233
|
||||
S113063816D1FAE7042308240820EEE7102320241F
|
||||
S11306482020EAE7402380248020E6E74FF48073E3
|
||||
S11306584FF400744FF40070DFE703E01B480460B4
|
||||
S113066800F09AF810BD000004000C400124F400C6
|
||||
S11306780024F400809FD5000400180028800C4052
|
||||
S113068854800C4050800C4024800C402C800C403A
|
||||
S113069808800C4004800C403004080030140A0020
|
||||
S11306A868800C4030000C0040051400401516000A
|
||||
S11306B870800C4044800C4040800C4058800C40B2
|
||||
S11306C860800C4078800C407C800C4020800C407A
|
||||
S11306D880B500F008F82449096811F00F01C840F2
|
||||
S11306E82249086002BD2248006810F47050B0F531
|
||||
S11306F8006F0BD0B0F5805F05D0B0F5005F08D16E
|
||||
S11307081C48006827E04FF4004024E01A480068B9
|
||||
S113071821E01A48006810F4E060002818D0B0F509
|
||||
S1130728807F13D0B0F5007F0ED0B0F5407F09D09C
|
||||
S1130738B0F5806F04D0B0F5A06F0BD110480AE073
|
||||
S1130748104808E0104806E0104804E0104802E0A9
|
||||
S1130758104800E00020704770474FF4004070478D
|
||||
S1130768044800687047000004800C4054060020C8
|
||||
S11307782C800C40700100206C0100200C800C407F
|
||||
S1130788003FAB01406F4001809FD500C0D8A7004F
|
||||
S1130798C0CF6A0040420F0002480349096801803B
|
||||
S11307A870470000580600202C800C40DFF800F049
|
||||
S11307B889000020DFF800F00100002080B500F077
|
||||
S11307C845FADFF878045FF0FF310160DFF8700460
|
||||
S11307D85FF0FF31016001BD70B504000D00160023
|
||||
S11307E8200000F0C8F9FF2805D02819401E00F0A1
|
||||
S11307F8C2F9FF2801D1002019E0600A4FF4007102
|
||||
S11308084843DFF840140968884208D12B009BB29A
|
||||
S113081832002100DFF8280400F0E9F807E02B0093
|
||||
S11308289BB232002100DFF8140400F0E0F870BD38
|
||||
S113083870B504000D00200000F09DF90600281989
|
||||
S1130848401E00F098F9F6B2FF2E02D0C0B2FF287D
|
||||
S113085801D1002005E00100C9B23000C0B200F0A7
|
||||
S113086849F970BD80B500200090DFF8D403006812
|
||||
S113087810F1010F01D1012037E00098DFF8C0130F
|
||||
S11308884968081800900098DFF8B41389680818B4
|
||||
S113089800900098DFF8A813C96808180090009819
|
||||
S11308A8DFF89C130969081800900098DFF8901382
|
||||
S11308B84969081800900098DFF8841389690818B2
|
||||
S11308C800900098DFF87813C96908180090009818
|
||||
S11308D8C04300900098401C009000AA0421DFF84F
|
||||
S11308E864030068B830FFF777FF02BD0020DFF823
|
||||
S11308F85413096809680818DFF84813096849682F
|
||||
S11309080818DFF84013096889680818DFF83413F1
|
||||
S11309180968C9680818CB49096809690818C949E0
|
||||
S1130928096849690818C749096889690818C549D7
|
||||
S11309380968D1F8B8100818002801D1012000E08E
|
||||
S11309480020704780B5BE48006810F1010F06D03A
|
||||
S1130958BB4800F091F8002801D100200EE0B74808
|
||||
S1130968006810F1010F06D0B44800F085F800289B
|
||||
S113097801D1002002E000F07AF9012002BD80B51F
|
||||
S11309884FF40072B1FBF2F303FB1213002B01D0F6
|
||||
S113099800200BE002688A4201D1012006E00160D0
|
||||
S11309A84FF40072001D00F089F9012002BD38B52A
|
||||
S11309B804000D00A248844208D1A04C290020005C
|
||||
S11309C8FFF7DDFF002810D100200FE09D480068E4
|
||||
S11309D8854203D19A4C9B480568EFE7200000F054
|
||||
S11309E84BF80028EAD1002000E0200032BD2DE9B0
|
||||
S11309F8F04104000F0015001E00780A4FF400713E
|
||||
S1130A0801FB00F8206810F1010F07D141462000CE
|
||||
S1130A18FFF7B5FF002801D100202BE020684045EE
|
||||
S1130A2808D041462000FFF7C2FF0400002C01D182
|
||||
S1130A3800201FE02068381A0019071D00F054F937
|
||||
S1130A48201D381A4FF4007188420AD308F2002195
|
||||
S1130A582000FFF7ACFF0400002C01D1002009E0BE
|
||||
S1130A68271D287838707F1C6D1C761EB6B2012E9F
|
||||
S1130A78E4D20120BDE8F081F8B505000124286816
|
||||
S1130A8800F079F8C0B2FF2801D100201DE000264B
|
||||
S1130A9800E0761C802E16D2286810EB860715EB2A
|
||||
S1130AA886004068009000F01FF9042200A938006D
|
||||
S1130AB8FFF77CFE002801D0002404E03868009980
|
||||
S1130AC88842E6D000242000C0B2F2BD5E48007817
|
||||
S1130AD8C0B2472802D0C0B2492802D14FF40070EE
|
||||
S1130AE807E0C0B2482802D14FF4805001E04FF427
|
||||
S1130AF800607047F8B506000C00E4B2F6B2B442E0
|
||||
S1130B0801D2002036E04F48007AF6B2864205D377
|
||||
S1130B184C4890F8B000E4B2A04201D2002029E089
|
||||
S1130B28FFF7D4FF05003000C0B200F04EF806000D
|
||||
S1130B382000C0B200F049F807002000C0B200F05D
|
||||
S1130B4861F8C019401E801B401CB0FBF5F4002757
|
||||
S1130B5800E07F1CBFB2A4B2A7420AD200F0C4F8D6
|
||||
S1130B68BFB205FB0760FFF725FE0028F1D000207F
|
||||
S1130B7800E00120F2BD38B50400002500E06D1C3A
|
||||
S1130B88EDB20F2D1FD200F0AFF8EDB20C202D49B5
|
||||
S1130B9800FB051000688442F1D3EDB20C2029490A
|
||||
S1130BA800FB05100068EDB20C21264A01FB052163
|
||||
S1130BB8496808188442E2D2EDB20C20214900FBAE
|
||||
S1130BC80510007A00E0FF2032BD38B50400002586
|
||||
S1130BD800E06D1CEDB20F2D11D200F085F8EDB2D6
|
||||
S1130BE80C20184900FB0510007AE4B2A042F0D1A9
|
||||
S1130BF8EDB20C20134900FB0510006801E05FF01A
|
||||
S1130C08FF3032BD38B50400002500E06D1CEDB29C
|
||||
S1130C180F2D11D200F068F8EDB20C20094900FB41
|
||||
S1130C280510007AE4B2A042F0D1EDB20C200549D7
|
||||
S1130C3800FB0510406800E0002032BD740100206C
|
||||
S1130C4878030020D8190000FE81E00F10480068DE
|
||||
S1130C5850F001000E4908600E4841F671310160F8
|
||||
S1130C680B48006840084000094908607047084874
|
||||
S1130C78006850F001000649086006480021016038
|
||||
S1130C8803480068400840000149086070470000B4
|
||||
S1130C9808000C403C000C4080B500F032F80028F5
|
||||
S1130CA809D000F06EF804484FF40051016042F294
|
||||
S1130CB804000068804701BD08ED00E070B5040039
|
||||
S1130CC80D00160005E0287820706D1C641C00F0E7
|
||||
S1130CD80BF83000461E80B20128F4D270BD80B5EE
|
||||
S1130CE800F06AF801BD7047704780B5FFF766FDEC
|
||||
S1130CF801BD80B5FFF770FD02BD80B5FFF798FD13
|
||||
S1130D0802BD80B5FFF7F2FD02BD80B5FFF7AAFD6D
|
||||
S1130D18002801D1002001E0FFF714FE02BD10B441
|
||||
S1130D2850F8041B81B102681218001D50F8043BE6
|
||||
S1130D38DC0744BFA9F10104E31852F8044B43F853
|
||||
S1130D48044B091FF9D1EBE710BC704780B500A824
|
||||
S1130D5814490A88028000F03BF800F06FFA124840
|
||||
S1130D680078012802D100A800F05CF801BD80B524
|
||||
S1130D780E4800F0CEFA012802D10C4800F052F8CF
|
||||
S1130D8801BD704780B5C9B200F099FA00F044F883
|
||||
S1130D9801BD054801210170704703480021017015
|
||||
S1130DA870470000161400005D0600200C060020A1
|
||||
S1130DB880B500F028F802BD044B9D46C046C046E5
|
||||
S1130DC8C046C046FFF7E9FF00F016FB60070020A5
|
||||
S1130DD8DFF8240400210170DFF81C040021816479
|
||||
S1130DE8DFF81404002180F84310DFF80C04002114
|
||||
S1130DF8A0F84410DFF8000400218170DFF8F8033C
|
||||
S1130E08002141707047DFF8F0030078002801D111
|
||||
S1130E18002000E001207047DFF8DC03002180F89F
|
||||
S1130E284310704780B50178FF2918D100F08BF87A
|
||||
S1130E38DFF8C40390F84300012802D1102000F021
|
||||
S1130E4878F8DFF8B403012180F84310DFF8A80329
|
||||
S1130E58B0F94410DFF8A40300F053F801BDDFF83B
|
||||
S1130E689813097801294BD10178C92932D0CC29A2
|
||||
S1130E783FD0CF293AD0D0292FD0D12933D0D22965
|
||||
S1130E882ED0F32917D0F4290FD0F5290AD0F62942
|
||||
S1130E980ED0FA2912D0FC2913D0FD2914D0FE292A
|
||||
S1130EA815D029E000F0CDF8C2E700F0E9F8BFE773
|
||||
S1130EB800F0BCF8BCE700F005F9B9E700F09EF8CB
|
||||
S1130EC8B6E700F095F8B3E700F07AF8B0E700F079
|
||||
S1130ED868F8ADE700F027F9AAE700F03EF9A7E7BC
|
||||
S1130EE800F007F9A4E700F066F9A1E700F077F944
|
||||
S1130EF89EE700F08BF99BE7202000F01AF897E7AB
|
||||
S1130F08ACE780B589B2FFF73DFF01BD10B40023FB
|
||||
S1130F1802E00478E318401C0C00611E002CF8D190
|
||||
S1130F28DBB21360012010BC7047B3480021417044
|
||||
S1130F387047B149FE22CA70AF490871AE48022110
|
||||
S1130F48A0F84410704710B50400FFF7EEFFAA4854
|
||||
S1130F5801210170A848FF21C170A748002101712F
|
||||
S1130F68A548007950F01000A3490871A24800214F
|
||||
S1130F784171A148A049497941719F484021817133
|
||||
S1130F889D484021C1719C48002101729A48012161
|
||||
S1130F98417299480121817297480821A0F84410A8
|
||||
S1130FA810BD10B50400944800210170FFF7BDFF7F
|
||||
S1130FB89148FF21C17090480121A0F8441010BD48
|
||||
S1130FC88D49FF22CA708C4900220A718A498A4ACB
|
||||
S1130FD852784A71884900228A7187490022CA7165
|
||||
S1130FE8854900220A7284490622A1F844207047E0
|
||||
S1130FF810B504000020FFF79CFF10BD7E49FF22B6
|
||||
S1131008CA707D497E4A8A647B4900220A717A49FA
|
||||
S113101800224A71784900228A7177490722C1F867
|
||||
S1131028072075490822A1F8442070477249FF2215
|
||||
S1131038CA707149406888646F480121A0F8441057
|
||||
S1131048704710B504006078402803D32220FFF7C6
|
||||
S113105870FF14E0627892B26748816C6948FFF7C0
|
||||
S11310682DFE6548FF21C1706348806C61780818BB
|
||||
S1131078614988646078401C5F49A1F8440010BD48
|
||||
S113108810B504006078402803D32220FFF751FFED
|
||||
S113109817E0594861688164627892B25648816C55
|
||||
S11310A85848FFF70BFE5448FF21C1705248806C22
|
||||
S11310B861780818504988646078401C4E49A1F842
|
||||
S11310C8440010BD80B54C49FF22CA704E4A41689D
|
||||
S11310D84948806CFFF71AFF4749087146480021C0
|
||||
S11310E8417145480021817143480821A0F8441002
|
||||
S11310F801BD4149FF22CA703F4900220A713E4995
|
||||
S113110800224A713C4940228A713B490022CA7133
|
||||
S1131118394900220A72384900224A72364907229C
|
||||
S1131128A1F84420704780B5421C3F213248806CA6
|
||||
S1131138FFF7DFFD002803D13120FFF7FAFE0BE0AB
|
||||
S11311482D48FF21C1702C48806C3F302A4988649F
|
||||
S113115829480121A0F8441001BD10B504006078A5
|
||||
S11311683F2803D32220FFF7E4FE23E02248FF218F
|
||||
S1131178C17021480121A0F844106078002807D1E3
|
||||
S1131188FFF7C3FD002802D13120FFF7D2FE11E09A
|
||||
S1131198A21C61781848806CFFF7ABFD002803D1C6
|
||||
S11311A83120FFF7C6FE05E01348806C6178081803
|
||||
S11311B81149886410BD80B541680F48806CFFF7F9
|
||||
S11311C89CFD002803D13120FFF7B3FE06E00A484E
|
||||
S11311D8FF21C17008480121A0F8441001BD10B5D1
|
||||
S11311E80400FFF77CFD0448FF21C1700248012177
|
||||
S11311F8A0F8441010BD00007C0500207F050020E5
|
||||
S1131208681B0000800500208305002080B531207C
|
||||
S1131218FFF78FFE01BD50F8041B61B150F8042B91
|
||||
S1131228D30744BFA9F101039A18002342F8043BE9
|
||||
S1131238091FFAD1EFE770474163704700B585B0DD
|
||||
S113124800A85F49102200F0E3F801215D48FFF788
|
||||
S11312586FF8012304220621022000F016F9002366
|
||||
S113126801220721022000F010F901215648FFF756
|
||||
S11312785FF802215548FFF75FF901215448FEF74A
|
||||
S1131288B4FF01215248FFF753F800208DF80000FD
|
||||
S113129800A9504800F0ADF94FF4165200214D480A
|
||||
S11312A800F065F94C480321016004214948FFF71F
|
||||
S11312B8C3FF0521474800F081F905B000BD70B5AA
|
||||
S11312C804000D00EDB2412D03D36821434800F01A
|
||||
S11312D8C7F92800C0B200F05DF8012803D06B21DB
|
||||
S11312E83E4800F0BDF900260CE0FFF7FDFCB6B25D
|
||||
S11312F8305D00F04FF8012803D07321374800F01F
|
||||
S1131308AFF9761C2800C0B2B6B280B28642ECD3DC
|
||||
S113131870BD10B504003248007800280CD131485B
|
||||
S113132800F02AF8012805D12D48012101702E4822
|
||||
S113133800210170002010BD2B480078294940186D
|
||||
S1131348401C00F019F80128F4D127480078401C03
|
||||
S11313582549087024480078224909788842E9D147
|
||||
S11313682148027892B221492000FFF7A7FC1C48C3
|
||||
S1131378002101700120DEE710B5040000201C499B
|
||||
S11313880968490704D5134800F056F9207001206C
|
||||
S1131398C0B210BD80B517490968C90601D4002038
|
||||
S11313A80CE00100C9B20B4800F04CF901E0FFF76A
|
||||
S11313B89BFC10480068C006F9D5012002BD000056
|
||||
S11313C83C1B000000C202000023040003001200BA
|
||||
S11313D8401516000044084054440840D41A00003C
|
||||
S11313E85F060020C80500205E060020C90500200D
|
||||
S11313F82C4408400844084000F03EF9002801D075
|
||||
S113140800F03CF9002000F0BEF900F057FAFF00A4
|
||||
S1131418103A07D330B4B1E83810103AA0E83810BD
|
||||
S1131428F9D230BC530724BFB1E80810A0E808106B
|
||||
S113143844BF51F8043B40F8043BD20724BF31F8B9
|
||||
S1131448022B20F8022B44BF0B7803707047083A2C
|
||||
S113145807D3B1E80810083A40F8043B40F804CB35
|
||||
S1131468F7D25307E4E70000C0B224223B4B02FB47
|
||||
S11314780032126892089200C9B21143C0B2242201
|
||||
S1131488364B02FB00300160704770B4D2B2002AB8
|
||||
S113149812D0002B08D0C0B22424304D04FB0054D1
|
||||
S11314A801258D40256107E0C0B224242B4D04FB9F
|
||||
S11314B8005401258D406561082919D2C0B224243D
|
||||
S11314C8264D04FB005464680F250E00F6B2B600DE
|
||||
S11314D8B540AC43D2B20D00EDB2AD0012FA05F539
|
||||
S11314E82C43C0B224251D4E05FB00656C601AE030
|
||||
S11314F8C0B22424194D04FB0054A4680F250E001F
|
||||
S1131508083EF6B2B600B540AC43D2B20D00083D71
|
||||
S1131518EDB2AD0012FA05F52C43C0B224250F4EE6
|
||||
S113152805FB0065AC60D2B2002A14D1002B09D0A7
|
||||
S1131538C0B22422094B02FB0030012212FA01F145
|
||||
S1131548016108E0C0B22422044B02FB00300122EE
|
||||
S113155812FA01F1416170BC70470000006000405C
|
||||
S1131568026CD20702D4426C0A42FCD1704738B5E7
|
||||
S113157804001500002906D10C4884420ED10C48F9
|
||||
S1131588FEF70AFF01004801B0FBF5F5203DED0028
|
||||
S113159804212000FFF7E4FFE56031BD05488442DB
|
||||
S11315A801D10548ECE7F8E70000000000400840D6
|
||||
S11315B840051400004408404015160038B50400DE
|
||||
S11315C8C9B2CD4315F005056D00C9B20D4302211A
|
||||
S11315D82000FFF7C5FF656031BDC9B2002905D0F9
|
||||
S11315E8416C0029FCD10121016401E0002101645E
|
||||
S11315F8704738B504000D0002212000FFF7B0FF42
|
||||
S11316080A20606001212000FFF7E7FF206830F01E
|
||||
S11316181C00297B0843697B0843A97B0843206095
|
||||
S1131628AA6869682000FFF7A2FF28786060002193
|
||||
S11316382000FFF7D2FF31BD81688906FCD5C06957
|
||||
S1131648C0B2704738B504000D00A068C006FCD5C8
|
||||
S113165840212000FFF784FFEDB2A56231BD0000F0
|
||||
S113166880B5034A106003480160FFF73DFBFCE7BF
|
||||
S11316784C060020500600200120704710B5084988
|
||||
S113168879441C31074C7C441A34A14206D0081D05
|
||||
S11316980A68511888470146A142F8D110BD00BF15
|
||||
S11316A8700400009004000080B568480168080EC2
|
||||
S11316B800280DD16648026832F07002026065485D
|
||||
S11316C80268D200D2080260026872F060620260A6
|
||||
S11316D8080E042813D25F48016831F4FC510160F4
|
||||
S11316E85D48002101605D48002101605C480021DB
|
||||
S11316F801605C48002101605B480021016000A88A
|
||||
S113170800F0DEF89DF80000012811D19DF80100D1
|
||||
S1131718002804D15048016851F0020101609DF885
|
||||
S11317280100022804D24D48016851F0010101600A
|
||||
S11317384E4801684E48814224D24848016851F411
|
||||
S1131748904101604B480068000410F0FE4149488C
|
||||
S1131758006810F07F0051EA00414648006810F420
|
||||
S1131768FE4001434348006810F07F0001434248AB
|
||||
S1131778016042484249096801603848016831F407
|
||||
S11317889041016001BD80B500F005F800F0AEF8A5
|
||||
S113179800F0B6F8FCE780B5FEF7DEFFFFF784FF3C
|
||||
S11317A8012201210020FEF72BFF2B48006850F08E
|
||||
S11317B80F00294908602948006840F47F4050F028
|
||||
S11317C8FF002649086000212E48FEF7B1FD0021DC
|
||||
S11317D82D48FEF7ADFD00212C48FEF7A9FD002198
|
||||
S11317E82B48FEF7A5FD00212A48FEF7A1FD00219C
|
||||
S11317F82948FEF79DFD00212848FEF799FD0021A0
|
||||
S11318082748FEF795FD00212648FEF791FD0021A3
|
||||
S11318182548FEF78DFD00212448FEF789FD0021A7
|
||||
S11318282348FEF785FD00212248FEF781FD0021AB
|
||||
S11318382148FEF77DFD0123052209210120FFF738
|
||||
S113184824FE02210120FFF70FFE01BDFC81E00FF9
|
||||
S11318580CA00C4020600C4040800C4044800C409C
|
||||
S113186858800C4060800C4078800C40F081E00F78
|
||||
S113187800BA8A4CB481E00F342000402C40004068
|
||||
S1131888C881E00F000304000013040000330400BF
|
||||
S113189800A202000002020000120200002202005C
|
||||
S11318A800320200007202000082020000B202004C
|
||||
S11318B800E2020000F2020000D2020000F028B8A0
|
||||
S11318C80749096811F03F0101700649096811F0D8
|
||||
S11318D8F001054A1268C2F30312114341707047BC
|
||||
S11318E8E0FF0FE0E8FF0FE0ECFF0FE080B5FFF743
|
||||
S11318F8FAF900F013F8FFF7F8F9FFF727FA01BD32
|
||||
S113190880B5FFF7F1F9FFF732FA00F010F801BDDE
|
||||
S11319180746384600F022F8FBE7000080B50E4879
|
||||
S11319280121017000F024F800F001F801BD80B530
|
||||
S1131938FFF73EFA01280ED00748007801280AD19B
|
||||
S113194800F038F8322806D303480021017000F06B
|
||||
S113195820F8FFF7A1F901BD5C06002080B5C04658
|
||||
S1131968C046024A11001820ABBEFBE7260002005D
|
||||
S113197880B500F00EF8124843F2AF6101601148D7
|
||||
S113198800210160104805210160002000F00FF8D3
|
||||
S113199801BD0D480021016070470B480068C00371
|
||||
S11319A804D50A480088401C08490880704707493C
|
||||
S11319B80880704780B5FFF7F0FF0448008802BD2F
|
||||
S11319C814E000E018E000E010E000E05A0600200F
|
||||
S11319D8002000000020000001000000004000007A
|
||||
S11319E80020000002000000006000000020000049
|
||||
S11319F80300000000800000002000000400000034
|
||||
S1131A0800A00000002000000500000000C0000045
|
||||
S1131A18002000000600000000E000000020000094
|
||||
S1131A28070000000000010000200000080000007A
|
||||
S1131A38002001000020000009000000004001000F
|
||||
S1131A48002000000A0000000060010000200000DF
|
||||
S1131A580B00000000800100002000000C000000C2
|
||||
S1131A6800A00100002000000D00000000C00100DB
|
||||
S1131A78002000000E00000000E00100002000002B
|
||||
S1131A880F000000443A5C7573725C6665617365A7
|
||||
S1131A98725C736F6674776172655C4F70656E42D1
|
||||
S1131AA84C545C5461726765745C536F75726365FA
|
||||
S1131AB85C41524D434D335F45464D33325C494199
|
||||
S1131AC8525C766563746F72732E6300443A5C7576
|
||||
S1131AD873725C6665617365725C736F6674776153
|
||||
S1131AE872655C4F70656E424C545C5461726765F4
|
||||
S1131AF8745C536F757263655C41524D434D335F3B
|
||||
S1131B0845464D33325C756172742E6300000000E3
|
||||
S1131B1807F7FFFFEC040000740100200000000038
|
||||
S1131B28FFF1FFFF740100004000000000000020E6
|
||||
S1131B3800000000050000000000000080250000EF
|
||||
S1131B480000000080B540210148FFF789FD01BD70
|
||||
S1131B588C1A0000C046C046C046C046FFF74CFC7D
|
||||
S1131B684F70656E424C54005449554A126852F0FD
|
||||
S1131B780102534B1A60534A106053480122026011
|
||||
S1131B8852480068400708D54D480068400840009E
|
||||
S1131B984B4908605FF0FF3029E04C480068800733
|
||||
S1131BA808D54748006840084000454908607FF068
|
||||
S1131BB801001CE044480222026000E0491E434838
|
||||
S1131BC80068C00701D50029F8D1002908D13C488C
|
||||
S1131BD80068400840003A4908607FF0020006E0C7
|
||||
S1131BE837480068400840003549086000207047BD
|
||||
S1131BF830B4334B1B6853F00103314C236093100A
|
||||
S1131C08002200E0521C9A424FDA10EB82042D4D58
|
||||
S1131C182C602D4C012525602C4C2468640708D5BC
|
||||
S1131C282748006840084000254908605FF0FF30F5
|
||||
S1131C3842E0264C2468A40708D5214800684008D7
|
||||
S1131C4840001F4908607FF0010035E01B4C00E0AC
|
||||
S1131C58641E1E4D2D682D0701D4002CF8D1002CCC
|
||||
S1131C6808D11748006840084000154908607FF00B
|
||||
S1131C78020021E051F82240154D2C60124C082531
|
||||
S1131C8825600E4C00E0641E104D2D68ED0701D54B
|
||||
S1131C98002CF8D1002CB5D1094800684008400050
|
||||
S1131CA8074908607FF0020006E00548006840081C
|
||||
S1131CB8400003490860002030BC704780969800B3
|
||||
S1131CC808000C4010000C400C000C401C000C4098
|
||||
S10F1CD818000C400048E80100800000E7
|
||||
S9031B5D84
|
|
@ -0,0 +1,108 @@
|
|||
/****************************************************************************************
|
||||
| Description: bootloader configuration header file
|
||||
| File Name: config.h
|
||||
|
|
||||
|----------------------------------------------------------------------------------------
|
||||
| C O P Y R I G H T
|
||||
|----------------------------------------------------------------------------------------
|
||||
| Copyright (c) 2012 by Feaser http://www.feaser.com All rights reserved
|
||||
|
|
||||
|----------------------------------------------------------------------------------------
|
||||
| L I C E N S E
|
||||
|----------------------------------------------------------------------------------------
|
||||
| This file is part of OpenBLT. OpenBLT is free software: you can redistribute it and/or
|
||||
| modify it under the terms of the GNU General Public License as published by the Free
|
||||
| Software Foundation, either version 3 of the License, or (at your option) any later
|
||||
| version.
|
||||
|
|
||||
| OpenBLT is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
|
||||
| without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
|
||||
| PURPOSE. See the GNU General Public License for more details.
|
||||
|
|
||||
| You should have received a copy of the GNU General Public License along with OpenBLT.
|
||||
| If not, see <http://www.gnu.org/licenses/>.
|
||||
|
|
||||
| A special exception to the GPL is included to allow you to distribute a combined work
|
||||
| that includes OpenBLT without being obliged to provide the source code for any
|
||||
| proprietary components. The exception text is included at the bottom of the license
|
||||
| file <license.html>.
|
||||
|
|
||||
****************************************************************************************/
|
||||
#ifndef CONFIG_H
|
||||
#define CONFIG_H
|
||||
|
||||
/****************************************************************************************
|
||||
* C P U D R I V E R C O N F I G U R A T I O N
|
||||
****************************************************************************************/
|
||||
/* To properly initialize the baudrate clocks of the communication interface, typically
|
||||
* the speed of the crystal oscillator and/or the speed at which the system runs is
|
||||
* needed. Set these through configurables BOOT_CPU_XTAL_SPEED_KHZ and
|
||||
* BOOT_CPU_SYSTEM_SPEED_KHZ, respectively. To enable data exchange with the host that is
|
||||
* not dependent on the targets architecture, the byte ordering needs to be known.
|
||||
* Setting BOOT_CPU_BYTE_ORDER_MOTOROLA to 1 selects little endian mode and 0 selects
|
||||
* big endian mode.
|
||||
*/
|
||||
#define BOOT_CPU_XTAL_SPEED_KHZ (32000)
|
||||
#define BOOT_CPU_SYSTEM_SPEED_KHZ (14000)
|
||||
#define BOOT_CPU_BYTE_ORDER_MOTOROLA (0)
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
* C O M M U N I C A T I O N I N T E R F A C E C O N F I G U R A T I O N
|
||||
****************************************************************************************/
|
||||
/* The UART communication interface is selected by setting the BOOT_COM_UART_ENABLE
|
||||
* configurable to 1. Configurable BOOT_COM_UART_BAUDRATE selects the communication speed
|
||||
* in bits/second. The maximum amount of data bytes in a message for data transmission
|
||||
* and reception is set through BOOT_COM_UART_TX_MAX_DATA and BOOT_COM_UART_RX_MAX_DATA,
|
||||
* respectively. It is common for a microcontroller to have more than 1 UART interface
|
||||
* on board. The zero-based BOOT_COM_UART_CHANNEL_INDEX selects the UART interface.
|
||||
*
|
||||
*/
|
||||
#define BOOT_COM_UART_ENABLE (1)
|
||||
#define BOOT_COM_UART_BAUDRATE (9600)
|
||||
#define BOOT_COM_UART_TX_MAX_DATA (64)
|
||||
#define BOOT_COM_UART_RX_MAX_DATA (64)
|
||||
#define BOOT_COM_UART_CHANNEL_INDEX (1)
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
* B A C K D O O R E N T R Y C O N F I G U R A T I O N
|
||||
****************************************************************************************/
|
||||
/* It is possible to implement an application specific method to force the bootloader to
|
||||
* stay active after a reset. Such a backdoor entry into the bootloader is desired in
|
||||
* situations where the user program does not run properly and therefore cannot
|
||||
* reactivate the bootloader. By enabling these hook functions, the application can
|
||||
* implement the backdoor, which overrides the default backdoor entry that is programmed
|
||||
* into the bootloader. When desired for security purposes, these hook functions can
|
||||
* also be implemented in a way that disables the backdoor entry altogether.
|
||||
*/
|
||||
#define BOOT_BACKDOOR_HOOKS_ENABLE (0)
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
* N O N - V O L A T I L E M E M O R Y D R I V E R C O N F I G U R A T I O N
|
||||
****************************************************************************************/
|
||||
/* The NVM driver typically supports erase and program operations of the internal memory
|
||||
* present on the microcontroller. Through these hook functions the NVM driver can be
|
||||
* extended to support additional memory types such as external flash memory and serial
|
||||
* eeproms. The size of the internal memory in kilobytes is specified with configurable
|
||||
* BOOT_NVM_SIZE_KB.
|
||||
*/
|
||||
#define BOOT_NVM_HOOKS_ENABLE (0)
|
||||
#define BOOT_NVM_SIZE_KB (128)
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
* W A T C H D O G D R I V E R C O N F I G U R A T I O N
|
||||
****************************************************************************************/
|
||||
/* The COP driver cannot be configured internally in the bootloader, because its use
|
||||
* and configuration is application specific. The bootloader does need to service the
|
||||
* watchdog in case it is used. When the application requires the use of a watchdog,
|
||||
* set BOOT_COP_HOOKS_ENABLE to be able to initialize and service the watchdog through
|
||||
* hook functions.
|
||||
*/
|
||||
#define BOOT_COP_HOOKS_ENABLE (0)
|
||||
|
||||
|
||||
#endif /* CONFIG_H */
|
||||
/*********************************** end of config.h ***********************************/
|
|
@ -0,0 +1,179 @@
|
|||
/****************************************************************************************
|
||||
| Description: bootloader callback source file
|
||||
| File Name: hooks.c
|
||||
|
|
||||
|----------------------------------------------------------------------------------------
|
||||
| C O P Y R I G H T
|
||||
|----------------------------------------------------------------------------------------
|
||||
| Copyright (c) 2012 by Feaser http://www.feaser.com All rights reserved
|
||||
|
|
||||
|----------------------------------------------------------------------------------------
|
||||
| L I C E N S E
|
||||
|----------------------------------------------------------------------------------------
|
||||
| This file is part of OpenBLT. OpenBLT is free software: you can redistribute it and/or
|
||||
| modify it under the terms of the GNU General Public License as published by the Free
|
||||
| Software Foundation, either version 3 of the License, or (at your option) any later
|
||||
| version.
|
||||
|
|
||||
| OpenBLT is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY;
|
||||
| without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR
|
||||
| PURPOSE. See the GNU General Public License for more details.
|
||||
|
|
||||
| You should have received a copy of the GNU General Public License along with OpenBLT.
|
||||
| If not, see <http://www.gnu.org/licenses/>.
|
||||
|
|
||||
| A special exception to the GPL is included to allow you to distribute a combined work
|
||||
| that includes OpenBLT without being obliged to provide the source code for any
|
||||
| proprietary components. The exception text is included at the bottom of the license
|
||||
| file <license.html>.
|
||||
|
|
||||
****************************************************************************************/
|
||||
|
||||
/****************************************************************************************
|
||||
* Include files
|
||||
****************************************************************************************/
|
||||
#include "boot.h" /* bootloader generic header */
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
* B A C K D O O R E N T R Y H O O K F U N C T I O N S
|
||||
****************************************************************************************/
|
||||
|
||||
#if (BOOT_BACKDOOR_HOOKS_ENABLE > 0)
|
||||
/****************************************************************************************
|
||||
** NAME: BackDoorInitHook
|
||||
** PARAMETER: none
|
||||
** RETURN VALUE: none
|
||||
** DESCRIPTION: Initializes the backdoor entry option.
|
||||
**
|
||||
****************************************************************************************/
|
||||
void BackDoorInitHook(void)
|
||||
{
|
||||
} /*** end of BackDoorInitHook ***/
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
** NAME: BackDoorEntryHook
|
||||
** PARAMETER: none
|
||||
** RETURN VALUE: BLT_TRUE if the backdoor entry is requested, BLT_FALSE otherwise.
|
||||
** DESCRIPTION: Checks if a backdoor entry is requested.
|
||||
**
|
||||
****************************************************************************************/
|
||||
blt_bool BackDoorEntryHook(void)
|
||||
{
|
||||
/* default implementation always activates the bootloader after a reset */
|
||||
return BLT_TRUE;
|
||||
} /*** end of BackDoorEntryHook ***/
|
||||
#endif /* BOOT_BACKDOOR_HOOKS_ENABLE > 0 */
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
* N O N - V O L A T I L E M E M O R Y D R I V E R H O O K F U N C T I O N S
|
||||
****************************************************************************************/
|
||||
|
||||
#if (BOOT_NVM_HOOKS_ENABLE > 0)
|
||||
/****************************************************************************************
|
||||
** NAME: NvmInitHook
|
||||
** PARAMETER: none
|
||||
** RETURN VALUE: none
|
||||
** DESCRIPTION: Callback that gets called at the start of the internal NVM driver
|
||||
** initialization routine.
|
||||
**
|
||||
****************************************************************************************/
|
||||
void NvmInitHook(void)
|
||||
{
|
||||
} /*** end of NvmInitHook ***/
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
** NAME: NvmWriteHook
|
||||
** PARAMETER: addr start address
|
||||
** len length in bytes
|
||||
** data pointer to the data buffer.
|
||||
** RETURN VALUE: BLT_NVM_OKAY if successful, BLT_NVM_NOT_IN_RANGE if the address is
|
||||
** not within the supported memory range, or BLT_NVM_ERROR is the write
|
||||
** operation failed.
|
||||
** DESCRIPTION: Callback that gets called at the start of the NVM driver write
|
||||
** routine. It allows additional memory to be operated on. If the address
|
||||
** is not within the range of the additional memory, then
|
||||
** BLT_NVM_NOT_IN_RANGE must be returned to indicate that the data hasn't
|
||||
** been written yet.
|
||||
**
|
||||
**
|
||||
****************************************************************************************/
|
||||
blt_int8u NvmWriteHook(blt_addr addr, blt_int32u len, blt_int8u *data)
|
||||
{
|
||||
return BLT_NVM_NOT_IN_RANGE;
|
||||
} /*** end of NvmWriteHook ***/
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
** NAME: NvmEraseHook
|
||||
** PARAMETER: addr start address
|
||||
** len length in bytes
|
||||
** RETURN VALUE: BLT_NVM_OKAY if successful, BLT_NVM_NOT_IN_RANGE if the address is
|
||||
** not within the supported memory range, or BLT_NVM_ERROR is the erase
|
||||
** operation failed.
|
||||
** DESCRIPTION: Callback that gets called at the start of the NVM driver erase
|
||||
** routine. It allows additional memory to be operated on. If the address
|
||||
** is not within the range of the additional memory, then
|
||||
** BLT_NVM_NOT_IN_RANGE must be returned to indicate that the memory
|
||||
** hasn't been erased yet.
|
||||
**
|
||||
****************************************************************************************/
|
||||
blt_int8u NvmEraseHook(blt_addr addr, blt_int32u len)
|
||||
{
|
||||
return BLT_NVM_NOT_IN_RANGE;
|
||||
} /*** end of NvmEraseHook ***/
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
** NAME: NvmDoneHook
|
||||
** PARAMETER: none
|
||||
** RETURN VALUE: BLT_TRUE is successful, BLT_FALSE otherwise.
|
||||
** DESCRIPTION: Callback that gets called at the end of the NVM programming session.
|
||||
**
|
||||
****************************************************************************************/
|
||||
blt_bool NvmDoneHook(void)
|
||||
{
|
||||
return BLT_TRUE;
|
||||
} /*** end of NvmDoneHook ***/
|
||||
#endif /* BOOT_NVM_HOOKS_ENABLE > 0 */
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
* W A T C H D O G D R I V E R H O O K F U N C T I O N S
|
||||
****************************************************************************************/
|
||||
|
||||
#if (BOOT_COP_HOOKS_ENABLE > 0)
|
||||
/****************************************************************************************
|
||||
** NAME: CopInitHook
|
||||
** PARAMETER: none
|
||||
** RETURN VALUE: none
|
||||
** DESCRIPTION: Callback that gets called at the end of the internal COP driver
|
||||
** initialization routine. It can be used to configure and enable the
|
||||
** watchdog.
|
||||
**
|
||||
****************************************************************************************/
|
||||
void CopInitHook(void)
|
||||
{
|
||||
} /*** end of CopInitHook ***/
|
||||
|
||||
|
||||
/****************************************************************************************
|
||||
** NAME: CopServiceHook
|
||||
** PARAMETER: none
|
||||
** RETURN VALUE: none
|
||||
** DESCRIPTION: Callback that gets called at the end of the internal COP driver
|
||||
** service routine. This gets called upon initialization and during
|
||||
** potential long lasting loops and routine. It can be used to service
|
||||
** the watchdog to prevent a watchdog reset.
|
||||
**
|
||||
****************************************************************************************/
|
||||
void CopServiceHook(void)
|
||||
{
|
||||
} /*** end of CopServiceHook ***/
|
||||
#endif /* BOOT_COP_HOOKS_ENABLE > 0 */
|
||||
|
||||
|
||||
/*********************************** end of hooks.c ************************************/
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,10 @@
|
|||
<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
|
||||
<workspace>
|
||||
<project>
|
||||
<path>$WS_DIR$\efm32G880.ewp</path>
|
||||
</project>
|
||||
<batchBuild/>
|
||||
</workspace>
|
||||
|
||||
|
|
@ -0,0 +1,4 @@
|
|||
Integrated Development Environment
|
||||
----------------------------------
|
||||
IAR Embedded Workbench for ARM v6.30 was used as the editor during the development of this software program. This directory contains
|
||||
the Embedded Workbench project and worksapce files. More info is available at: http://www.iar.com/
|
|
@ -0,0 +1,15 @@
|
|||
@REM This batch file has been generated by the IAR Embedded Workbench
|
||||
@REM C-SPY Debugger, as an aid to preparing a command line for running
|
||||
@REM the cspybat command line utility using the appropriate settings.
|
||||
@REM
|
||||
@REM You can launch cspybat by typing the name of this batch file followed
|
||||
@REM by the name of the debug file (usually an ELF/DWARF or UBROF file).
|
||||
@REM Note that this file is generated every time a new debug session
|
||||
@REM is initialized, so you may want to move or rename the file before
|
||||
@REM making changes.
|
||||
@REM
|
||||
|
||||
|
||||
"C:\Program Files (x86)\IAR Systems\Embedded Workbench 6.0 Kickstart\common\bin\cspybat" "C:\Program Files (x86)\IAR Systems\Embedded Workbench 6.0 Kickstart\arm\bin\armproc.dll" "C:\Program Files (x86)\IAR Systems\Embedded Workbench 6.0 Kickstart\arm\bin\armjlink.dll" %1 --plugin "C:\Program Files (x86)\IAR Systems\Embedded Workbench 6.0 Kickstart\arm\bin\armbat.dll" --flash_loader "C:\Program Files (x86)\IAR Systems\Embedded Workbench 6.0 Kickstart\arm\config\flashloader\EnergyMicro\FlashEFM32.board" --backend -B "--endian=little" "--cpu=Cortex-M3" "--fpu=None" "-p" "C:\Program Files (x86)\IAR Systems\Embedded Workbench 6.0 Kickstart\arm\CONFIG\debugger\EnergyMicro\EFM32G880F128.ddf" "--drv_verify_download" "--semihosting" "--device=EFM32G880F128" "--drv_communication=USB0" "--jlink_speed=auto" "--jlink_initial_speed=32" "--jlink_reset_strategy=0,0" "--drv_catch_exceptions=0x000" "--drv_swo_clock_setup=72000000,0,2000000"
|
||||
|
||||
|
|
@ -0,0 +1,5 @@
|
|||
<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
|
||||
<Project/>
|
||||
|
||||
|
|
@ -0,0 +1,19 @@
|
|||
[Stack]
|
||||
FillEnabled=0
|
||||
OverflowWarningsEnabled=1
|
||||
WarningThreshold=90
|
||||
SpWarningsEnabled=1
|
||||
WarnLogOnly=1
|
||||
UseTrigger=1
|
||||
TriggerName=main
|
||||
LimitSize=0
|
||||
ByteLimit=50
|
||||
[Breakpoints]
|
||||
Count=0
|
||||
[Disassemble mode]
|
||||
mode=0
|
||||
[Breakpoints2]
|
||||
Count=0
|
||||
[Aliases]
|
||||
Count=0
|
||||
SuppressDialog=0
|
|
@ -0,0 +1,77 @@
|
|||
<?xml version="1.0" encoding="iso-8859-1"?>
|
||||
|
||||
<Workspace>
|
||||
<ConfigDictionary>
|
||||
|
||||
<CurrentConfigs><Project>efm32G880/Debug</Project></CurrentConfigs></ConfigDictionary>
|
||||
<Desktop>
|
||||
<Static>
|
||||
<Workspace>
|
||||
<ColumnWidths>
|
||||
|
||||
|
||||
|
||||
|
||||
<Column0>277</Column0><Column1>27</Column1><Column2>27</Column2><Column3>27</Column3></ColumnWidths>
|
||||
</Workspace>
|
||||
<Build>
|
||||
|
||||
|
||||
|
||||
|
||||
<ColumnWidth0>20</ColumnWidth0><ColumnWidth1>1155</ColumnWidth1><ColumnWidth2>308</ColumnWidth2><ColumnWidth3>77</ColumnWidth3></Build>
|
||||
<Find-in-Files>
|
||||
<ColumnWidth0>552</ColumnWidth0>
|
||||
<ColumnWidth1>78</ColumnWidth1>
|
||||
<ColumnWidth2>946</ColumnWidth2>
|
||||
</Find-in-Files>
|
||||
</Static>
|
||||
<Windows>
|
||||
|
||||
|
||||
<Wnd0>
|
||||
<Tabs>
|
||||
<Tab>
|
||||
<Identity>TabID-3636-6432</Identity>
|
||||
<TabName>Workspace</TabName>
|
||||
<Factory>Workspace</Factory>
|
||||
<Session>
|
||||
|
||||
<NodeDict><ExpandedNode>efm32G880</ExpandedNode><ExpandedNode>efm32G880/Boot</ExpandedNode><ExpandedNode>efm32G880/Output</ExpandedNode><ExpandedNode>efm32G880/Source</ExpandedNode><ExpandedNode>efm32G880/Source/ARMCM3_EFM32</ExpandedNode><ExpandedNode>efm32G880/Source/ARMCM3_EFM32/IAR</ExpandedNode></NodeDict></Session>
|
||||
</Tab>
|
||||
</Tabs>
|
||||
|
||||
<SelectedTab>0</SelectedTab></Wnd0><Wnd1>
|
||||
<Tabs>
|
||||
<Tab>
|
||||
<Identity>TabID-28813-8212</Identity>
|
||||
<TabName>Build</TabName>
|
||||
<Factory>Build</Factory>
|
||||
<Session/>
|
||||
</Tab>
|
||||
<Tab>
|
||||
<Identity>TabID-4765-8663</Identity>
|
||||
<TabName>Find in Files</TabName>
|
||||
<Factory>Find-in-Files</Factory>
|
||||
<Session/>
|
||||
</Tab>
|
||||
</Tabs>
|
||||
|
||||
<SelectedTab>0</SelectedTab></Wnd1></Windows>
|
||||
<Editor>
|
||||
|
||||
|
||||
|
||||
|
||||
<Pane><Tab><Factory>TextEditor</Factory><Filename>$WS_DIR$\..\main.c</Filename><XPos>0</XPos><YPos>51</YPos><SelStart>3132</SelStart><SelEnd>3132</SelEnd></Tab><Tab><Factory>TextEditor</Factory><Filename>$WS_DIR$\..\..\..\..\Source\ARMCM3_EFM32\timer.h</Filename><XPos>0</XPos><YPos>32</YPos><SelStart>1983</SelStart><SelEnd>1983</SelEnd></Tab><ActiveTab>1</ActiveTab><Tab><Factory>TextEditor</Factory><Filename>$WS_DIR$\..\..\..\..\Source\ARMCM3_EFM32\timer.c</Filename><XPos>0</XPos><YPos>96</YPos><SelStart>5082</SelStart><SelEnd>5082</SelEnd></Tab></Pane><ActivePane>0</ActivePane><Sizes><Pane><X>1000000</X><Y>1000000</Y></Pane></Sizes><SplitMode>1</SplitMode></Editor>
|
||||
<Positions>
|
||||
|
||||
|
||||
|
||||
|
||||
|
||||
<Top><Row0><Sizes><Toolbar-02e07930><key>iaridepm.enu1</key></Toolbar-02e07930></Sizes></Row0></Top><Left><Row0><Sizes><Wnd0><Rect><Top>-2</Top><Left>-2</Left><Bottom>587</Bottom><Right>368</Right><x>-2</x><y>-2</y><xscreen>200</xscreen><yscreen>200</yscreen><sizeHorzCX>125000</sizeHorzCX><sizeHorzCY>240964</sizeHorzCY><sizeVertCX>231250</sizeVertCX><sizeVertCY>709639</sizeVertCY></Rect></Wnd0></Sizes></Row0></Left><Right><Row0><Sizes/></Row0></Right><Bottom><Row0><Sizes><Wnd1><Rect><Top>-2</Top><Left>-2</Left><Bottom>198</Bottom><Right>1602</Right><x>-2</x><y>-2</y><xscreen>1604</xscreen><yscreen>200</yscreen><sizeHorzCX>1002500</sizeHorzCX><sizeHorzCY>240964</sizeHorzCY><sizeVertCX>125000</sizeVertCX><sizeVertCY>240964</sizeVertCY></Rect></Wnd1></Sizes></Row0></Bottom><Float><Sizes/></Float></Positions>
|
||||
</Desktop>
|
||||
</Workspace>
|
||||
|
||||
|
|
@ -0,0 +1,339 @@
|
|||
/**************************************************************************//**
|
||||
* @file core_cm3.c
|
||||
* @brief CMSIS Cortex-M3 Core Peripheral Access Layer Source File
|
||||
* @version V2.00
|
||||
* @date 13. September 2010
|
||||
*
|
||||
* @note
|
||||
* Copyright (C) 2009-2010 ARM Limited. All rights reserved.
|
||||
*
|
||||
* @par
|
||||
* ARM Limited (ARM) is supplying this software for use with Cortex-M
|
||||
* processor based microcontrollers. This file can be freely distributed
|
||||
* within development tools that are supporting such ARM based processors.
|
||||
*
|
||||
* @par
|
||||
* THIS SOFTWARE IS PROVIDED "AS IS". NO WARRANTIES, WHETHER EXPRESS, IMPLIED
|
||||
* OR STATUTORY, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF
|
||||
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE APPLY TO THIS SOFTWARE.
|
||||
* ARM SHALL NOT, IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL, OR
|
||||
* CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
/* define compiler specific symbols */
|
||||
#if defined ( __CC_ARM )
|
||||
#define __ASM __asm /*!< asm keyword for ARM Compiler */
|
||||
#define __INLINE __inline /*!< inline keyword for ARM Compiler */
|
||||
|
||||
#elif defined ( __ICCARM__ )
|
||||
#define __ASM __asm /*!< asm keyword for IAR Compiler */
|
||||
#define __INLINE inline /*!< inline keyword for IAR Compiler. Only avaiable in High optimization mode! */
|
||||
|
||||
#elif defined ( __GNUC__ )
|
||||
#define __ASM __asm /*!< asm keyword for GNU Compiler */
|
||||
#define __INLINE inline /*!< inline keyword for GNU Compiler */
|
||||
|
||||
#elif defined ( __TASKING__ )
|
||||
#define __ASM __asm /*!< asm keyword for TASKING Compiler */
|
||||
#define __INLINE inline /*!< inline keyword for TASKING Compiler */
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
/* ########################## Core Instruction Access ######################### */
|
||||
|
||||
#if defined ( __CC_ARM ) /*------------------ RealView Compiler ----------------*/
|
||||
|
||||
/** \brief Reverse byte order (16 bit)
|
||||
|
||||
This function reverses the byte order in two unsigned short values.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400677)
|
||||
__ASM uint32_t __REV16(uint32_t value)
|
||||
{
|
||||
rev16 r0, r0
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Reverse byte order in signed short value
|
||||
|
||||
This function reverses the byte order in a signed short value with sign extension to integer.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400677)
|
||||
__ASM int32_t __REVSH(int32_t value)
|
||||
{
|
||||
revsh r0, r0
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Remove the exclusive lock
|
||||
|
||||
This function removes the exclusive lock which is created by LDREX.
|
||||
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM void __CLREX(void)
|
||||
{
|
||||
clrex
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
#elif (defined (__ICCARM__)) /*---------------- ICC Compiler ---------------------*/
|
||||
/* obsolete */
|
||||
#elif (defined (__GNUC__)) /*------------------ GNU Compiler ---------------------*/
|
||||
/* obsolete */
|
||||
#elif (defined (__TASKING__)) /*--------------- TASKING Compiler -----------------*/
|
||||
/* obsolete */
|
||||
#endif
|
||||
|
||||
|
||||
/* ########################### Core Function Access ########################### */
|
||||
|
||||
#if defined ( __CC_ARM ) /*------------------ RealView Compiler ----------------*/
|
||||
|
||||
/** \brief Get Control Register
|
||||
|
||||
This function returns the content of the Control Register.
|
||||
|
||||
\return Control Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM uint32_t __get_CONTROL(void)
|
||||
{
|
||||
mrs r0, control
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Control Register
|
||||
|
||||
This function writes the given value to the Control Register.
|
||||
|
||||
\param [in] control Control Register value to set
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM void __set_CONTROL(uint32_t control)
|
||||
{
|
||||
msr control, r0
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get ISPR Register
|
||||
|
||||
This function returns the content of the ISPR Register.
|
||||
|
||||
\return ISPR Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM uint32_t __get_IPSR(void)
|
||||
{
|
||||
mrs r0, ipsr
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get APSR Register
|
||||
|
||||
This function returns the content of the APSR Register.
|
||||
|
||||
\return APSR Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM uint32_t __get_APSR(void)
|
||||
{
|
||||
mrs r0, apsr
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get xPSR Register
|
||||
|
||||
This function returns the content of the xPSR Register.
|
||||
|
||||
\return xPSR Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM uint32_t __get_xPSR(void)
|
||||
{
|
||||
mrs r0, xpsr
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get Process Stack Pointer
|
||||
|
||||
This function returns the current value of the Process Stack Pointer (PSP).
|
||||
|
||||
\return PSP Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM uint32_t __get_PSP(void)
|
||||
{
|
||||
mrs r0, psp
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Process Stack Pointer
|
||||
|
||||
This function assigns the given value to the Process Stack Pointer (PSP).
|
||||
|
||||
\param [in] topOfProcStack Process Stack Pointer value to set
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM void __set_PSP(uint32_t topOfProcStack)
|
||||
{
|
||||
msr psp, r0
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get Main Stack Pointer
|
||||
|
||||
This function returns the current value of the Main Stack Pointer (MSP).
|
||||
|
||||
\return MSP Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM uint32_t __get_MSP(void)
|
||||
{
|
||||
mrs r0, msp
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Main Stack Pointer
|
||||
|
||||
This function assigns the given value to the Main Stack Pointer (MSP).
|
||||
|
||||
\param [in] topOfMainStack Main Stack Pointer value to set
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM void __set_MSP(uint32_t mainStackPointer)
|
||||
{
|
||||
msr msp, r0
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get Base Priority
|
||||
|
||||
This function returns the current value of the Base Priority register.
|
||||
|
||||
\return Base Priority register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM uint32_t __get_BASEPRI(void)
|
||||
{
|
||||
mrs r0, basepri
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Base Priority
|
||||
|
||||
This function assigns the given value to the Base Priority register.
|
||||
|
||||
\param [in] basePri Base Priority value to set
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM void __set_BASEPRI(uint32_t basePri)
|
||||
{
|
||||
msr basepri, r0
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
/** \brief Get Priority Mask
|
||||
|
||||
This function returns the current state of the priority mask bit from the Priority Mask Register.
|
||||
|
||||
\return Priority Mask value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM uint32_t __get_PRIMASK(void)
|
||||
{
|
||||
mrs r0, primask
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Priority Mask
|
||||
|
||||
This function assigns the given value to the Priority Mask Register.
|
||||
|
||||
\param [in] priMask Priority Mask
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM void __set_PRIMASK(uint32_t priMask)
|
||||
{
|
||||
msr primask, r0
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get Fault Mask
|
||||
|
||||
This function returns the current value of the Fault Mask Register.
|
||||
|
||||
\return Fault Mask value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM uint32_t __get_FAULTMASK(void)
|
||||
{
|
||||
mrs r0, faultmask
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set the Fault Mask
|
||||
|
||||
This function assigns the given value to the Fault Mask Register.
|
||||
|
||||
\param [in] faultMask Fault Mask value value to set
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
__ASM void __set_FAULTMASK(uint32_t faultMask)
|
||||
{
|
||||
msr faultmask, r0
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
|
||||
#elif (defined (__ICCARM__)) /*---------------- ICC Compiler ---------------------*/
|
||||
/* obsolete */
|
||||
#elif (defined (__GNUC__)) /*------------------ GNU Compiler ---------------------*/
|
||||
/* obsolete */
|
||||
#elif (defined (__TASKING__)) /*--------------- TASKING Compiler -----------------*/
|
||||
/* obsolete */
|
||||
#endif
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,851 @@
|
|||
/**************************************************************************//**
|
||||
* @file core_cmFunc.h
|
||||
* @brief CMSIS Cortex-M Core Function Access Header File
|
||||
* @version V2.01
|
||||
* @date 06. December 2010
|
||||
*
|
||||
* @note
|
||||
* Copyright (C) 2009-2010 ARM Limited. All rights reserved.
|
||||
*
|
||||
* @par
|
||||
* ARM Limited (ARM) is supplying this software for use with Cortex-M
|
||||
* processor based microcontrollers. This file can be freely distributed
|
||||
* within development tools that are supporting such ARM based processors.
|
||||
*
|
||||
* @par
|
||||
* THIS SOFTWARE IS PROVIDED "AS IS". NO WARRANTIES, WHETHER EXPRESS, IMPLIED
|
||||
* OR STATUTORY, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF
|
||||
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE APPLY TO THIS SOFTWARE.
|
||||
* ARM SHALL NOT, IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL, OR
|
||||
* CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#ifndef __CORE_CMFUNC_H__
|
||||
#define __CORE_CMFUNC_H__
|
||||
|
||||
/* ########################### Core Function Access ########################### */
|
||||
/** \ingroup CMSIS_Core_FunctionInterface
|
||||
\defgroup CMSIS_Core_RegAccFunctions CMSIS Core Register Access Functions
|
||||
@{
|
||||
*/
|
||||
|
||||
#if defined ( __CC_ARM ) /*------------------ RealView Compiler ----------------*/
|
||||
/* ARM armcc specific functions */
|
||||
|
||||
/* intrinsic void __enable_irq(); */
|
||||
/* intrinsic void __disable_irq(); */
|
||||
|
||||
/** \brief Get Control Register
|
||||
|
||||
This function returns the content of the Control Register.
|
||||
|
||||
\return Control Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern uint32_t __get_CONTROL(void);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE uint32_t __get_CONTROL(void)
|
||||
{
|
||||
register uint32_t __regControl __ASM("control");
|
||||
return(__regControl);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Control Register
|
||||
|
||||
This function writes the given value to the Control Register.
|
||||
|
||||
\param [in] control Control Register value to set
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern void __set_CONTROL(uint32_t control);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE void __set_CONTROL(uint32_t control)
|
||||
{
|
||||
register uint32_t __regControl __ASM("control");
|
||||
__regControl = control;
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get ISPR Register
|
||||
|
||||
This function returns the content of the ISPR Register.
|
||||
|
||||
\return ISPR Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern uint32_t __get_IPSR(void);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE uint32_t __get_IPSR(void)
|
||||
{
|
||||
register uint32_t __regIPSR __ASM("ipsr");
|
||||
return(__regIPSR);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get APSR Register
|
||||
|
||||
This function returns the content of the APSR Register.
|
||||
|
||||
\return APSR Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern uint32_t __get_APSR(void);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE uint32_t __get_APSR(void)
|
||||
{
|
||||
register uint32_t __regAPSR __ASM("apsr");
|
||||
return(__regAPSR);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get xPSR Register
|
||||
|
||||
This function returns the content of the xPSR Register.
|
||||
|
||||
\return xPSR Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern uint32_t __get_xPSR(void);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE uint32_t __get_xPSR(void)
|
||||
{
|
||||
register uint32_t __regXPSR __ASM("xpsr");
|
||||
return(__regXPSR);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get Process Stack Pointer
|
||||
|
||||
This function returns the current value of the Process Stack Pointer (PSP).
|
||||
|
||||
\return PSP Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern uint32_t __get_PSP(void);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE uint32_t __get_PSP(void)
|
||||
{
|
||||
register uint32_t __regProcessStackPointer __ASM("psp");
|
||||
return(__regProcessStackPointer);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Process Stack Pointer
|
||||
|
||||
This function assigns the given value to the Process Stack Pointer (PSP).
|
||||
|
||||
\param [in] topOfProcStack Process Stack Pointer value to set
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern void __set_PSP(uint32_t topOfProcStack);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE void __set_PSP(uint32_t topOfProcStack)
|
||||
{
|
||||
register uint32_t __regProcessStackPointer __ASM("psp");
|
||||
__regProcessStackPointer = topOfProcStack;
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get Main Stack Pointer
|
||||
|
||||
This function returns the current value of the Main Stack Pointer (MSP).
|
||||
|
||||
\return MSP Register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern uint32_t __get_MSP(void);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE uint32_t __get_MSP(void)
|
||||
{
|
||||
register uint32_t __regMainStackPointer __ASM("msp");
|
||||
return(__regMainStackPointer);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Main Stack Pointer
|
||||
|
||||
This function assigns the given value to the Main Stack Pointer (MSP).
|
||||
|
||||
\param [in] topOfMainStack Main Stack Pointer value to set
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern void __set_MSP(uint32_t topOfMainStack);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE void __set_MSP(uint32_t topOfMainStack)
|
||||
{
|
||||
register uint32_t __regMainStackPointer __ASM("msp");
|
||||
__regMainStackPointer = topOfMainStack;
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get Priority Mask
|
||||
|
||||
This function returns the current state of the priority mask bit from the Priority Mask Register.
|
||||
|
||||
\return Priority Mask value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern uint32_t __get_PRIMASK(void);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE uint32_t __get_PRIMASK(void)
|
||||
{
|
||||
register uint32_t __regPriMask __ASM("primask");
|
||||
return(__regPriMask);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Priority Mask
|
||||
|
||||
This function assigns the given value to the Priority Mask Register.
|
||||
|
||||
\param [in] priMask Priority Mask
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern void __set_PRIMASK(uint32_t priMask);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE void __set_PRIMASK(uint32_t priMask)
|
||||
{
|
||||
register uint32_t __regPriMask __ASM("primask");
|
||||
__regPriMask = (priMask);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
#if (__CORTEX_M >= 0x03)
|
||||
|
||||
/** \brief Enable FIQ
|
||||
|
||||
This function enables FIQ interrupts by clearing the F-bit in the CPSR.
|
||||
Can only be executed in Privileged modes.
|
||||
*/
|
||||
#define __enable_fault_irq __enable_fiq
|
||||
|
||||
|
||||
/** \brief Disable FIQ
|
||||
|
||||
This function disables FIQ interrupts by setting the F-bit in the CPSR.
|
||||
Can only be executed in Privileged modes.
|
||||
*/
|
||||
#define __disable_fault_irq __disable_fiq
|
||||
|
||||
|
||||
/** \brief Get Base Priority
|
||||
|
||||
This function returns the current value of the Base Priority register.
|
||||
|
||||
\return Base Priority register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern uint32_t __get_BASEPRI(void);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE uint32_t __get_BASEPRI(void)
|
||||
{
|
||||
register uint32_t __regBasePri __ASM("basepri");
|
||||
return(__regBasePri);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Base Priority
|
||||
|
||||
This function assigns the given value to the Base Priority register.
|
||||
|
||||
\param [in] basePri Base Priority value to set
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern void __set_BASEPRI(uint32_t basePri);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE void __set_BASEPRI(uint32_t basePri)
|
||||
{
|
||||
register uint32_t __regBasePri __ASM("basepri");
|
||||
__regBasePri = (basePri & 0xff);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Get Fault Mask
|
||||
|
||||
This function returns the current value of the Fault Mask register.
|
||||
|
||||
\return Fault Mask register value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern uint32_t __get_FAULTMASK(void);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE uint32_t __get_FAULTMASK(void)
|
||||
{
|
||||
register uint32_t __regFaultMask __ASM("faultmask");
|
||||
return(__regFaultMask);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Set Fault Mask
|
||||
|
||||
This function assigns the given value to the Fault Mask register.
|
||||
|
||||
\param [in] faultMask Fault Mask value to set
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern void __set_FAULTMASK(uint32_t faultMask);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
static __INLINE void __set_FAULTMASK(uint32_t faultMask)
|
||||
{
|
||||
register uint32_t __regFaultMask __ASM("faultmask");
|
||||
__regFaultMask = (faultMask & 1);
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
#endif /* (__CORTEX_M >= 0x03) */
|
||||
|
||||
|
||||
#if (__CORTEX_M == 0x04)
|
||||
|
||||
/** \brief Get FPSCR
|
||||
|
||||
This function returns the current value of the Floating Point Status/Control register.
|
||||
|
||||
\return Floating Point Status/Control register value
|
||||
*/
|
||||
static __INLINE uint32_t __get_FPSCR(void)
|
||||
{
|
||||
#if (__FPU_PRESENT == 1)
|
||||
register uint32_t __regfpscr __ASM("fpscr");
|
||||
return(__regfpscr);
|
||||
#else
|
||||
return(0);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set FPSCR
|
||||
|
||||
This function assigns the given value to the Floating Point Status/Control register.
|
||||
|
||||
\param [in] fpscr Floating Point Status/Control value to set
|
||||
*/
|
||||
static __INLINE void __set_FPSCR(uint32_t fpscr)
|
||||
{
|
||||
#if (__FPU_PRESENT == 1)
|
||||
register uint32_t __regfpscr __ASM("fpscr");
|
||||
__regfpscr = (fpscr);
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /* (__CORTEX_M == 0x04) */
|
||||
|
||||
|
||||
#elif (defined (__ICCARM__)) /*---------------- ICC Compiler ---------------------*/
|
||||
/* IAR iccarm specific functions */
|
||||
|
||||
/* Energy Micro: Add support for new versions of IAR */
|
||||
#if __VER__ >= 6020000
|
||||
#include "cmsis_iar.h"
|
||||
#else
|
||||
/* Energy Micro: Fix end */
|
||||
#include <intrinsics.h> /* IAR Intrinsics */
|
||||
|
||||
#pragma diag_suppress=Pe940
|
||||
|
||||
/** \brief Enable IRQ Interrupts
|
||||
|
||||
This function enables IRQ interrupts by clearing the I-bit in the CPSR.
|
||||
Can only be executed in Privileged modes.
|
||||
*/
|
||||
#define __enable_irq __enable_interrupt
|
||||
|
||||
|
||||
/** \brief Disable IRQ Interrupts
|
||||
|
||||
This function disables IRQ interrupts by setting the I-bit in the CPSR.
|
||||
Can only be executed in Privileged modes.
|
||||
*/
|
||||
#define __disable_irq __disable_interrupt
|
||||
|
||||
|
||||
/* intrinsic unsigned long __get_CONTROL( void ); (see intrinsic.h) */
|
||||
/* intrinsic void __set_CONTROL( unsigned long ); (see intrinsic.h) */
|
||||
|
||||
|
||||
/** \brief Get ISPR Register
|
||||
|
||||
This function returns the content of the ISPR Register.
|
||||
|
||||
\return ISPR Register value
|
||||
*/
|
||||
static uint32_t __get_IPSR(void)
|
||||
{
|
||||
__ASM("mrs r0, ipsr");
|
||||
}
|
||||
|
||||
/* Energy Micro: This function is present in new IAR versions */
|
||||
#if __VER__ < 6010002
|
||||
/** \brief Get APSR Register
|
||||
|
||||
This function returns the content of the APSR Register.
|
||||
|
||||
\return APSR Register value
|
||||
*/
|
||||
static uint32_t __get_APSR(void)
|
||||
{
|
||||
__ASM("mrs r0, apsr");
|
||||
}
|
||||
#endif
|
||||
/* Energy Micro: Fix end */
|
||||
|
||||
/** \brief Get xPSR Register
|
||||
|
||||
This function returns the content of the xPSR Register.
|
||||
|
||||
\return xPSR Register value
|
||||
*/
|
||||
static uint32_t __get_xPSR(void)
|
||||
{
|
||||
__ASM("mrs r0, psr"); // assembler does not know "xpsr"
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get Process Stack Pointer
|
||||
|
||||
This function returns the current value of the Process Stack Pointer (PSP).
|
||||
|
||||
\return PSP Register value
|
||||
*/
|
||||
static uint32_t __get_PSP(void)
|
||||
{
|
||||
__ASM("mrs r0, psp");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set Process Stack Pointer
|
||||
|
||||
This function assigns the given value to the Process Stack Pointer (PSP).
|
||||
|
||||
\param [in] topOfProcStack Process Stack Pointer value to set
|
||||
*/
|
||||
static void __set_PSP(uint32_t topOfProcStack)
|
||||
{
|
||||
__ASM("msr psp, r0");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get Main Stack Pointer
|
||||
|
||||
This function returns the current value of the Main Stack Pointer (MSP).
|
||||
|
||||
\return MSP Register value
|
||||
*/
|
||||
static uint32_t __get_MSP(void)
|
||||
{
|
||||
__ASM("mrs r0, msp");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set Main Stack Pointer
|
||||
|
||||
This function assigns the given value to the Main Stack Pointer (MSP).
|
||||
|
||||
\param [in] topOfMainStack Main Stack Pointer value to set
|
||||
*/
|
||||
static void __set_MSP(uint32_t topOfMainStack)
|
||||
{
|
||||
__ASM("msr msp, r0");
|
||||
}
|
||||
|
||||
|
||||
/* intrinsic unsigned long __get_PRIMASK( void ); (see intrinsic.h) */
|
||||
/* intrinsic void __set_PRIMASK( unsigned long ); (see intrinsic.h) */
|
||||
|
||||
|
||||
#if (__CORTEX_M >= 0x03)
|
||||
|
||||
/** \brief Enable FIQ
|
||||
|
||||
This function enables FIQ interrupts by clearing the F-bit in the CPSR.
|
||||
Can only be executed in Privileged modes.
|
||||
*/
|
||||
static __INLINE void __enable_fault_irq(void)
|
||||
{
|
||||
__ASM ("cpsie f");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Disable FIQ
|
||||
|
||||
This function disables FIQ interrupts by setting the F-bit in the CPSR.
|
||||
Can only be executed in Privileged modes.
|
||||
*/
|
||||
static __INLINE void __disable_fault_irq(void)
|
||||
{
|
||||
__ASM ("cpsid f");
|
||||
}
|
||||
|
||||
|
||||
/* intrinsic unsigned long __get_BASEPRI( void ); (see intrinsic.h) */
|
||||
/* intrinsic void __set_BASEPRI( unsigned long ); (see intrinsic.h) */
|
||||
/* intrinsic unsigned long __get_FAULTMASK( void ); (see intrinsic.h) */
|
||||
/* intrinsic void __set_FAULTMASK(unsigned long); (see intrinsic.h) */
|
||||
|
||||
#endif /* (__CORTEX_M >= 0x03) */
|
||||
|
||||
|
||||
#if (__CORTEX_M == 0x04)
|
||||
|
||||
/** \brief Get FPSCR
|
||||
|
||||
This function returns the current value of the Floating Point Status/Control register.
|
||||
|
||||
\return Floating Point Status/Control register value
|
||||
*/
|
||||
static uint32_t __get_FPSCR(void)
|
||||
{
|
||||
#if (__FPU_PRESENT == 1)
|
||||
__ASM("vmrs r0, fpscr");
|
||||
#else
|
||||
return(0);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set FPSCR
|
||||
|
||||
This function assigns the given value to the Floating Point Status/Control register.
|
||||
|
||||
\param [in] fpscr Floating Point Status/Control value to set
|
||||
*/
|
||||
static void __set_FPSCR(uint32_t fpscr)
|
||||
{
|
||||
#if (__FPU_PRESENT == 1)
|
||||
__ASM("vmsr fpscr, r0");
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /* (__CORTEX_M == 0x04) */
|
||||
|
||||
#pragma diag_default=Pe940
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
#elif (defined (__GNUC__)) /*------------------ GNU Compiler ---------------------*/
|
||||
/* GNU gcc specific functions */
|
||||
|
||||
/** \brief Enable IRQ Interrupts
|
||||
|
||||
This function enables IRQ interrupts by clearing the I-bit in the CPSR.
|
||||
Can only be executed in Privileged modes.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __enable_irq(void)
|
||||
{
|
||||
__ASM volatile ("cpsie i");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Disable IRQ Interrupts
|
||||
|
||||
This function disables IRQ interrupts by setting the I-bit in the CPSR.
|
||||
Can only be executed in Privileged modes.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __disable_irq(void)
|
||||
{
|
||||
__ASM volatile ("cpsid i");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get Control Register
|
||||
|
||||
This function returns the content of the Control Register.
|
||||
|
||||
\return Control Register value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __get_CONTROL(void)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("MRS %0, control" : "=r" (result) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set Control Register
|
||||
|
||||
This function writes the given value to the Control Register.
|
||||
|
||||
\param [in] control Control Register value to set
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __set_CONTROL(uint32_t control)
|
||||
{
|
||||
__ASM volatile ("MSR control, %0" : : "r" (control) );
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get ISPR Register
|
||||
|
||||
This function returns the content of the ISPR Register.
|
||||
|
||||
\return ISPR Register value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __get_IPSR(void)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("MRS %0, ipsr" : "=r" (result) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get APSR Register
|
||||
|
||||
This function returns the content of the APSR Register.
|
||||
|
||||
\return APSR Register value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __get_APSR(void)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("MRS %0, apsr" : "=r" (result) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get xPSR Register
|
||||
|
||||
This function returns the content of the xPSR Register.
|
||||
|
||||
\return xPSR Register value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __get_xPSR(void)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("MRS %0, xpsr" : "=r" (result) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get Process Stack Pointer
|
||||
|
||||
This function returns the current value of the Process Stack Pointer (PSP).
|
||||
|
||||
\return PSP Register value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __get_PSP(void)
|
||||
{
|
||||
register uint32_t result;
|
||||
|
||||
__ASM volatile ("MRS %0, psp\n" : "=r" (result) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set Process Stack Pointer
|
||||
|
||||
This function assigns the given value to the Process Stack Pointer (PSP).
|
||||
|
||||
\param [in] topOfProcStack Process Stack Pointer value to set
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __set_PSP(uint32_t topOfProcStack)
|
||||
{
|
||||
__ASM volatile ("MSR psp, %0\n" : : "r" (topOfProcStack) );
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get Main Stack Pointer
|
||||
|
||||
This function returns the current value of the Main Stack Pointer (MSP).
|
||||
|
||||
\return MSP Register value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __get_MSP(void)
|
||||
{
|
||||
register uint32_t result;
|
||||
|
||||
__ASM volatile ("MRS %0, msp\n" : "=r" (result) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set Main Stack Pointer
|
||||
|
||||
This function assigns the given value to the Main Stack Pointer (MSP).
|
||||
|
||||
\param [in] topOfMainStack Main Stack Pointer value to set
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __set_MSP(uint32_t topOfMainStack)
|
||||
{
|
||||
__ASM volatile ("MSR msp, %0\n" : : "r" (topOfMainStack) );
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get Priority Mask
|
||||
|
||||
This function returns the current state of the priority mask bit from the Priority Mask Register.
|
||||
|
||||
\return Priority Mask value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __get_PRIMASK(void)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("MRS %0, primask" : "=r" (result) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set Priority Mask
|
||||
|
||||
This function assigns the given value to the Priority Mask Register.
|
||||
|
||||
\param [in] priMask Priority Mask
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __set_PRIMASK(uint32_t priMask)
|
||||
{
|
||||
__ASM volatile ("MSR primask, %0" : : "r" (priMask) );
|
||||
}
|
||||
|
||||
|
||||
#if (__CORTEX_M >= 0x03)
|
||||
|
||||
/** \brief Enable FIQ
|
||||
|
||||
This function enables FIQ interrupts by clearing the F-bit in the CPSR.
|
||||
Can only be executed in Privileged modes.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __enable_fault_irq(void)
|
||||
{
|
||||
__ASM volatile ("cpsie f");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Disable FIQ
|
||||
|
||||
This function disables FIQ interrupts by setting the F-bit in the CPSR.
|
||||
Can only be executed in Privileged modes.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __disable_fault_irq(void)
|
||||
{
|
||||
__ASM volatile ("cpsid f");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get Base Priority
|
||||
|
||||
This function returns the current value of the Base Priority register.
|
||||
|
||||
\return Base Priority register value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __get_BASEPRI(void)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("MRS %0, basepri_max" : "=r" (result) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set Base Priority
|
||||
|
||||
This function assigns the given value to the Base Priority register.
|
||||
|
||||
\param [in] basePri Base Priority value to set
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __set_BASEPRI(uint32_t value)
|
||||
{
|
||||
__ASM volatile ("MSR basepri, %0" : : "r" (value) );
|
||||
}
|
||||
|
||||
|
||||
/** \brief Get Fault Mask
|
||||
|
||||
This function returns the current value of the Fault Mask register.
|
||||
|
||||
\return Fault Mask register value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __get_FAULTMASK(void)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("MRS %0, faultmask" : "=r" (result) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set Fault Mask
|
||||
|
||||
This function assigns the given value to the Fault Mask register.
|
||||
|
||||
\param [in] faultMask Fault Mask value to set
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __set_FAULTMASK(uint32_t faultMask)
|
||||
{
|
||||
__ASM volatile ("MSR faultmask, %0" : : "r" (faultMask) );
|
||||
}
|
||||
|
||||
#endif /* (__CORTEX_M >= 0x03) */
|
||||
|
||||
|
||||
#if (__CORTEX_M == 0x04)
|
||||
|
||||
/** \brief Get FPSCR
|
||||
|
||||
This function returns the current value of the Floating Point Status/Control register.
|
||||
|
||||
\return Floating Point Status/Control register value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __get_FPSCR(void)
|
||||
{
|
||||
#if (__FPU_PRESENT == 1)
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("MRS %0, fpscr" : "=r" (result) );
|
||||
return(result);
|
||||
#else
|
||||
return(0);
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/** \brief Set FPSCR
|
||||
|
||||
This function assigns the given value to the Floating Point Status/Control register.
|
||||
|
||||
\param [in] fpscr Floating Point Status/Control value to set
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __set_FPSCR(uint32_t fpscr)
|
||||
{
|
||||
#if (__FPU_PRESENT == 1)
|
||||
__ASM volatile ("MSR fpscr, %0" : : "r" (fpscr) );
|
||||
#endif
|
||||
}
|
||||
|
||||
#endif /* (__CORTEX_M == 0x04) */
|
||||
|
||||
|
||||
#elif (defined (__TASKING__)) /*--------------- TASKING Compiler -----------------*/
|
||||
/* TASKING carm specific functions */
|
||||
|
||||
/*
|
||||
* The CMSIS functions have been implemented as intrinsics in the compiler.
|
||||
* Please use "carm -?i" to get an up to date list of all instrinsics,
|
||||
* Including the CMSIS ones.
|
||||
*/
|
||||
|
||||
#endif
|
||||
|
||||
/*@} end of CMSIS_Core_RegAccFunctions */
|
||||
|
||||
|
||||
#endif /* __CORE_CMFUNC_H__ */
|
|
@ -0,0 +1,782 @@
|
|||
/**************************************************************************//**
|
||||
* @file core_cmInstr.h
|
||||
* @brief CMSIS Cortex-M Core Instruction Access Header File
|
||||
* @version V2.01
|
||||
* @date 06. December 2010
|
||||
*
|
||||
* @note
|
||||
* Copyright (C) 2009-2010 ARM Limited. All rights reserved.
|
||||
*
|
||||
* @par
|
||||
* ARM Limited (ARM) is supplying this software for use with Cortex-M
|
||||
* processor based microcontrollers. This file can be freely distributed
|
||||
* within development tools that are supporting such ARM based processors.
|
||||
*
|
||||
* @par
|
||||
* THIS SOFTWARE IS PROVIDED "AS IS". NO WARRANTIES, WHETHER EXPRESS, IMPLIED
|
||||
* OR STATUTORY, INCLUDING, BUT NOT LIMITED TO, IMPLIED WARRANTIES OF
|
||||
* MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE APPLY TO THIS SOFTWARE.
|
||||
* ARM SHALL NOT, IN ANY CIRCUMSTANCES, BE LIABLE FOR SPECIAL, INCIDENTAL, OR
|
||||
* CONSEQUENTIAL DAMAGES, FOR ANY REASON WHATSOEVER.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#ifndef __CORE_CMINSTR_H__
|
||||
#define __CORE_CMINSTR_H__
|
||||
|
||||
|
||||
/* ########################## Core Instruction Access ######################### */
|
||||
/** \defgroup CMSIS_Core_InstructionInterface CMSIS Core Instruction Interface
|
||||
Access to dedicated instructions
|
||||
@{
|
||||
*/
|
||||
|
||||
#if defined ( __CC_ARM ) /*------------------ RealView Compiler ----------------*/
|
||||
/* ARM armcc specific functions */
|
||||
|
||||
/** \brief No Operation
|
||||
|
||||
No Operation does nothing. This instruction can be used for code alignment purposes.
|
||||
*/
|
||||
#define __NOP __nop
|
||||
|
||||
|
||||
/** \brief Wait For Interrupt
|
||||
|
||||
Wait For Interrupt is a hint instruction that suspends execution
|
||||
until one of a number of events occurs.
|
||||
*/
|
||||
#define __WFI __wfi
|
||||
|
||||
|
||||
/** \brief Wait For Event
|
||||
|
||||
Wait For Event is a hint instruction that permits the processor to enter
|
||||
a low-power state until one of a number of events occurs.
|
||||
*/
|
||||
#define __WFE __wfe
|
||||
|
||||
|
||||
/** \brief Send Event
|
||||
|
||||
Send Event is a hint instruction. It causes an event to be signaled to the CPU.
|
||||
*/
|
||||
#define __SEV __sev
|
||||
|
||||
|
||||
/** \brief Instruction Synchronization Barrier
|
||||
|
||||
Instruction Synchronization Barrier flushes the pipeline in the processor,
|
||||
so that all instructions following the ISB are fetched from cache or
|
||||
memory, after the instruction has been completed.
|
||||
*/
|
||||
#define __ISB() __isb(0xF)
|
||||
|
||||
|
||||
/** \brief Data Synchronization Barrier
|
||||
|
||||
This function acts as a special kind of Data Memory Barrier.
|
||||
It completes when all explicit memory accesses before this instruction complete.
|
||||
*/
|
||||
#define __DSB() __dsb(0xF)
|
||||
|
||||
|
||||
/** \brief Data Memory Barrier
|
||||
|
||||
This function ensures the apparent order of the explicit memory operations before
|
||||
and after the instruction, without ensuring their completion.
|
||||
*/
|
||||
#define __DMB() __dmb(0xF)
|
||||
|
||||
|
||||
/** \brief Reverse byte order (32 bit)
|
||||
|
||||
This function reverses the byte order in integer value.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
#define __REV __rev
|
||||
|
||||
|
||||
/** \brief Reverse byte order (16 bit)
|
||||
|
||||
This function reverses the byte order in two unsigned short values.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400677)
|
||||
extern uint32_t __REV16(uint32_t value);
|
||||
#else /* (__ARMCC_VERSION >= 400677) */
|
||||
static __INLINE __ASM uint32_t __REV16(uint32_t value)
|
||||
{
|
||||
rev16 r0, r0
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Reverse byte order in signed short value
|
||||
|
||||
This function reverses the byte order in a signed short value with sign extension to integer.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400677)
|
||||
extern int32_t __REVSH(int32_t value);
|
||||
#else /* (__ARMCC_VERSION >= 400677) */
|
||||
static __INLINE __ASM int32_t __REVSH(int32_t value)
|
||||
{
|
||||
revsh r0, r0
|
||||
bx lr
|
||||
}
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
#if (__CORTEX_M >= 0x03)
|
||||
|
||||
/** \brief Reverse bit order of value
|
||||
|
||||
This function reverses the bit order of the given value.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
#define __RBIT __rbit
|
||||
|
||||
|
||||
/** \brief LDR Exclusive (8 bit)
|
||||
|
||||
This function performs a exclusive LDR command for 8 bit value.
|
||||
|
||||
\param [in] ptr Pointer to data
|
||||
\return value of type uint8_t at (*ptr)
|
||||
*/
|
||||
#define __LDREXB(ptr) ((uint8_t ) __ldrex(ptr))
|
||||
|
||||
|
||||
/** \brief LDR Exclusive (16 bit)
|
||||
|
||||
This function performs a exclusive LDR command for 16 bit values.
|
||||
|
||||
\param [in] ptr Pointer to data
|
||||
\return value of type uint16_t at (*ptr)
|
||||
*/
|
||||
#define __LDREXH(ptr) ((uint16_t) __ldrex(ptr))
|
||||
|
||||
|
||||
/** \brief LDR Exclusive (32 bit)
|
||||
|
||||
This function performs a exclusive LDR command for 32 bit values.
|
||||
|
||||
\param [in] ptr Pointer to data
|
||||
\return value of type uint32_t at (*ptr)
|
||||
*/
|
||||
#define __LDREXW(ptr) ((uint32_t ) __ldrex(ptr))
|
||||
|
||||
|
||||
/** \brief STR Exclusive (8 bit)
|
||||
|
||||
This function performs a exclusive STR command for 8 bit values.
|
||||
|
||||
\param [in] value Value to store
|
||||
\param [in] ptr Pointer to location
|
||||
\return 0 Function succeeded
|
||||
\return 1 Function failed
|
||||
*/
|
||||
#define __STREXB(value, ptr) __strex(value, ptr)
|
||||
|
||||
|
||||
/** \brief STR Exclusive (16 bit)
|
||||
|
||||
This function performs a exclusive STR command for 16 bit values.
|
||||
|
||||
\param [in] value Value to store
|
||||
\param [in] ptr Pointer to location
|
||||
\return 0 Function succeeded
|
||||
\return 1 Function failed
|
||||
*/
|
||||
#define __STREXH(value, ptr) __strex(value, ptr)
|
||||
|
||||
|
||||
/** \brief STR Exclusive (32 bit)
|
||||
|
||||
This function performs a exclusive STR command for 32 bit values.
|
||||
|
||||
\param [in] value Value to store
|
||||
\param [in] ptr Pointer to location
|
||||
\return 0 Function succeeded
|
||||
\return 1 Function failed
|
||||
*/
|
||||
#define __STREXW(value, ptr) __strex(value, ptr)
|
||||
|
||||
|
||||
/** \brief Remove the exclusive lock
|
||||
|
||||
This function removes the exclusive lock which is created by LDREX.
|
||||
|
||||
*/
|
||||
#if (__ARMCC_VERSION < 400000)
|
||||
extern void __CLREX(void);
|
||||
#else /* (__ARMCC_VERSION >= 400000) */
|
||||
#define __CLREX __clrex
|
||||
#endif /* __ARMCC_VERSION */
|
||||
|
||||
|
||||
/** \brief Signed Saturate
|
||||
|
||||
This function saturates a signed value.
|
||||
|
||||
\param [in] value Value to be saturated
|
||||
\param [in] sat Bit position to saturate to (1..32)
|
||||
\return Saturated value
|
||||
*/
|
||||
#define __SSAT __ssat
|
||||
|
||||
|
||||
/** \brief Unsigned Saturate
|
||||
|
||||
This function saturates an unsigned value.
|
||||
|
||||
\param [in] value Value to be saturated
|
||||
\param [in] sat Bit position to saturate to (0..31)
|
||||
\return Saturated value
|
||||
*/
|
||||
#define __USAT __usat
|
||||
|
||||
|
||||
/** \brief Count leading zeros
|
||||
|
||||
This function counts the number of leading zeros of a data value.
|
||||
|
||||
\param [in] value Value to count the leading zeros
|
||||
\return number of leading zeros in value
|
||||
*/
|
||||
#define __CLZ __clz
|
||||
|
||||
#endif /* (__CORTEX_M >= 0x03) */
|
||||
|
||||
|
||||
|
||||
#elif (defined (__ICCARM__)) /*---------------- ICC Compiler ---------------------*/
|
||||
/* IAR iccarm specific functions */
|
||||
|
||||
/* Energy Micro: Add support for new versions of IAR */
|
||||
#if __VER__ >= 6020000
|
||||
#include "cmsis_iar.h"
|
||||
#else
|
||||
/* Energy Micro: Adpaptation end */
|
||||
#include <intrinsics.h> /* IAR Intrinsics */
|
||||
|
||||
#pragma diag_suppress=Pe940
|
||||
|
||||
/** \brief No Operation
|
||||
|
||||
No Operation does nothing. This instruction can be used for code alignment purposes.
|
||||
*/
|
||||
#define __NOP __no_operation
|
||||
|
||||
|
||||
/** \brief Wait For Interrupt
|
||||
|
||||
Wait For Interrupt is a hint instruction that suspends execution
|
||||
until one of a number of events occurs.
|
||||
*/
|
||||
static __INLINE void __WFI(void)
|
||||
{
|
||||
__ASM ("wfi");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Wait For Event
|
||||
|
||||
Wait For Event is a hint instruction that permits the processor to enter
|
||||
a low-power state until one of a number of events occurs.
|
||||
*/
|
||||
static __INLINE void __WFE(void)
|
||||
{
|
||||
__ASM ("wfe");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Send Event
|
||||
|
||||
Send Event is a hint instruction. It causes an event to be signaled to the CPU.
|
||||
*/
|
||||
static __INLINE void __SEV(void)
|
||||
{
|
||||
__ASM ("sev");
|
||||
}
|
||||
|
||||
|
||||
/* intrinsic void __ISB(void) (see intrinsics.h) */
|
||||
/* intrinsic void __DSB(void) (see intrinsics.h) */
|
||||
/* intrinsic void __DMB(void) (see intrinsics.h) */
|
||||
/* intrinsic uint32_t __REV(uint32_t value) (see intrinsics.h) */
|
||||
/* intrinsic __SSAT (see intrinsics.h) */
|
||||
/* intrinsic __USAT (see intrinsics.h) */
|
||||
|
||||
|
||||
/** \brief Reverse byte order (16 bit)
|
||||
|
||||
This function reverses the byte order in two unsigned short values.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
static uint32_t __REV16(uint32_t value)
|
||||
{
|
||||
__ASM("rev16 r0, r0");
|
||||
}
|
||||
|
||||
|
||||
/* intrinsic uint32_t __REVSH(uint32_t value) (see intrinsics.h */
|
||||
|
||||
|
||||
#if (__CORTEX_M >= 0x03)
|
||||
|
||||
/** \brief Reverse bit order of value
|
||||
|
||||
This function reverses the bit order of the given value.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
static uint32_t __RBIT(uint32_t value)
|
||||
{
|
||||
__ASM("rbit r0, r0");
|
||||
}
|
||||
|
||||
|
||||
/** \brief LDR Exclusive (8 bit)
|
||||
|
||||
This function performs a exclusive LDR command for 8 bit value.
|
||||
|
||||
\param [in] ptr Pointer to data
|
||||
\return value of type uint8_t at (*ptr)
|
||||
*/
|
||||
static uint8_t __LDREXB(volatile uint8_t *addr)
|
||||
{
|
||||
__ASM("ldrexb r0, [r0]");
|
||||
}
|
||||
|
||||
|
||||
/** \brief LDR Exclusive (16 bit)
|
||||
|
||||
This function performs a exclusive LDR command for 16 bit values.
|
||||
|
||||
\param [in] ptr Pointer to data
|
||||
\return value of type uint16_t at (*ptr)
|
||||
*/
|
||||
static uint16_t __LDREXH(volatile uint16_t *addr)
|
||||
{
|
||||
__ASM("ldrexh r0, [r0]");
|
||||
}
|
||||
|
||||
|
||||
/** \brief LDR Exclusive (32 bit)
|
||||
|
||||
This function performs a exclusive LDR command for 32 bit values.
|
||||
|
||||
\param [in] ptr Pointer to data
|
||||
\return value of type uint32_t at (*ptr)
|
||||
*/
|
||||
/* intrinsic unsigned long __LDREX(unsigned long *) (see intrinsics.h) */
|
||||
static uint32_t __LDREXW(volatile uint32_t *addr)
|
||||
{
|
||||
__ASM("ldrex r0, [r0]");
|
||||
}
|
||||
|
||||
|
||||
/** \brief STR Exclusive (8 bit)
|
||||
|
||||
This function performs a exclusive STR command for 8 bit values.
|
||||
|
||||
\param [in] value Value to store
|
||||
\param [in] ptr Pointer to location
|
||||
\return 0 Function succeeded
|
||||
\return 1 Function failed
|
||||
*/
|
||||
static uint32_t __STREXB(uint8_t value, volatile uint8_t *addr)
|
||||
{
|
||||
__ASM("strexb r0, r0, [r1]");
|
||||
}
|
||||
|
||||
|
||||
/** \brief STR Exclusive (16 bit)
|
||||
|
||||
This function performs a exclusive STR command for 16 bit values.
|
||||
|
||||
\param [in] value Value to store
|
||||
\param [in] ptr Pointer to location
|
||||
\return 0 Function succeeded
|
||||
\return 1 Function failed
|
||||
*/
|
||||
static uint32_t __STREXH(uint16_t value, volatile uint16_t *addr)
|
||||
{
|
||||
__ASM("strexh r0, r0, [r1]");
|
||||
}
|
||||
|
||||
|
||||
/** \brief STR Exclusive (32 bit)
|
||||
|
||||
This function performs a exclusive STR command for 32 bit values.
|
||||
|
||||
\param [in] value Value to store
|
||||
\param [in] ptr Pointer to location
|
||||
\return 0 Function succeeded
|
||||
\return 1 Function failed
|
||||
*/
|
||||
/* intrinsic unsigned long __STREX(unsigned long, unsigned long) (see intrinsics.h )*/
|
||||
static uint32_t __STREXW(uint32_t value, volatile uint32_t *addr)
|
||||
{
|
||||
__ASM("strex r0, r0, [r1]");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Remove the exclusive lock
|
||||
|
||||
This function removes the exclusive lock which is created by LDREX.
|
||||
|
||||
*/
|
||||
static __INLINE void __CLREX(void)
|
||||
{
|
||||
__ASM ("clrex");
|
||||
}
|
||||
|
||||
/* intrinsic unsigned char __CLZ( unsigned long ) (see intrinsics.h) */
|
||||
|
||||
#endif /* (__CORTEX_M >= 0x03) */
|
||||
|
||||
#pragma diag_default=Pe940
|
||||
|
||||
#endif
|
||||
/* Energy Micro: Fix end */
|
||||
|
||||
|
||||
#elif (defined (__GNUC__)) /*------------------ GNU Compiler ---------------------*/
|
||||
/* GNU gcc specific functions */
|
||||
|
||||
/** \brief No Operation
|
||||
|
||||
No Operation does nothing. This instruction can be used for code alignment purposes.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __NOP(void)
|
||||
{
|
||||
__ASM volatile ("nop");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Wait For Interrupt
|
||||
|
||||
Wait For Interrupt is a hint instruction that suspends execution
|
||||
until one of a number of events occurs.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __WFI(void)
|
||||
{
|
||||
__ASM volatile ("wfi");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Wait For Event
|
||||
|
||||
Wait For Event is a hint instruction that permits the processor to enter
|
||||
a low-power state until one of a number of events occurs.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __WFE(void)
|
||||
{
|
||||
__ASM volatile ("wfe");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Send Event
|
||||
|
||||
Send Event is a hint instruction. It causes an event to be signaled to the CPU.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __SEV(void)
|
||||
{
|
||||
__ASM volatile ("sev");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Instruction Synchronization Barrier
|
||||
|
||||
Instruction Synchronization Barrier flushes the pipeline in the processor,
|
||||
so that all instructions following the ISB are fetched from cache or
|
||||
memory, after the instruction has been completed.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __ISB(void)
|
||||
{
|
||||
__ASM volatile ("isb");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Data Synchronization Barrier
|
||||
|
||||
This function acts as a special kind of Data Memory Barrier.
|
||||
It completes when all explicit memory accesses before this instruction complete.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __DSB(void)
|
||||
{
|
||||
__ASM volatile ("dsb");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Data Memory Barrier
|
||||
|
||||
This function ensures the apparent order of the explicit memory operations before
|
||||
and after the instruction, without ensuring their completion.
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __DMB(void)
|
||||
{
|
||||
__ASM volatile ("dmb");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Reverse byte order (32 bit)
|
||||
|
||||
This function reverses the byte order in integer value.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __REV(uint32_t value)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("rev %0, %1" : "=r" (result) : "r" (value) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Reverse byte order (16 bit)
|
||||
|
||||
This function reverses the byte order in two unsigned short values.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __REV16(uint32_t value)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("rev16 %0, %1" : "=r" (result) : "r" (value) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Reverse byte order in signed short value
|
||||
|
||||
This function reverses the byte order in a signed short value with sign extension to integer.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE int32_t __REVSH(int32_t value)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("revsh %0, %1" : "=r" (result) : "r" (value) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
#if (__CORTEX_M >= 0x03)
|
||||
|
||||
/** \brief Reverse bit order of value
|
||||
|
||||
This function reverses the bit order of the given value.
|
||||
|
||||
\param [in] value Value to reverse
|
||||
\return Reversed value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __RBIT(uint32_t value)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("rbit %0, %1" : "=r" (result) : "r" (value) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief LDR Exclusive (8 bit)
|
||||
|
||||
This function performs a exclusive LDR command for 8 bit value.
|
||||
|
||||
\param [in] ptr Pointer to data
|
||||
\return value of type uint8_t at (*ptr)
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint8_t __LDREXB(volatile uint8_t *addr)
|
||||
{
|
||||
uint8_t result;
|
||||
|
||||
__ASM volatile ("ldrexb %0, [%1]" : "=r" (result) : "r" (addr) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief LDR Exclusive (16 bit)
|
||||
|
||||
This function performs a exclusive LDR command for 16 bit values.
|
||||
|
||||
\param [in] ptr Pointer to data
|
||||
\return value of type uint16_t at (*ptr)
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint16_t __LDREXH(volatile uint16_t *addr)
|
||||
{
|
||||
uint16_t result;
|
||||
|
||||
__ASM volatile ("ldrexh %0, [%1]" : "=r" (result) : "r" (addr) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief LDR Exclusive (32 bit)
|
||||
|
||||
This function performs a exclusive LDR command for 32 bit values.
|
||||
|
||||
\param [in] ptr Pointer to data
|
||||
\return value of type uint32_t at (*ptr)
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __LDREXW(volatile uint32_t *addr)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("ldrex %0, [%1]" : "=r" (result) : "r" (addr) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief STR Exclusive (8 bit)
|
||||
|
||||
This function performs a exclusive STR command for 8 bit values.
|
||||
|
||||
\param [in] value Value to store
|
||||
\param [in] ptr Pointer to location
|
||||
\return 0 Function succeeded
|
||||
\return 1 Function failed
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __STREXB(uint8_t value, volatile uint8_t *addr)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("strexb %0, %2, [%1]" : "=r" (result) : "r" (addr), "r" (value) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief STR Exclusive (16 bit)
|
||||
|
||||
This function performs a exclusive STR command for 16 bit values.
|
||||
|
||||
\param [in] value Value to store
|
||||
\param [in] ptr Pointer to location
|
||||
\return 0 Function succeeded
|
||||
\return 1 Function failed
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __STREXH(uint16_t value, volatile uint16_t *addr)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("strexh %0, %2, [%1]" : "=r" (result) : "r" (addr), "r" (value) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief STR Exclusive (32 bit)
|
||||
|
||||
This function performs a exclusive STR command for 32 bit values.
|
||||
|
||||
\param [in] value Value to store
|
||||
\param [in] ptr Pointer to location
|
||||
\return 0 Function succeeded
|
||||
\return 1 Function failed
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint32_t __STREXW(uint32_t value, volatile uint32_t *addr)
|
||||
{
|
||||
uint32_t result;
|
||||
|
||||
__ASM volatile ("strex %0, %2, [%1]" : "=r" (result) : "r" (addr), "r" (value) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
|
||||
/** \brief Remove the exclusive lock
|
||||
|
||||
This function removes the exclusive lock which is created by LDREX.
|
||||
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE void __CLREX(void)
|
||||
{
|
||||
__ASM volatile ("clrex");
|
||||
}
|
||||
|
||||
|
||||
/** \brief Signed Saturate
|
||||
|
||||
This function saturates a signed value.
|
||||
|
||||
\param [in] value Value to be saturated
|
||||
\param [in] sat Bit position to saturate to (1..32)
|
||||
\return Saturated value
|
||||
*/
|
||||
#define __SSAT(ARG1,ARG2) \
|
||||
({ \
|
||||
uint32_t __RES, __ARG1 = (ARG1); \
|
||||
__ASM ("ssat %0, %1, %2" : "=r" (__RES) : "I" (ARG2), "r" (__ARG1) ); \
|
||||
__RES; \
|
||||
})
|
||||
|
||||
|
||||
/** \brief Unsigned Saturate
|
||||
|
||||
This function saturates an unsigned value.
|
||||
|
||||
\param [in] value Value to be saturated
|
||||
\param [in] sat Bit position to saturate to (0..31)
|
||||
\return Saturated value
|
||||
*/
|
||||
#define __USAT(ARG1,ARG2) \
|
||||
({ \
|
||||
uint32_t __RES, __ARG1 = (ARG1); \
|
||||
__ASM ("usat %0, %1, %2" : "=r" (__RES) : "I" (ARG2), "r" (__ARG1) ); \
|
||||
__RES; \
|
||||
})
|
||||
|
||||
|
||||
/** \brief Count leading zeros
|
||||
|
||||
This function counts the number of leading zeros of a data value.
|
||||
|
||||
\param [in] value Value to count the leading zeros
|
||||
\return number of leading zeros in value
|
||||
*/
|
||||
__attribute__( ( always_inline ) ) static __INLINE uint8_t __CLZ(uint32_t value)
|
||||
{
|
||||
uint8_t result;
|
||||
|
||||
__ASM volatile ("clz %0, %1" : "=r" (result) : "r" (value) );
|
||||
return(result);
|
||||
}
|
||||
|
||||
#endif /* (__CORTEX_M >= 0x03) */
|
||||
|
||||
|
||||
|
||||
|
||||
#elif (defined (__TASKING__)) /*--------------- TASKING Compiler -----------------*/
|
||||
/* TASKING carm specific functions */
|
||||
|
||||
/*
|
||||
* The CMSIS functions have been implemented as intrinsics in the compiler.
|
||||
* Please use "carm -?i" to get an up to date list of all instrinsics,
|
||||
* Including the CMSIS ones.
|
||||
*/
|
||||
|
||||
#endif
|
||||
|
||||
/*@}*/ /* end of group CMSIS_Core_InstructionInterface */
|
||||
|
||||
#endif /* __CORE_CMINSTR_H__ */
|
|
@ -0,0 +1,526 @@
|
|||
/**************************************************************************//**
|
||||
* @file
|
||||
* @brief CMSIS Cortex-M0/M3 Peripheral Access Layer for EFM32 device series
|
||||
*
|
||||
* This is a convenience header file for defining the EFM32 part number on the
|
||||
* build command line, instead of specifying the part specific header file.
|
||||
* @verbatim
|
||||
* Example: Add "-DEFM32G890F128" to your build options, to define part
|
||||
* Add "#include "efm32.h" to your source files
|
||||
* @endverbatim
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2011 Energy Micro AS, http://www.energymicro.com</b>
|
||||
******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
*****************************************************************************/
|
||||
|
||||
#ifndef __EFM32_H
|
||||
#define __EFM32_H
|
||||
|
||||
|
||||
#if defined(EFM32G200F16)
|
||||
#include "efm32g200f16.h"
|
||||
|
||||
#elif defined(EFM32G200F32)
|
||||
#include "efm32g200f32.h"
|
||||
|
||||
#elif defined(EFM32G200F64)
|
||||
#include "efm32g200f64.h"
|
||||
|
||||
#elif defined(EFM32G210F128)
|
||||
#include "efm32g210f128.h"
|
||||
|
||||
#elif defined(EFM32G222F128)
|
||||
#include "efm32g222f128.h"
|
||||
|
||||
#elif defined(EFM32G222F32)
|
||||
#include "efm32g222f32.h"
|
||||
|
||||
#elif defined(EFM32G222F64)
|
||||
#include "efm32g222f64.h"
|
||||
|
||||
#elif defined(EFM32G230F128)
|
||||
#include "efm32g230f128.h"
|
||||
|
||||
#elif defined(EFM32G230F32)
|
||||
#include "efm32g230f32.h"
|
||||
|
||||
#elif defined(EFM32G230F64)
|
||||
#include "efm32g230f64.h"
|
||||
|
||||
#elif defined(EFM32G232F128)
|
||||
#include "efm32g232f128.h"
|
||||
|
||||
#elif defined(EFM32G232F32)
|
||||
#include "efm32g232f32.h"
|
||||
|
||||
#elif defined(EFM32G232F64)
|
||||
#include "efm32g232f64.h"
|
||||
|
||||
#elif defined(EFM32G280F128)
|
||||
#include "efm32g280f128.h"
|
||||
|
||||
#elif defined(EFM32G280F32)
|
||||
#include "efm32g280f32.h"
|
||||
|
||||
#elif defined(EFM32G280F64)
|
||||
#include "efm32g280f64.h"
|
||||
|
||||
#elif defined(EFM32G290F128)
|
||||
#include "efm32g290f128.h"
|
||||
|
||||
#elif defined(EFM32G290F32)
|
||||
#include "efm32g290f32.h"
|
||||
|
||||
#elif defined(EFM32G290F64)
|
||||
#include "efm32g290f64.h"
|
||||
|
||||
#elif defined(EFM32G840F128)
|
||||
#include "efm32g840f128.h"
|
||||
|
||||
#elif defined(EFM32G840F32)
|
||||
#include "efm32g840f32.h"
|
||||
|
||||
#elif defined(EFM32G840F64)
|
||||
#include "efm32g840f64.h"
|
||||
|
||||
#elif defined(EFM32G842F128)
|
||||
#include "efm32g842f128.h"
|
||||
|
||||
#elif defined(EFM32G842F32)
|
||||
#include "efm32g842f32.h"
|
||||
|
||||
#elif defined(EFM32G842F64)
|
||||
#include "efm32g842f64.h"
|
||||
|
||||
#elif defined(EFM32G880F128)
|
||||
#include "efm32g880f128.h"
|
||||
|
||||
#elif defined(EFM32G880F32)
|
||||
#include "efm32g880f32.h"
|
||||
|
||||
#elif defined(EFM32G880F64)
|
||||
#include "efm32g880f64.h"
|
||||
|
||||
#elif defined(EFM32G890F128)
|
||||
#include "efm32g890f128.h"
|
||||
|
||||
#elif defined(EFM32G890F32)
|
||||
#include "efm32g890f32.h"
|
||||
|
||||
#elif defined(EFM32G890F64)
|
||||
#include "efm32g890f64.h"
|
||||
|
||||
#elif defined(EFM32GG230F1024)
|
||||
#include "efm32gg230f1024.h"
|
||||
|
||||
#elif defined(EFM32GG230F512)
|
||||
#include "efm32gg230f512.h"
|
||||
|
||||
#elif defined(EFM32GG232F1024)
|
||||
#include "efm32gg232f1024.h"
|
||||
|
||||
#elif defined(EFM32GG232F512)
|
||||
#include "efm32gg232f512.h"
|
||||
|
||||
#elif defined(EFM32GG280F1024)
|
||||
#include "efm32gg280f1024.h"
|
||||
|
||||
#elif defined(EFM32GG280F512)
|
||||
#include "efm32gg280f512.h"
|
||||
|
||||
#elif defined(EFM32GG290F1024)
|
||||
#include "efm32gg290f1024.h"
|
||||
|
||||
#elif defined(EFM32GG290F512)
|
||||
#include "efm32gg290f512.h"
|
||||
|
||||
#elif defined(EFM32GG295F1024)
|
||||
#include "efm32gg295f1024.h"
|
||||
|
||||
#elif defined(EFM32GG295F512)
|
||||
#include "efm32gg295f512.h"
|
||||
|
||||
#elif defined(EFM32GG330F1024)
|
||||
#include "efm32gg330f1024.h"
|
||||
|
||||
#elif defined(EFM32GG330F512)
|
||||
#include "efm32gg330f512.h"
|
||||
|
||||
#elif defined(EFM32GG332F1024)
|
||||
#include "efm32gg332f1024.h"
|
||||
|
||||
#elif defined(EFM32GG332F512)
|
||||
#include "efm32gg332f512.h"
|
||||
|
||||
#elif defined(EFM32GG380F1024)
|
||||
#include "efm32gg380f1024.h"
|
||||
|
||||
#elif defined(EFM32GG380F512)
|
||||
#include "efm32gg380f512.h"
|
||||
|
||||
#elif defined(EFM32GG390F1024)
|
||||
#include "efm32gg390f1024.h"
|
||||
|
||||
#elif defined(EFM32GG390F512)
|
||||
#include "efm32gg390f512.h"
|
||||
|
||||
#elif defined(EFM32GG395F1024)
|
||||
#include "efm32gg395f1024.h"
|
||||
|
||||
#elif defined(EFM32GG395F512)
|
||||
#include "efm32gg395f512.h"
|
||||
|
||||
#elif defined(EFM32GG840F1024)
|
||||
#include "efm32gg840f1024.h"
|
||||
|
||||
#elif defined(EFM32GG840F512)
|
||||
#include "efm32gg840f512.h"
|
||||
|
||||
#elif defined(EFM32GG842F1024)
|
||||
#include "efm32gg842f1024.h"
|
||||
|
||||
#elif defined(EFM32GG842F512)
|
||||
#include "efm32gg842f512.h"
|
||||
|
||||
#elif defined(EFM32GG880F1024)
|
||||
#include "efm32gg880f1024.h"
|
||||
|
||||
#elif defined(EFM32GG880F512)
|
||||
#include "efm32gg880f512.h"
|
||||
|
||||
#elif defined(EFM32GG890F1024)
|
||||
#include "efm32gg890f1024.h"
|
||||
|
||||
#elif defined(EFM32GG890F512)
|
||||
#include "efm32gg890f512.h"
|
||||
|
||||
#elif defined(EFM32GG895F1024)
|
||||
#include "efm32gg895f1024.h"
|
||||
|
||||
#elif defined(EFM32GG895F512)
|
||||
#include "efm32gg895f512.h"
|
||||
|
||||
#elif defined(EFM32GG940F1024)
|
||||
#include "efm32gg940f1024.h"
|
||||
|
||||
#elif defined(EFM32GG940F512)
|
||||
#include "efm32gg940f512.h"
|
||||
|
||||
#elif defined(EFM32GG942F1024)
|
||||
#include "efm32gg942f1024.h"
|
||||
|
||||
#elif defined(EFM32GG942F512)
|
||||
#include "efm32gg942f512.h"
|
||||
|
||||
#elif defined(EFM32GG980F1024)
|
||||
#include "efm32gg980f1024.h"
|
||||
|
||||
#elif defined(EFM32GG980F512)
|
||||
#include "efm32gg980f512.h"
|
||||
|
||||
#elif defined(EFM32GG990F1024)
|
||||
#include "efm32gg990f1024.h"
|
||||
|
||||
#elif defined(EFM32GG990F512)
|
||||
#include "efm32gg990f512.h"
|
||||
|
||||
#elif defined(EFM32GG995F1024)
|
||||
#include "efm32gg995f1024.h"
|
||||
|
||||
#elif defined(EFM32GG995F512)
|
||||
#include "efm32gg995f512.h"
|
||||
|
||||
#elif defined(EFM32LG230F128)
|
||||
#include "efm32lg230f128.h"
|
||||
|
||||
#elif defined(EFM32LG230F256)
|
||||
#include "efm32lg230f256.h"
|
||||
|
||||
#elif defined(EFM32LG230F64)
|
||||
#include "efm32lg230f64.h"
|
||||
|
||||
#elif defined(EFM32LG232F128)
|
||||
#include "efm32lg232f128.h"
|
||||
|
||||
#elif defined(EFM32LG232F256)
|
||||
#include "efm32lg232f256.h"
|
||||
|
||||
#elif defined(EFM32LG232F64)
|
||||
#include "efm32lg232f64.h"
|
||||
|
||||
#elif defined(EFM32LG280F128)
|
||||
#include "efm32lg280f128.h"
|
||||
|
||||
#elif defined(EFM32LG280F256)
|
||||
#include "efm32lg280f256.h"
|
||||
|
||||
#elif defined(EFM32LG280F64)
|
||||
#include "efm32lg280f64.h"
|
||||
|
||||
#elif defined(EFM32LG290F128)
|
||||
#include "efm32lg290f128.h"
|
||||
|
||||
#elif defined(EFM32LG290F256)
|
||||
#include "efm32lg290f256.h"
|
||||
|
||||
#elif defined(EFM32LG290F64)
|
||||
#include "efm32lg290f64.h"
|
||||
|
||||
#elif defined(EFM32LG295F128)
|
||||
#include "efm32lg295f128.h"
|
||||
|
||||
#elif defined(EFM32LG295F256)
|
||||
#include "efm32lg295f256.h"
|
||||
|
||||
#elif defined(EFM32LG295F64)
|
||||
#include "efm32lg295f64.h"
|
||||
|
||||
#elif defined(EFM32LG330F128)
|
||||
#include "efm32lg330f128.h"
|
||||
|
||||
#elif defined(EFM32LG330F256)
|
||||
#include "efm32lg330f256.h"
|
||||
|
||||
#elif defined(EFM32LG330F64)
|
||||
#include "efm32lg330f64.h"
|
||||
|
||||
#elif defined(EFM32LG332F128)
|
||||
#include "efm32lg332f128.h"
|
||||
|
||||
#elif defined(EFM32LG332F256)
|
||||
#include "efm32lg332f256.h"
|
||||
|
||||
#elif defined(EFM32LG332F64)
|
||||
#include "efm32lg332f64.h"
|
||||
|
||||
#elif defined(EFM32LG380F128)
|
||||
#include "efm32lg380f128.h"
|
||||
|
||||
#elif defined(EFM32LG380F256)
|
||||
#include "efm32lg380f256.h"
|
||||
|
||||
#elif defined(EFM32LG380F64)
|
||||
#include "efm32lg380f64.h"
|
||||
|
||||
#elif defined(EFM32LG390F128)
|
||||
#include "efm32lg390f128.h"
|
||||
|
||||
#elif defined(EFM32LG390F256)
|
||||
#include "efm32lg390f256.h"
|
||||
|
||||
#elif defined(EFM32LG390F64)
|
||||
#include "efm32lg390f64.h"
|
||||
|
||||
#elif defined(EFM32LG395F128)
|
||||
#include "efm32lg395f128.h"
|
||||
|
||||
#elif defined(EFM32LG395F256)
|
||||
#include "efm32lg395f256.h"
|
||||
|
||||
#elif defined(EFM32LG395F64)
|
||||
#include "efm32lg395f64.h"
|
||||
|
||||
#elif defined(EFM32LG840F128)
|
||||
#include "efm32lg840f128.h"
|
||||
|
||||
#elif defined(EFM32LG840F256)
|
||||
#include "efm32lg840f256.h"
|
||||
|
||||
#elif defined(EFM32LG840F64)
|
||||
#include "efm32lg840f64.h"
|
||||
|
||||
#elif defined(EFM32LG842F128)
|
||||
#include "efm32lg842f128.h"
|
||||
|
||||
#elif defined(EFM32LG842F256)
|
||||
#include "efm32lg842f256.h"
|
||||
|
||||
#elif defined(EFM32LG842F64)
|
||||
#include "efm32lg842f64.h"
|
||||
|
||||
#elif defined(EFM32LG880F128)
|
||||
#include "efm32lg880f128.h"
|
||||
|
||||
#elif defined(EFM32LG880F256)
|
||||
#include "efm32lg880f256.h"
|
||||
|
||||
#elif defined(EFM32LG880F64)
|
||||
#include "efm32lg880f64.h"
|
||||
|
||||
#elif defined(EFM32LG890F128)
|
||||
#include "efm32lg890f128.h"
|
||||
|
||||
#elif defined(EFM32LG890F256)
|
||||
#include "efm32lg890f256.h"
|
||||
|
||||
#elif defined(EFM32LG890F64)
|
||||
#include "efm32lg890f64.h"
|
||||
|
||||
#elif defined(EFM32LG895F128)
|
||||
#include "efm32lg895f128.h"
|
||||
|
||||
#elif defined(EFM32LG895F256)
|
||||
#include "efm32lg895f256.h"
|
||||
|
||||
#elif defined(EFM32LG895F64)
|
||||
#include "efm32lg895f64.h"
|
||||
|
||||
#elif defined(EFM32LG940F128)
|
||||
#include "efm32lg940f128.h"
|
||||
|
||||
#elif defined(EFM32LG940F256)
|
||||
#include "efm32lg940f256.h"
|
||||
|
||||
#elif defined(EFM32LG940F64)
|
||||
#include "efm32lg940f64.h"
|
||||
|
||||
#elif defined(EFM32LG942F128)
|
||||
#include "efm32lg942f128.h"
|
||||
|
||||
#elif defined(EFM32LG942F256)
|
||||
#include "efm32lg942f256.h"
|
||||
|
||||
#elif defined(EFM32LG942F64)
|
||||
#include "efm32lg942f64.h"
|
||||
|
||||
#elif defined(EFM32LG980F128)
|
||||
#include "efm32lg980f128.h"
|
||||
|
||||
#elif defined(EFM32LG980F256)
|
||||
#include "efm32lg980f256.h"
|
||||
|
||||
#elif defined(EFM32LG980F64)
|
||||
#include "efm32lg980f64.h"
|
||||
|
||||
#elif defined(EFM32LG990F128)
|
||||
#include "efm32lg990f128.h"
|
||||
|
||||
#elif defined(EFM32LG990F256)
|
||||
#include "efm32lg990f256.h"
|
||||
|
||||
#elif defined(EFM32LG990F64)
|
||||
#include "efm32lg990f64.h"
|
||||
|
||||
#elif defined(EFM32LG995F128)
|
||||
#include "efm32lg995f128.h"
|
||||
|
||||
#elif defined(EFM32LG995F256)
|
||||
#include "efm32lg995f256.h"
|
||||
|
||||
#elif defined(EFM32LG995F64)
|
||||
#include "efm32lg995f64.h"
|
||||
|
||||
#elif defined(EFM32TG108F16)
|
||||
#include "efm32tg108f16.h"
|
||||
|
||||
#elif defined(EFM32TG108F32)
|
||||
#include "efm32tg108f32.h"
|
||||
|
||||
#elif defined(EFM32TG108F4)
|
||||
#include "efm32tg108f4.h"
|
||||
|
||||
#elif defined(EFM32TG108F8)
|
||||
#include "efm32tg108f8.h"
|
||||
|
||||
#elif defined(EFM32TG110F16)
|
||||
#include "efm32tg110f16.h"
|
||||
|
||||
#elif defined(EFM32TG110F32)
|
||||
#include "efm32tg110f32.h"
|
||||
|
||||
#elif defined(EFM32TG110F4)
|
||||
#include "efm32tg110f4.h"
|
||||
|
||||
#elif defined(EFM32TG110F8)
|
||||
#include "efm32tg110f8.h"
|
||||
|
||||
#elif defined(EFM32TG210F16)
|
||||
#include "efm32tg210f16.h"
|
||||
|
||||
#elif defined(EFM32TG210F32)
|
||||
#include "efm32tg210f32.h"
|
||||
|
||||
#elif defined(EFM32TG210F8)
|
||||
#include "efm32tg210f8.h"
|
||||
|
||||
#elif defined(EFM32TG222F16)
|
||||
#include "efm32tg222f16.h"
|
||||
|
||||
#elif defined(EFM32TG222F32)
|
||||
#include "efm32tg222f32.h"
|
||||
|
||||
#elif defined(EFM32TG222F8)
|
||||
#include "efm32tg222f8.h"
|
||||
|
||||
#elif defined(EFM32TG230F16)
|
||||
#include "efm32tg230f16.h"
|
||||
|
||||
#elif defined(EFM32TG230F32)
|
||||
#include "efm32tg230f32.h"
|
||||
|
||||
#elif defined(EFM32TG230F8)
|
||||
#include "efm32tg230f8.h"
|
||||
|
||||
#elif defined(EFM32TG232F16)
|
||||
#include "efm32tg232f16.h"
|
||||
|
||||
#elif defined(EFM32TG232F32)
|
||||
#include "efm32tg232f32.h"
|
||||
|
||||
#elif defined(EFM32TG232F8)
|
||||
#include "efm32tg232f8.h"
|
||||
|
||||
#elif defined(EFM32TG822F16)
|
||||
#include "efm32tg822f16.h"
|
||||
|
||||
#elif defined(EFM32TG822F32)
|
||||
#include "efm32tg822f32.h"
|
||||
|
||||
#elif defined(EFM32TG822F8)
|
||||
#include "efm32tg822f8.h"
|
||||
|
||||
#elif defined(EFM32TG840F16)
|
||||
#include "efm32tg840f16.h"
|
||||
|
||||
#elif defined(EFM32TG840F32)
|
||||
#include "efm32tg840f32.h"
|
||||
|
||||
#elif defined(EFM32TG840F8)
|
||||
#include "efm32tg840f8.h"
|
||||
|
||||
#elif defined(EFM32TG842F16)
|
||||
#include "efm32tg842f16.h"
|
||||
|
||||
#elif defined(EFM32TG842F32)
|
||||
#include "efm32tg842f32.h"
|
||||
|
||||
#elif defined(EFM32TG842F8)
|
||||
#include "efm32tg842f8.h"
|
||||
|
||||
|
||||
#else
|
||||
#error "efm32.h: PART NUMBER undefined"
|
||||
#endif
|
||||
|
||||
#endif
|
||||
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,369 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief CMSIS Cortex-M3 Peripheral Access Layer for EFM32 devices.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2011 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include <stdint.h>
|
||||
#include "efm32.h"
|
||||
|
||||
/*******************************************************************************
|
||||
****************************** DEFINES ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** LFRCO frequency, tuned to below frequency during manufacturing. */
|
||||
#define EFM32_LFRCO_FREQ (32768UL)
|
||||
#define EFM32_ULFRCO_FREQ (1000UL)
|
||||
|
||||
/*******************************************************************************
|
||||
************************** LOCAL VARIABLES ********************************
|
||||
******************************************************************************/
|
||||
|
||||
/* System oscillator frequencies. These frequencies are normally constant */
|
||||
/* for a target, but they are made configurable in order to allow run-time */
|
||||
/* handling of different boards. The crystal oscillator clocks can be set */
|
||||
/* compile time to a non-default value by defining respective EFM32_nFXO_FREQ */
|
||||
/* values according to board design. By defining the EFM32_nFXO_FREQ to 0, */
|
||||
/* one indicates that the oscillator is not present, in order to save some */
|
||||
/* SW footprint. */
|
||||
|
||||
#ifndef EFM32_HFXO_FREQ
|
||||
#ifdef _EFM32_GIANT_FAMILY
|
||||
#define EFM32_HFXO_FREQ (48000000UL)
|
||||
#else
|
||||
#define EFM32_HFXO_FREQ (32000000UL)
|
||||
#endif
|
||||
#endif
|
||||
/* Do not define variable if HF crystal oscillator not present */
|
||||
#if (EFM32_HFXO_FREQ > 0)
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
/** System HFXO clock. */
|
||||
static uint32_t SystemHFXOClock = EFM32_HFXO_FREQ;
|
||||
/** @endcond (DO_NOT_INCLUDE_WITH_DOXYGEN) */
|
||||
#endif
|
||||
|
||||
#ifndef EFM32_LFXO_FREQ
|
||||
#define EFM32_LFXO_FREQ (EFM32_LFRCO_FREQ)
|
||||
#endif
|
||||
/* Do not define variable if LF crystal oscillator not present */
|
||||
#if (EFM32_LFXO_FREQ > 0)
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
/** System LFXO clock. */
|
||||
static uint32_t SystemLFXOClock = EFM32_LFXO_FREQ;
|
||||
/** @endcond (DO_NOT_INCLUDE_WITH_DOXYGEN) */
|
||||
#endif
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL VARIABLES *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* System System Clock Frequency (Core Clock).
|
||||
*
|
||||
* @details
|
||||
* Required CMSIS global variable that must be kept up-to-date.
|
||||
*/
|
||||
uint32_t SystemCoreClock;
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get the current core clock frequency.
|
||||
*
|
||||
* @details
|
||||
* Calculate and get the current core clock frequency based on the current
|
||||
* configuration. Assuming that the SystemCoreClock global variable is
|
||||
* maintained, the core clock frequency is stored in that variable as well.
|
||||
* This function will however calculate the core clock based on actual HW
|
||||
* configuration. It will also update the SystemCoreClock global variable.
|
||||
*
|
||||
* @note
|
||||
* This is an EFM32 proprietary function, not part of the CMSIS definition.
|
||||
*
|
||||
* @return
|
||||
* The current core clock frequency in Hz.
|
||||
******************************************************************************/
|
||||
uint32_t SystemCoreClockGet(void)
|
||||
{
|
||||
uint32_t ret;
|
||||
|
||||
ret = SystemHFClockGet();
|
||||
#if defined (_EFM32_GIANT_FAMILY)
|
||||
/* Leopard/Giant Gecko has an additional divider */
|
||||
ret = ret / (1 + ((CMU->CTRL & _CMU_CTRL_HFCLKDIV_MASK)>>_CMU_CTRL_HFCLKDIV_SHIFT));
|
||||
#endif
|
||||
ret >>= (CMU->HFCORECLKDIV & _CMU_HFCORECLKDIV_HFCORECLKDIV_MASK) >>
|
||||
_CMU_HFCORECLKDIV_HFCORECLKDIV_SHIFT;
|
||||
|
||||
/* Keep CMSIS variable up-to-date just in case */
|
||||
SystemCoreClock = ret;
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get the current HFCLK frequency.
|
||||
*
|
||||
* @note
|
||||
* This is an EFM32 proprietary function, not part of the CMSIS definition.
|
||||
*
|
||||
* @return
|
||||
* The current HFCLK frequency in Hz.
|
||||
******************************************************************************/
|
||||
uint32_t SystemHFClockGet(void)
|
||||
{
|
||||
uint32_t ret;
|
||||
|
||||
switch (CMU->STATUS & (CMU_STATUS_HFRCOSEL | CMU_STATUS_HFXOSEL |
|
||||
CMU_STATUS_LFRCOSEL | CMU_STATUS_LFXOSEL))
|
||||
{
|
||||
case CMU_STATUS_LFXOSEL:
|
||||
#if (EFM32_LFXO_FREQ > 0)
|
||||
ret = SystemLFXOClock;
|
||||
#else
|
||||
/* We should not get here, since core should not be clocked. May */
|
||||
/* be caused by a misconfiguration though. */
|
||||
ret = 0;
|
||||
#endif
|
||||
break;
|
||||
|
||||
case CMU_STATUS_LFRCOSEL:
|
||||
ret = EFM32_LFRCO_FREQ;
|
||||
break;
|
||||
|
||||
case CMU_STATUS_HFXOSEL:
|
||||
#if (EFM32_HFXO_FREQ > 0)
|
||||
ret = SystemHFXOClock;
|
||||
#else
|
||||
/* We should not get here, since core should not be clocked. May */
|
||||
/* be caused by a misconfiguration though. */
|
||||
ret = 0;
|
||||
#endif
|
||||
break;
|
||||
|
||||
default: /* CMU_STATUS_HFRCOSEL */
|
||||
switch (CMU->HFRCOCTRL & _CMU_HFRCOCTRL_BAND_MASK)
|
||||
{
|
||||
case CMU_HFRCOCTRL_BAND_28MHZ:
|
||||
ret = 28000000;
|
||||
break;
|
||||
|
||||
case CMU_HFRCOCTRL_BAND_21MHZ:
|
||||
ret = 21000000;
|
||||
break;
|
||||
|
||||
case CMU_HFRCOCTRL_BAND_14MHZ:
|
||||
ret = 14000000;
|
||||
break;
|
||||
|
||||
case CMU_HFRCOCTRL_BAND_11MHZ:
|
||||
ret = 11000000;
|
||||
break;
|
||||
|
||||
case CMU_HFRCOCTRL_BAND_7MHZ:
|
||||
ret = 7000000;
|
||||
break;
|
||||
|
||||
case CMU_HFRCOCTRL_BAND_1MHZ:
|
||||
ret = 1000000;
|
||||
break;
|
||||
|
||||
default:
|
||||
ret = 0;
|
||||
break;
|
||||
}
|
||||
break;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Get high frequency crystal oscillator clock frequency for target system.
|
||||
*
|
||||
* @note
|
||||
* This is an EFM32 proprietary function, not part of the CMSIS definition.
|
||||
*
|
||||
* @return
|
||||
* HFXO frequency in Hz.
|
||||
*****************************************************************************/
|
||||
uint32_t SystemHFXOClockGet(void)
|
||||
{
|
||||
/* External crystal oscillator present? */
|
||||
#if (EFM32_HFXO_FREQ > 0)
|
||||
return SystemHFXOClock;
|
||||
#else
|
||||
return 0;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Set high frequency crystal oscillator clock frequency for target system.
|
||||
*
|
||||
* @note
|
||||
* This function is mainly provided for being able to handle target systems
|
||||
* with different HF crystal oscillator frequencies run-time. If used, it
|
||||
* should probably only be used once during system startup.
|
||||
*
|
||||
* @note
|
||||
* This is an EFM32 proprietary function, not part of the CMSIS definition.
|
||||
*
|
||||
* @param[in] freq
|
||||
* HFXO frequency in Hz used for target.
|
||||
*****************************************************************************/
|
||||
void SystemHFXOClockSet(uint32_t freq)
|
||||
{
|
||||
/* External crystal oscillator present? */
|
||||
#if (EFM32_HFXO_FREQ > 0)
|
||||
SystemHFXOClock = freq;
|
||||
|
||||
/* Update core clock frequency if HFXO is used to clock core */
|
||||
if (CMU->STATUS & CMU_STATUS_HFXOSEL)
|
||||
{
|
||||
/* The function will update the global variable */
|
||||
SystemCoreClockGet();
|
||||
}
|
||||
#else
|
||||
(void)freq; /* Unused parameter */
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Initialize the system.
|
||||
*
|
||||
* @details
|
||||
* Do required generic HW system init.
|
||||
*
|
||||
* @note
|
||||
* This function is invoked during system init, before the main() routine
|
||||
* and any data has been initialized. For this reason, it cannot do any
|
||||
* initialization of variables etc.
|
||||
*****************************************************************************/
|
||||
void SystemInit(void)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Get low frequency RC oscillator clock frequency for target system.
|
||||
*
|
||||
* @note
|
||||
* This is an EFM32 proprietary function, not part of the CMSIS definition.
|
||||
*
|
||||
* @return
|
||||
* LFRCO frequency in Hz.
|
||||
*****************************************************************************/
|
||||
uint32_t SystemLFRCOClockGet(void)
|
||||
{
|
||||
/* Currently we assume that this frequency is properly tuned during */
|
||||
/* manufacturing and is not changed after reset. If future requirements */
|
||||
/* for re-tuning by user, we can add support for that. */
|
||||
return EFM32_LFRCO_FREQ;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Get ultra low frequency RC oscillator clock frequency for target system.
|
||||
*
|
||||
* @note
|
||||
* This is an EFM32 proprietary function, not part of the CMSIS definition.
|
||||
*
|
||||
* @return
|
||||
* ULFRCO frequency in Hz.
|
||||
*****************************************************************************/
|
||||
uint32_t SystemULFRCOClockGet(void)
|
||||
{
|
||||
/* The ULFRCO frequency is not tuned, and can be very inaccurate */
|
||||
return EFM32_ULFRCO_FREQ;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Get low frequency crystal oscillator clock frequency for target system.
|
||||
*
|
||||
* @note
|
||||
* This is an EFM32 proprietary function, not part of the CMSIS definition.
|
||||
*
|
||||
* @return
|
||||
* LFXO frequency in Hz.
|
||||
*****************************************************************************/
|
||||
uint32_t SystemLFXOClockGet(void)
|
||||
{
|
||||
/* External crystal oscillator present? */
|
||||
#if (EFM32_LFXO_FREQ > 0)
|
||||
return SystemLFXOClock;
|
||||
#else
|
||||
return 0;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Set low frequency crystal oscillator clock frequency for target system.
|
||||
*
|
||||
* @note
|
||||
* This function is mainly provided for being able to handle target systems
|
||||
* with different HF crystal oscillator frequencies run-time. If used, it
|
||||
* should probably only be used once during system startup.
|
||||
*
|
||||
* @note
|
||||
* This is an EFM32 proprietary function, not part of the CMSIS definition.
|
||||
*
|
||||
* @param[in] freq
|
||||
* LFXO frequency in Hz used for target.
|
||||
*****************************************************************************/
|
||||
void SystemLFXOClockSet(uint32_t freq)
|
||||
{
|
||||
/* External crystal oscillator present? */
|
||||
#if (EFM32_LFXO_FREQ > 0)
|
||||
SystemLFXOClock = freq;
|
||||
|
||||
/* Update core clock frequency if LFXO is used to clock core */
|
||||
if (CMU->STATUS & CMU_STATUS_LFXOSEL)
|
||||
{
|
||||
/* The function will update the global variable */
|
||||
SystemCoreClockGet();
|
||||
}
|
||||
#else
|
||||
(void)freq; /* Unused parameter */
|
||||
#endif
|
||||
}
|
|
@ -0,0 +1,215 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief CMSIS Cortex-M3 Peripheral Access Layer for EFM32 devices.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2011 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#ifndef __SYSTEM_EFM32_H
|
||||
#define __SYSTEM_EFM32_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include <stdint.h>
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL VARIABLES *******************************
|
||||
******************************************************************************/
|
||||
|
||||
extern uint32_t SystemCoreClock; /**< System Clock Frequency (Core Clock) */
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
/* Interrupt routines - prototypes */
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
void Reset_Handler(void);
|
||||
void NMI_Handler(void);
|
||||
void HardFault_Handler(void);
|
||||
void MemManage_Handler(void);
|
||||
void BusFault_Handler(void);
|
||||
void UsageFault_Handler(void);
|
||||
void SVC_Handler(void);
|
||||
void DebugMon_Handler(void);
|
||||
void PendSV_Handler(void);
|
||||
void SysTick_Handler(void);
|
||||
void DMA_IRQHandler(void);
|
||||
void GPIO_EVEN_IRQHandler(void);
|
||||
void TIMER0_IRQHandler(void);
|
||||
void USART0_RX_IRQHandler(void);
|
||||
void USART0_TX_IRQHandler(void);
|
||||
void ACMP0_IRQHandler(void);
|
||||
void ADC0_IRQHandler(void);
|
||||
void DAC0_IRQHandler(void);
|
||||
void I2C0_IRQHandler(void);
|
||||
void GPIO_ODD_IRQHandler(void);
|
||||
void TIMER1_IRQHandler(void);
|
||||
void TIMER2_IRQHandler(void);
|
||||
void USART1_RX_IRQHandler(void);
|
||||
void USART1_TX_IRQHandler(void);
|
||||
void USART2_RX_IRQHandler(void);
|
||||
void USART2_TX_IRQHandler(void);
|
||||
void UART0_RX_IRQHandler(void);
|
||||
void UART0_TX_IRQHandler(void);
|
||||
void LEUART0_IRQHandler(void);
|
||||
void LEUART1_IRQHandler(void);
|
||||
void LETIMER0_IRQHandler(void);
|
||||
void PCNT0_IRQHandler(void);
|
||||
void PCNT1_IRQHandler(void);
|
||||
void PCNT2_IRQHandler(void);
|
||||
void RTC_IRQHandler(void);
|
||||
void CMU_IRQHandler(void);
|
||||
void VCMP_IRQHandler(void);
|
||||
void LCD_IRQHandler(void);
|
||||
void MSC_IRQHandler(void);
|
||||
void AES_IRQHandler(void);
|
||||
#endif
|
||||
|
||||
#if defined(_EFM32_TINY_FAMILY)
|
||||
void Reset_Handler(void);
|
||||
void NMI_Handler(void);
|
||||
void HardFault_Handler(void);
|
||||
void MemManage_Handler(void);
|
||||
void BusFault_Handler(void);
|
||||
void UsageFault_Handler(void);
|
||||
void SVC_Handler(void);
|
||||
void DebugMon_Handler(void);
|
||||
void PendSV_Handler(void);
|
||||
void SysTick_Handler(void);
|
||||
void DMA_IRQHandler(void);
|
||||
void GPIO_EVEN_IRQHandler(void);
|
||||
void TIMER0_IRQHandler(void);
|
||||
void USART0_RX_IRQHandler(void);
|
||||
void USART0_TX_IRQHandler(void);
|
||||
void ACMP0_IRQHandler(void);
|
||||
void ADC0_IRQHandler(void);
|
||||
void DAC0_IRQHandler(void);
|
||||
void I2C0_IRQHandler(void);
|
||||
void GPIO_ODD_IRQHandler(void);
|
||||
void TIMER1_IRQHandler(void);
|
||||
void USART1_RX_IRQHandler(void);
|
||||
void USART1_TX_IRQHandler(void);
|
||||
void LESENSE_IRQHandler(void);
|
||||
void LEUART0_IRQHandler(void);
|
||||
void LETIMER0_IRQHandler(void);
|
||||
void PCNT0_IRQHandler(void);
|
||||
void RTC_IRQHandler(void);
|
||||
void CMU_IRQHandler(void);
|
||||
void VCMP_IRQHandler(void);
|
||||
void LCD_IRQHandler(void);
|
||||
void MSC_IRQHandler(void);
|
||||
void AES_IRQHandler(void);
|
||||
#endif
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
void Reset_Handler(void);
|
||||
void NMI_Handler(void);
|
||||
void HardFault_Handler(void);
|
||||
void MemManage_Handler(void);
|
||||
void BusFault_Handler(void);
|
||||
void UsageFault_Handler(void);
|
||||
void SVC_Handler(void);
|
||||
void DebugMon_Handler(void);
|
||||
void PendSV_Handler(void);
|
||||
void SysTick_Handler(void);
|
||||
void DMA_IRQHandler(void);
|
||||
void GPIO_EVEN_IRQHandler(void);
|
||||
void TIMER0_IRQHandler(void);
|
||||
void USART0_RX_IRQHandler(void);
|
||||
void USART0_TX_IRQHandler(void);
|
||||
void USB_IRQHandler(void);
|
||||
void ACMP0_IRQHandler(void);
|
||||
void ADC0_IRQHandler(void);
|
||||
void DAC0_IRQHandler(void);
|
||||
void I2C0_IRQHandler(void);
|
||||
void I2C1_IRQHandler(void);
|
||||
void GPIO_ODD_IRQHandler(void);
|
||||
void TIMER1_IRQHandler(void);
|
||||
void TIMER2_IRQHandler(void);
|
||||
void TIMER3_IRQHandler(void);
|
||||
void USART1_RX_IRQHandler(void);
|
||||
void USART1_TX_IRQHandler(void);
|
||||
void LESENSE_IRQHandler(void);
|
||||
void USART2_RX_IRQHandler(void);
|
||||
void USART2_TX_IRQHandler(void);
|
||||
void UART0_RX_IRQHandler(void);
|
||||
void UART0_TX_IRQHandler(void);
|
||||
void UART1_RX_IRQHandler(void);
|
||||
void UART1_TX_IRQHandler(void);
|
||||
void LEUART0_IRQHandler(void);
|
||||
void LEUART1_IRQHandler(void);
|
||||
void LETIMER0_IRQHandler(void);
|
||||
void PCNT0_IRQHandler(void);
|
||||
void PCNT1_IRQHandler(void);
|
||||
void PCNT2_IRQHandler(void);
|
||||
void RTC_IRQHandler(void);
|
||||
void BURTC_IRQHandler(void);
|
||||
void CMU_IRQHandler(void);
|
||||
void VCMP_IRQHandler(void);
|
||||
void LCD_IRQHandler(void);
|
||||
void MSC_IRQHandler(void);
|
||||
void AES_IRQHandler(void);
|
||||
void EBI_IRQHandler(void);
|
||||
void EMU_IRQHandler(void);
|
||||
#endif
|
||||
|
||||
uint32_t SystemCoreClockGet(void);
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Update CMSIS SystemCoreClock variable.
|
||||
*
|
||||
* @details
|
||||
* CMSIS defines a global variable SystemCoreClock that shall hold the
|
||||
* core frequency in Hz. If the core frequency is dynamically changed, the
|
||||
* variable must be kept updated in order to be CMSIS compliant.
|
||||
*
|
||||
* Notice that if only changing core clock frequency through the EFM32 CMU
|
||||
* API, this variable will be kept updated. This function is only provided
|
||||
* for CMSIS compliance and if a user modifies the the core clock outside
|
||||
* the CMU API.
|
||||
*****************************************************************************/
|
||||
static __INLINE void SystemCoreClockUpdate(void)
|
||||
{
|
||||
SystemCoreClockGet();
|
||||
}
|
||||
|
||||
void SystemInit(void);
|
||||
|
||||
uint32_t SystemHFClockGet(void);
|
||||
uint32_t SystemHFXOClockGet(void);
|
||||
void SystemHFXOClockSet(uint32_t freq);
|
||||
uint32_t SystemLFRCOClockGet(void);
|
||||
uint32_t SystemULFRCOClockGet(void);
|
||||
uint32_t SystemLFXOClockGet(void);
|
||||
void SystemLFXOClockSet(uint32_t freq);
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __SYSTEM_EFM32_H */
|
Binary file not shown.
|
@ -0,0 +1,154 @@
|
|||
================ Revision history ============================================
|
||||
2.3.2:
|
||||
- Fixed IAR startup files, corrected alignment of interrupt vector table
|
||||
- Updated efm32usb library with fixes
|
||||
- Updated efm32lib with new Tiny Gecko and Giant Gecko features
|
||||
|
||||
2.3.0:
|
||||
- Added DEVICE_FAMILY defines to identify Gecko/Tiny/Leopard/Giant parts
|
||||
- Fixed missing EMU_IRQ definitions in Leopard Gecko startup files
|
||||
- Added USART location to Tiny Gecko parts
|
||||
- Added LEUART locations to Tiny Gecko parts
|
||||
- Updated efm32lib with new Giant Gecko features (see separate readme)
|
||||
- Updated efm32usb with USB Host stack support (see separate readme)
|
||||
|
||||
2.2.2:
|
||||
- Removed huge AF_PORT, AF_PIN macros from header files, only peripheral
|
||||
specific alternate function defines are included
|
||||
- Updated efm32usb library with fixes
|
||||
- Updated efm32lib library with fixes
|
||||
|
||||
2.2.1:
|
||||
- Added interleave to all Giant Gecko parts
|
||||
- Updated efm32lib with more Giant Gecko features
|
||||
- Added efm32usb, USB Device stack for Giant Gecko USB parts
|
||||
- Added LOCATION defines for all I2C alternate locations on Tiny Gecko
|
||||
|
||||
2.1.1:
|
||||
- Added header files for Giant Gecko and Leopard Gecko devices
|
||||
- Minor fix for Gecko devices, EMU_CTRL_MASK was wrong
|
||||
- Fix for linker issue alignment of .data section in codesourcery .ld files
|
||||
|
||||
2.0.1:
|
||||
- DAC_OPAnMUX_POSSEL_OPAnIN changed to DAC_OPAnMUX_POSSEL_OPAnINP for Tiny
|
||||
Gecko
|
||||
- Added CMU_ROUTE_LOCATION, LOC2 for Tiny Gecko
|
||||
- PRS #define fixes, remove extra IRDA fields only available on USART0
|
||||
|
||||
2.0.0:
|
||||
- This release based on CMSIS_2_00, includes DSP_Lib (for Keil MDKARM, IAR has
|
||||
a port included with EWARM)
|
||||
- Removed "shadow" example that used to be in CMSIS directory earlier, use
|
||||
"blink" from board examples as starting point instead
|
||||
- Restructured header files to comply with CMSIS_2_00
|
||||
- CMU_CALCTRL_REFSEL is renamed to CMU_CALCTRL_UPSEL to match reference
|
||||
manual and clearify new DOWNSEL calibrartion features for Tiny Gecko
|
||||
- Added header files for new package types for Gecko devices
|
||||
- Added header files for Tiny Gecko devices
|
||||
|
||||
1.3.0:
|
||||
- DMA register WAITSTATUS changed to CHWAITSTATUS for consistency
|
||||
DMA test req/sreq registers added, CHSREQSTATUS and CHREQSTATUS
|
||||
- IFS and IFC interrupt registers are now marked as readable for several
|
||||
peripherals
|
||||
- TIMER, CCC renamed to CDTI
|
||||
- TIMER, QEM has been renamed to QDM
|
||||
- AF_DBG_SWV/TCLK/TDIO renamed to more commonly used AF_DBG_SWD/SWDIO/SWDCLK
|
||||
- AF_EBI_ADDRDAT renamed to AF_EBI_AD
|
||||
- Removed bit fields for extra LCD segment registers for Gecko parts
|
||||
- Fixed LCD_SEGEN_MASK, bit width was too narrow in version 1.2.x
|
||||
- Fixed LCD_SYNCBUSY bit fields
|
||||
- CMU_PCNTCTRL reset values corrected
|
||||
- PCNT_TOP and PCNT_TOPB reset values corrected
|
||||
- ADC_LPFMODE_RCFILT and LPFMOD_DECAP definitions corrected (they were
|
||||
reversed)
|
||||
- USART_RXDATAFULLRIGHT and USART_RXDATAVRIGHT removed for Gecko parts
|
||||
- GPIO, renamed INSENSE_PRSSENSE to INSENSE_PRS, similar for INT
|
||||
to be consistent with updated documentation (Reference Manual)
|
||||
|
||||
1.2.1:
|
||||
- Fixed DEVINFO calibration shift and mask value for temperature sensor
|
||||
fixed in rev.C Gecko devices
|
||||
|
||||
1.2.0:
|
||||
- Added new subgroup "Parts" for all part definitions in doxygen format
|
||||
- Removed unused _PARAM_ type definitions, less clutter in header files
|
||||
- _CMU_PCNTCTRL_RESETVALUE corrected
|
||||
- Added C startup file for IAR, can be used as replacement for assembly file
|
||||
- Use #defines instead of "numeric values reentered" in bit field definitions
|
||||
- TIMER_PARAM_CCNUM(i) changed to TIMER_PARAM_CC_NUM(i)
|
||||
- DPI_CHAN_COUNT changed to PRS_CHAN_COUNT
|
||||
|
||||
1.1.4:
|
||||
- TIMER_INIT_DEFAULT fix to efm32lib
|
||||
|
||||
1.1.3:
|
||||
- Removed ADC ROUTE register
|
||||
- Renamed DEVINFO DACCAL -> DAC0CAL for all 3 calibration registers and bit
|
||||
fields
|
||||
- Updated efm32lib with new peripherals
|
||||
|
||||
1.1.2:
|
||||
- Added support for CodeSourcery Sourcery G++ compiler and startup files
|
||||
- Device Information page (DEVINFO_TypeDef) - fixed several issues with
|
||||
endianness, and other changes to support test revision 4 and above parts.
|
||||
This has led to a small incompatibilty with test rev <= 4 and rev A parts,
|
||||
in that the flash and sram size bit fields has changed location.
|
||||
- DMA_CONTROL_TypeDef changed name to DMA_DESCRIPTOR_TypeDef to be better
|
||||
aligned with PL230 manual and code
|
||||
- DMA bit fields not supported on EFM32 was removed for the PL230 controller
|
||||
- DMA CTRL bit fields renamed to be more consistent with PL230 TRM manual
|
||||
- Added additional volatile statements to pointers in DMA Control structure
|
||||
- Fixed several registers that were readable, and was marked as __O (output
|
||||
only)
|
||||
|
||||
1.1.1:
|
||||
- Fixed startup code, CMSIS SystemInit cannot update global variable
|
||||
|
||||
1.1.0:
|
||||
- Note - some register bit field updates in this release are _not_ backward
|
||||
compatible
|
||||
- Updated register bit fields to comply with documentation updates, i.e.
|
||||
reference manual version > 0.83
|
||||
- Apply patch to CMSIS core for GCC issues
|
||||
- Added DMA_CONTROL_TypeDef control block for PrimeCell PL230 DMA controller
|
||||
- Added ROMTABLE PID / CHIP revision table and masks
|
||||
- Revised and updated Device Information page structure "DEVINFO page"
|
||||
This structure is ONLY valid for rev.B production devices
|
||||
- GPIO EXTIPSEL bit field marked "16" changed to 15 (bug correction)
|
||||
- Added more bit fields to TIMER_ROUTE registers
|
||||
- Cosmetic updates in doxygen comments and copyright statements
|
||||
|
||||
1.0.4:
|
||||
- ACMP INPUTSEL bit fields changed from ohm rating to res-n,
|
||||
- Added bit-band base addresses for peripherals and sram
|
||||
|
||||
1.0.3:
|
||||
- ADC SCANMODE and SCANCTRL bit field updates and corrections
|
||||
- Moved Readme.txt and Changes.txt to CMSIS/Readme-EFM32.txt and
|
||||
CMSIS/Changes-EFM32.txt
|
||||
- CCPEN and CDTIPEN splitted in TIMER_ROUTE
|
||||
- EMVREG in EMU_CTRL enumeration changed
|
||||
- LCD DISPCTRL volatage levels are part specific, changed settings changed to
|
||||
reflect this
|
||||
- Added "UL" (unsigned long) to some bit fields giving warnings due to sign
|
||||
conversion
|
||||
|
||||
1.0.2:
|
||||
- Corrected revision numbers in file headers
|
||||
- Removed example code that was moved into BSP/DVK installer package
|
||||
|
||||
1.0.1:
|
||||
- Updated to use official CMSIS1V30 release
|
||||
- Corrected IRQ vector table in assembly startup files, IMEM to MSC,
|
||||
UDMA to DMA
|
||||
- DMA peripheral/signal names corrected
|
||||
- Example Blinky application updated to work on all EFM32 MCU-Modules on DVK
|
||||
- Added "simple" board support package to example
|
||||
- Added "UL" (unsigned long) tag to several fields
|
||||
|
||||
1.0.0:
|
||||
- Initial release
|
||||
- Includes CMSIS1V30 2nd PreRelease
|
||||
- Now requires two include paths, CMSIS/CM3/DeviceSupport/EnergyMicro/EFM32 and
|
||||
CMSIS/CM3/CoreSupport
|
|
@ -0,0 +1,39 @@
|
|||
* -------------------------------------------------------------------
|
||||
* Copyright (C) 2010 ARM Limited. All rights reserved.
|
||||
*
|
||||
* Date: 30 November 2010
|
||||
* Revision: V2.00
|
||||
*
|
||||
* Project: Cortex Microcontroller Software Interface Standard (CMSIS)
|
||||
* Title: Release Note for CMSIS
|
||||
*
|
||||
* -------------------------------------------------------------------
|
||||
|
||||
|
||||
NOTE - Open the index.html file to access CMSIS documentation
|
||||
|
||||
|
||||
The Cortex Microcontroller Software Interface Standard (CMSIS) provides a single standard across all
|
||||
Cortex-Mx processor series vendors. It enables code re-use and code sharing across software projects
|
||||
and reduces time-to-market for new embedded applications.
|
||||
|
||||
CMSIS is released under the terms of the end user license agreement ("CMSIS END USER LICENCE AGREEMENT.pdf").
|
||||
Any user of the software package is bound to the terms and conditions of the end user license agreement.
|
||||
|
||||
|
||||
You will find the following sub-directories:
|
||||
|
||||
CM0 - CMSIS Core Support and Device Support package for Cortex-M0.
|
||||
|
||||
CM3 - CMSIS Core Support and Device Support package for Cortex-M3.
|
||||
|
||||
CM4 - CMSIS Core Support and Device Support package for Cortex-M4.
|
||||
|
||||
Documentation - Contains CMSIS documentation.
|
||||
|
||||
DSP_Lib - MDK project files, Examples and source files etc.. to build the
|
||||
CMSIS DSP Software Library for Cortex-M3 and Cortex-M4 processors.
|
||||
|
||||
Template_DeviceSupport - Template files for CMSIS Device Support package.
|
||||
|
||||
---
|
|
@ -0,0 +1,85 @@
|
|||
================ EFM32 Device Support Library (DSL) ==========================
|
||||
|
||||
This directory ,"CMSIS", contains the Energy Micro Support Library for the
|
||||
EFM32 series of microcontrollers.
|
||||
|
||||
================ About CMSIS =================================================
|
||||
|
||||
The library is based on CMSIS, the Cortex Microcontroller Software Interface
|
||||
Standard, as defined by ARM Inc.
|
||||
|
||||
For more information about CMSIS see
|
||||
http://www.onarm.com
|
||||
http://www.arm.com/products/CPUs/CMSIS.html
|
||||
|
||||
In short, CMSIS tries to provide a common interface for programming devices
|
||||
having one of the Cortex-M core architectures, making code sharing and reuse
|
||||
easier.
|
||||
|
||||
================ Development Environments ====================================
|
||||
|
||||
You will need a development environment which supports the Energy Micro EFM32
|
||||
devices. Currently this is either
|
||||
|
||||
IAR Embedded Workbench for ARM 5.40.6 or later, http://www.iar.com
|
||||
Keil uVision "MDK-ARM" 4.01 or later, http://www.keil.com
|
||||
Rowley CodeSourcery for ARM v2.0.5 or later, see http://www.rowley.co.uk
|
||||
Codesourcery Sourcery G++, see http://www.codesourcery.com
|
||||
|
||||
It is possible to develop with other tools, but for now these are the well
|
||||
supported development environment for Energy Micro example code.
|
||||
|
||||
This library uses C99-types, requires the presence of <stdint.h> and can use
|
||||
other functionality standardized in C99. If your compiler has a C99 compliance
|
||||
toggle, you should enable it for your projects.
|
||||
|
||||
================ File structure ==============================================
|
||||
|
||||
Short getting started guide:
|
||||
|
||||
The quickest way to start is to base your work on one of the simple example
|
||||
projects for the Energy Micro Development or Stareter Kits. These should be
|
||||
easy to port and change to adopt to your needs.
|
||||
|
||||
The board support packages for the various Energy Micro kits comes with a
|
||||
"blink" example, that serves as a good starting point for new projects.
|
||||
|
||||
Please note that you _will_ need to change the "Debugger" and "Flash/Download"
|
||||
configuration settings to fit your environment. See your IDE's manual for
|
||||
details.
|
||||
|
||||
Support for the EFM32 device family is located in the directory
|
||||
CMSIS/CM3/DeviceSupport/EnergyMicro/EFM32
|
||||
|
||||
The most convenient way to start a project, is to define the device target
|
||||
in your compiler options, e.g. add a -DEFM32G890F128 to your compile options
|
||||
if you are targetting an EFM32G890F128 part.
|
||||
|
||||
When this is done, you should include the file "efm32.h" wherever you need
|
||||
register and bit field definitions for the EFM32 peripherals.
|
||||
|
||||
The peripheral registers follow the CMSIS convention of defining a structure
|
||||
which holds the "volatile" registers. Again, take a look at the examples for
|
||||
usage.
|
||||
|
||||
================ Licenses ====================================================
|
||||
|
||||
See the top of each file for SW license. Basically you are free to use the
|
||||
Energy Micro code for any project using EFM32 devices. Part of the CMSIS
|
||||
library is copyrighted by ARM Inc. See "License.doc" for ARM's CMSIS license.
|
||||
|
||||
================ Software updates ============================================
|
||||
|
||||
Energy Micro continually works to provide updated and improved DSL, example
|
||||
code and other software of use for EFM32 customers. Please check the download
|
||||
section of
|
||||
|
||||
http://www.energymicro.com/downloads
|
||||
|
||||
for the latest releases, news and updates.
|
||||
|
||||
(C) Copyright Energy Micro AS, 2011
|
||||
|
||||
|
||||
|
||||
|
|
@ -0,0 +1,145 @@
|
|||
================ Revision history ============================================
|
||||
2.3.2:
|
||||
- Added Tiny Gecko and Giant Gecko support in RMU for new reset causes
|
||||
- CMU_ClockFreqGet will now report correct clock rates if HFLE is set (/4)
|
||||
- Added Giant Gecko specific MSC_MassErase(), erase entire flash
|
||||
- Added Giant Gecko specific MSC_BusStrategy (inline) function
|
||||
- MSC_Init() will now configure TIMEBASE correctly according to AUXHFRCO clock
|
||||
rate for Tiny Gecko and Giant Gecko
|
||||
|
||||
2.3.0:
|
||||
- USART - Added USART_InitPrsTrigger to initialize USART PRS triggered
|
||||
transmissions.
|
||||
- CMU - numerous updates, now supports full clock tree of Giant/Tiny Gecko
|
||||
- CMU_ClockDivSet/Get will now use real dividend and not logarithmic values
|
||||
as earlier. Prior enumerated values have been kept for backward compatibility.
|
||||
- Added support for CMU HFLE and DIV4 factor for core clock for LE
|
||||
peripherals
|
||||
- Added support for alternate LCD segment animation range for Giant Gecko
|
||||
- Fixed bug: Don't enable VCMP low power reference until after warm up,
|
||||
allow biasprog value of 0 in VCMP_Init()
|
||||
- Added support for ALTMAP (256MB address map) in EBI_BankAddress()
|
||||
- TIMER_Init() will now reset CNT value
|
||||
|
||||
2.2.2:
|
||||
- Added DAC0 channel 0 and 1 to ACMP for Tiny and Giant devices
|
||||
- Fixed bug in CMU for MSC WAITSTATE configuration, leading to too high wait
|
||||
states depending on clock rate
|
||||
- Fixed bug in CMU for UART1 clock enable
|
||||
|
||||
2.2.1:
|
||||
- UART_Reset() and LEUART_Reset() will now reset ROUTE register as well, this
|
||||
will mean GPIO pins will not be driven after this call. Take care to ensure
|
||||
that GPIO ROUTE register is configured after calls to *UART_Init*Sync
|
||||
- Fixed problems with EFM_ASSERT when using UART in USART API
|
||||
- Added Giant Gecko support for EBI (new modes and TFT direct drive)
|
||||
- Added Giant Gecko support for CMU 2 WAIT STATES, and I2C1
|
||||
- Added Giant Gecko support for UART1 in CMU
|
||||
- Added Giant Gecko support for DMA LOOP and 2D Copy operations
|
||||
|
||||
2.1.0:
|
||||
- EMU_Restore will now disable HFRCO if it was not enabled when entering
|
||||
an Energy Mode
|
||||
- Run time changes only applies to Gecko devices, filter out Tiny and Giant
|
||||
for CHIP_Init();
|
||||
- Added const specificers to various initialization structures, to ensure
|
||||
they can reside in flash instead of SRAM
|
||||
- Bugfix in efm32_i2c.c, keep returning i2cTransferInProgress until done
|
||||
|
||||
2.0.1:
|
||||
- Changed enum OPAMP_PosSel_TypeDef. Enum value opaPosSelOpaIn changed from
|
||||
DAC_OPA0MUX_POSSEL_OPA1IN to DAC_OPA0MUX_POSSEL_OPA0INP.
|
||||
- Bugfix in efm32_lesense.h, LESENSE_ChClk_TypeDef now contains unshifted
|
||||
values, fixed the implementation in efm32_lesense.c where the bug prevented
|
||||
the sampleClk to be set to AUXHFRCO.
|
||||
|
||||
2.0.0:
|
||||
- USART_Init-functions now calls USART_Reset() which will also disable/reset
|
||||
interrupt
|
||||
- USART_BaudrateSyncSet() now asserts on invalid oversample configuration
|
||||
- Added initialization of parity bit in LEUART_Init()
|
||||
- Added Tiny Gecko support for CMU, ULFRCO, LESENSE clocks and continuous
|
||||
calibration
|
||||
- Added Tiny Gecko support for GPIO, EM4 pin retention and wake up support
|
||||
- Added Tiny Gecko support for I2S, SPI auto TX mode on USART
|
||||
- Added Tiny Gecko support for CACHE mesasurements for MSC module
|
||||
- Added Tiny Gecko support for LCD module (with no HIGH segment registers)
|
||||
- Added Tiny Gecko support for TIMER, PWM 2x, (DT lock not supported)
|
||||
- Added Tiny Gecko support for LESENSE module
|
||||
- Added Tiny Gecko support for PRS input in PCNT
|
||||
- Added Tiny Gecko support for async signals in PRS, PRS_SourceAsyncSignalSet()
|
||||
- Initial support for some Giant Gecko features, where overlapping with Tiny
|
||||
- Removed LPFEN / LPFREQ support from DAC
|
||||
- Fixed comments around interrupt functions, making it clear it is bitwise
|
||||
logical or interrupt flags
|
||||
- Fixed PCNT initialization for external clock configurations, making sure
|
||||
config is synchronized at startup to 3 clocks. Note fix only works for
|
||||
>revC EFM32G devices.
|
||||
- Fixed efm32_cmu.c, EFM_ASSERT statement for LEUART clock div logic was
|
||||
inverted
|
||||
- Fixed ADC_InitScan, PRSSEL shift value corrected
|
||||
- Fixed CMU_ClockFreqGet for devices that do not have I2C
|
||||
- Fixed I2C_TransferInit for devices with more than one I2C-bus (Giant Gecko)
|
||||
- Changed ACMP_Disable() implementation, now only disables the ACMP instance
|
||||
by clearing the EN bit in the CTRL register
|
||||
- Removed ACMP_DisableNoReset() function
|
||||
- Fixed ACMP_Init(), removed automatic enabling, added new structure member
|
||||
"enaReq" for ACMP_Init_TypeDef to control, fixed the EFM_ASSERT of the
|
||||
biasprog parameter
|
||||
- Added default configuration macro ACMP_INIT_DEFAULT for ACMP_Init_TypeDef
|
||||
- Fixed ACMP_CapsenseInit(), removed automatic enabling, added new structure member
|
||||
"enaReq" for ACMP_CapsenseInit_TypeDef to control, fixed the EFM_ASSERT of
|
||||
the biasprog parameter
|
||||
- Changed the name of the default configuration macro for
|
||||
ACMP_CapsenseInit_TypeDef to ACMP_CAPSENSE_INIT_DEFAULT
|
||||
- Added RTC_Reset and RTC_CounterReset functions for RTC
|
||||
|
||||
1.3.0:
|
||||
- MSC is automatically enabled/disabled when using the MSC API. This saves
|
||||
power, and reduces errors due to not calling MSC_Init().
|
||||
- Added API for controlling Cortex-M3 MPU (memory protection unit)
|
||||
- Adjusted bit fields to comply with latest CMSIS release, see EFM_CMSIS
|
||||
changes file for details
|
||||
- Fixed issue with bit mask clearing in ACMP
|
||||
- Functions ACMP_Enable and ACMP_DisableNoReset added
|
||||
- Added comment about rev.C chips in PCNT, CMD_LTOPBIM not neccessary any more
|
||||
- Added missing instance validity asserts to peripherals (ACMP, LEUART, USART)
|
||||
- Fixed UART0 check in CMU_ClockFreqGet()
|
||||
- Fixed command sync for PCNT before setting TOPB value during init
|
||||
- Fixed instance validity check macro in PCNT
|
||||
- Fixed TIMER_Reset() removed write to unimplemented timer channel registers
|
||||
- Fixed EFM_ASSERT statements in ACMP, VCMP
|
||||
- General code style update: added missing curly braces, default cases, etc.
|
||||
|
||||
1.2.1:
|
||||
- Feature complete efm32lib, now also includes peripheral API for modules
|
||||
AES,PCNT,MSC,ACMP,VCMP,LCD,EBI
|
||||
- Fixed _TIMER_CC_CTRL_ICEDGE flags for correct timer configuration
|
||||
- Fixed ADC calibration of Single and Scan mode of operation
|
||||
- Added PCNT (ChipRev A/B PCNT0 errata NOT supported) and AES support
|
||||
- Fixed conditional inclusion in efm32_emu.h
|
||||
- Fixed code for LEUART0 for devices with multiple LEUARTs.
|
||||
- Fixed incorrect setting of DOUT for GPIO configuration
|
||||
|
||||
1.1.4
|
||||
- Fix for TIMER_INIT_DEFAULT
|
||||
|
||||
1.1.3:
|
||||
- Added ADC, DAC, LETIMER, PRS, TIMER (except DTI) support
|
||||
- Added utility for fetching chip revision (efm32_system.c/h)
|
||||
- Removed RTC instance ref in API, only one RTC will be supported
|
||||
(Affects also define in efm32_cmu.h)
|
||||
- Added default init struct macros for LEUART, USART
|
||||
- Added msbf parameter in USART synchronous init struct, USART_InitSync_TypeDef.
|
||||
- Updated reset for I2C, USART, LEUART to also reset IEN register.
|
||||
- Corrected fault in GPIO_PortOutSet()
|
||||
|
||||
1.1.2:
|
||||
- Corrected minor issues in EMU, EM3 mode when restoring clocks
|
||||
- Corrected RMU reset cause checking
|
||||
- Changed GPIO enumerator symbols to start with gpio (from GPIO_)
|
||||
- Changed CMU and WDOG enum typedefs to start with CMU_/WDOG_ (from cmu/wdog)
|
||||
- Added USART/UART, LEUART, DMA, I2C support
|
||||
|
||||
1.1.1:
|
||||
- First version including support for CMU, DBG, EMU, GPIO, RTC, WDOG
|
|
@ -0,0 +1,75 @@
|
|||
================ EFM32 Peripheral Library ===================================
|
||||
|
||||
This directory, "efm32lib", contains the Energy Micro Peripheral Support
|
||||
library for the EFM32 series of microcontrollers.
|
||||
|
||||
The "efm32lib" SW is designed to support EFM32 Gecko rev B and later versions.
|
||||
The following known caveats exists for rev A devices:
|
||||
|
||||
- CMU: HFRCO band tuning values are not correctly set for rev A.
|
||||
- EMU: Errata "Peripheral clocks not gated in EM2/EM3 with debug session
|
||||
active" has not been implemented with SW workaround for rev A.
|
||||
|
||||
Some design guidelines for this library:
|
||||
|
||||
* Follow the guidelines established by ARM's and Energy Micro's adaptation
|
||||
of the CMSIS (see below) standard
|
||||
|
||||
* Be usable as a starting point for developing richer, more target specific
|
||||
functionality (i.e. copy and modify further)
|
||||
|
||||
* Ability to be used as a standalone software component, used by other drivers
|
||||
that should cover "the most common cases"
|
||||
|
||||
* Readability of the code and usability preferred before optimization for speed
|
||||
and size or covering a particular "narrow" purpose
|
||||
|
||||
* As little "cross-dependency" between modules as possible, to enable users to
|
||||
pick and choose what they want
|
||||
|
||||
================ About CMSIS ================================================
|
||||
|
||||
These APIs are based on EFM32_CMSIS, the Cortex Microcontroller Software
|
||||
Interface Standard support headers, as supplied by Energy Micro AS.
|
||||
|
||||
As a result of this, the library requires basic C99-support. You might have
|
||||
to enable C99 support in your compiler. Comments are in doxygen compatible
|
||||
format.
|
||||
|
||||
The EFM32_CMSIS library contains all peripheral module registers and bit field
|
||||
descriptors.
|
||||
|
||||
To download EFM32_CMSIS, go to
|
||||
http://www.energymicro.com/downloads
|
||||
|
||||
For more information about CMSIS see
|
||||
http://www.onarm.com
|
||||
http://www.arm.com/products/CPUs/CMSIS.html
|
||||
|
||||
The requirements for using CMSIS also apply to this package.
|
||||
|
||||
================ File structure ==============================================
|
||||
|
||||
inc/ - header files
|
||||
src/ - source files
|
||||
|
||||
================ Licenses ====================================================
|
||||
|
||||
See the top of each file for SW license. Basically you are free to use the
|
||||
Energy Micro code for any project using EFM32 devices. Parts of the CMSIS
|
||||
library is copyrighted by ARM Inc. See "License.doc" for ARM's CMSIS license.
|
||||
|
||||
================ Software updates ============================================
|
||||
|
||||
Energy Micro continually works to provide updated and improved efm32lib,
|
||||
example code and other software of use for EFM32 customers. Please check the
|
||||
download section of Energy Micro's web site at
|
||||
|
||||
http://www.energymicro.com/downloads
|
||||
|
||||
for the latest releases, news and updates. If you download and install the
|
||||
Simplicity Studio application, you will be notified about updates when
|
||||
available.
|
||||
|
||||
|
||||
(C) Copyright Energy Micro AS, 2011
|
|
@ -0,0 +1,395 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Analog Comparator (ACMP) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2011 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_ACMP_H
|
||||
#define __EFM32_ACMP_H
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup ACMP
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Resistor values used for capacative sense. See the datasheet for your
|
||||
* device for details on each resistor value. */
|
||||
typedef enum
|
||||
{
|
||||
/** resistor value 0 */
|
||||
acmpResistor0 = _ACMP_INPUTSEL_CSRESSEL_RES0,
|
||||
/** resistor value 1 */
|
||||
acmpResistor1 = _ACMP_INPUTSEL_CSRESSEL_RES1,
|
||||
/** resistor value 2 */
|
||||
acmpResistor2 = _ACMP_INPUTSEL_CSRESSEL_RES2,
|
||||
/** resistor value 3 */
|
||||
acmpResistor3 = _ACMP_INPUTSEL_CSRESSEL_RES3
|
||||
} ACMP_CapsenseResistor_TypeDef;
|
||||
|
||||
/** Hysteresis level. See datasheet for your device for details on each
|
||||
* level. */
|
||||
typedef enum
|
||||
{
|
||||
acmpHysteresisLevel0 = _ACMP_CTRL_HYSTSEL_HYST0, /**< Hysteresis level 0 */
|
||||
acmpHysteresisLevel1 = _ACMP_CTRL_HYSTSEL_HYST1, /**< Hysteresis level 1 */
|
||||
acmpHysteresisLevel2 = _ACMP_CTRL_HYSTSEL_HYST2, /**< Hysteresis level 2 */
|
||||
acmpHysteresisLevel3 = _ACMP_CTRL_HYSTSEL_HYST3, /**< Hysteresis level 3 */
|
||||
acmpHysteresisLevel4 = _ACMP_CTRL_HYSTSEL_HYST4, /**< Hysteresis level 4 */
|
||||
acmpHysteresisLevel5 = _ACMP_CTRL_HYSTSEL_HYST5, /**< Hysteresis level 5 */
|
||||
acmpHysteresisLevel6 = _ACMP_CTRL_HYSTSEL_HYST6, /**< Hysteresis level 6 */
|
||||
acmpHysteresisLevel7 = _ACMP_CTRL_HYSTSEL_HYST7 /**< Hysteresis level 7 */
|
||||
} ACMP_HysteresisLevel_TypeDef;
|
||||
|
||||
/** ACMP warmup time. The delay is measured in HFPERCLK cycles and should
|
||||
* be at least 10 us. */
|
||||
typedef enum
|
||||
{
|
||||
/** 4 HFPERCLK cycles warmup */
|
||||
acmpWarmTime4 = _ACMP_CTRL_WARMTIME_4CYCLES,
|
||||
/** 8 HFPERCLK cycles warmup */
|
||||
acmpWarmTime8 = _ACMP_CTRL_WARMTIME_8CYCLES,
|
||||
/** 16 HFPERCLK cycles warmup */
|
||||
acmpWarmTime16 = _ACMP_CTRL_WARMTIME_16CYCLES,
|
||||
/** 32 HFPERCLK cycles warmup */
|
||||
acmpWarmTime32 = _ACMP_CTRL_WARMTIME_32CYCLES,
|
||||
/** 64 HFPERCLK cycles warmup */
|
||||
acmpWarmTime64 = _ACMP_CTRL_WARMTIME_64CYCLES,
|
||||
/** 128 HFPERCLK cycles warmup */
|
||||
acmpWarmTime128 = _ACMP_CTRL_WARMTIME_128CYCLES,
|
||||
/** 256 HFPERCLK cycles warmup */
|
||||
acmpWarmTime256 = _ACMP_CTRL_WARMTIME_256CYCLES,
|
||||
/** 512 HFPERCLK cycles warmup */
|
||||
acmpWarmTime512 = _ACMP_CTRL_WARMTIME_512CYCLES
|
||||
} ACMP_WarmTime_TypeDef;
|
||||
|
||||
/** ACMP inputs. Note that scaled VDD and bandgap references can only be used
|
||||
* as negative inputs. */
|
||||
typedef enum
|
||||
{
|
||||
/** Channel 0 */
|
||||
acmpChannel0 = _ACMP_INPUTSEL_NEGSEL_CH0,
|
||||
/** Channel 1 */
|
||||
acmpChannel1 = _ACMP_INPUTSEL_NEGSEL_CH1,
|
||||
/** Channel 2 */
|
||||
acmpChannel2 = _ACMP_INPUTSEL_NEGSEL_CH2,
|
||||
/** Channel 3 */
|
||||
acmpChannel3 = _ACMP_INPUTSEL_NEGSEL_CH3,
|
||||
/** Channel 4 */
|
||||
acmpChannel4 = _ACMP_INPUTSEL_NEGSEL_CH4,
|
||||
/** Channel 5 */
|
||||
acmpChannel5 = _ACMP_INPUTSEL_NEGSEL_CH5,
|
||||
/** Channel 6 */
|
||||
acmpChannel6 = _ACMP_INPUTSEL_NEGSEL_CH6,
|
||||
/** Channel 7 */
|
||||
acmpChannel7 = _ACMP_INPUTSEL_NEGSEL_CH7,
|
||||
/** 1.25V internal reference */
|
||||
acmpChannel1V25 = _ACMP_INPUTSEL_NEGSEL_1V25,
|
||||
/** 2.5V internal reference */
|
||||
acmpChannel2V5 = _ACMP_INPUTSEL_NEGSEL_2V5,
|
||||
/** Scaled VDD reference */
|
||||
acmpChannelVDD = _ACMP_INPUTSEL_NEGSEL_VDD,
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
/** DAC0 channel 0 */
|
||||
acmpChannelDAC0Ch0 = _ACMP_INPUTSEL_NEGSEL_DAC0CH0,
|
||||
/** DAC0 channel 1 */
|
||||
acmpChannelDAC0Ch1 = _ACMP_INPUTSEL_NEGSEL_DAC0CH1,
|
||||
#endif
|
||||
} ACMP_Channel_TypeDef;
|
||||
|
||||
/*******************************************************************************
|
||||
****************************** STRUCTS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Capsense initialization structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Full bias current. See the ACMP chapter about bias and response time in
|
||||
* the reference manual for details. */
|
||||
bool fullBias;
|
||||
|
||||
/** Half bias current. See the ACMP chapter about bias and response time in
|
||||
* the reference manual for details. */
|
||||
bool halfBias;
|
||||
|
||||
/** Bias current. See the ACMP chapter about bias and response time in the
|
||||
* reference manual for details. Valid values are in the range 0-7. */
|
||||
uint32_t biasProg;
|
||||
|
||||
/** Warmup time. This is measured in HFPERCLK cycles and should be
|
||||
* about 10us in wall clock time. */
|
||||
ACMP_WarmTime_TypeDef warmTime;
|
||||
|
||||
/** Hysteresis level */
|
||||
ACMP_HysteresisLevel_TypeDef hysteresisLevel;
|
||||
|
||||
/** Resistor used in the capacative sensing circuit. For values see
|
||||
* your device datasheet. */
|
||||
ACMP_CapsenseResistor_TypeDef resistor;
|
||||
|
||||
/** Low power reference enabled. This setting, if enabled, reduces the
|
||||
* power used by the VDD and bandgap references. */
|
||||
bool lowPowerReferenceEnabled;
|
||||
|
||||
/** Vdd reference value. VDD_SCALED = VDD × VDDLEVEL × 50mV/3.8V.
|
||||
* Valid values are in the range 0-63. */
|
||||
uint32_t vddLevel;
|
||||
|
||||
/** If true, ACMP is being enabled after configuration. */
|
||||
bool enable;
|
||||
} ACMP_CapsenseInit_TypeDef;
|
||||
|
||||
/** Default config for capacitive sense mode initialization. */
|
||||
#define ACMP_CAPSENSE_INIT_DEFAULT \
|
||||
{ false, /* fullBias */ \
|
||||
false, /* halfBias */ \
|
||||
0x7, /* biasProg */ \
|
||||
acmpWarmTime512, /* 512 cycle warmup to be safe */ \
|
||||
acmpHysteresisLevel5, \
|
||||
acmpResistor3, \
|
||||
false, /* low power reference */ \
|
||||
0x3D, /* VDD level */ \
|
||||
true /* Enable after init. */ \
|
||||
}
|
||||
|
||||
/** ACMP initialization structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Full bias current. See the ACMP chapter about bias and response time in
|
||||
* the reference manual for details. */
|
||||
bool fullBias;
|
||||
|
||||
/** Half bias current. See the ACMP chapter about bias and response time in
|
||||
* the reference manual for details. */
|
||||
bool halfBias;
|
||||
|
||||
/** Bias current. See the ACMP chapter about bias and response time in the
|
||||
* reference manual for details. Valid values are in the range 0-7. */
|
||||
uint32_t biasProg;
|
||||
|
||||
/** Enable setting the interrupt flag on falling edge */
|
||||
bool interruptOnFallingEdge;
|
||||
|
||||
/** Enable setting the interrupt flag on rising edge */
|
||||
bool interruptOnRisingEdge;
|
||||
|
||||
/** Warmup time. This is measured in HFPERCLK cycles and should be
|
||||
* about 10us in wall clock time. */
|
||||
ACMP_WarmTime_TypeDef warmTime;
|
||||
|
||||
/** Hysteresis level */
|
||||
ACMP_HysteresisLevel_TypeDef hysteresisLevel;
|
||||
|
||||
/** Inactive value emitted by the ACMP during warmup */
|
||||
bool inactiveValue;
|
||||
|
||||
/** Low power reference enabled. This setting, if enabled, reduces the
|
||||
* power used by the VDD and bandgap references. */
|
||||
bool lowPowerReferenceEnabled;
|
||||
|
||||
/** Vdd reference value. VDD_SCALED = VDD × VDDLEVEL × 50mV/3.8V.
|
||||
* Valid values are in the range 0-63. */
|
||||
uint32_t vddLevel;
|
||||
|
||||
/** If true, ACMP is being enabled after configuration. */
|
||||
bool enable;
|
||||
} ACMP_Init_TypeDef;
|
||||
|
||||
/** Default config for ACMP regular initialization. */
|
||||
#define ACMP_INIT_DEFAULT \
|
||||
{ false, /* fullBias */ \
|
||||
false, /* halfBias */ \
|
||||
0x7, /* biasProg */ \
|
||||
false, /* No interrupt on falling edge. */ \
|
||||
false, /* No interrupt on rising edge. */ \
|
||||
acmpWarmTime512, /* 512 cycle warmup to be safe */ \
|
||||
acmpHysteresisLevel5, \
|
||||
false, /* Disabled emitting inactive value during warmup. */ \
|
||||
false, /* low power reference */ \
|
||||
0x3D, /* VDD level */ \
|
||||
true /* Enable after init. */ \
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void ACMP_CapsenseInit(ACMP_TypeDef *acmp, const ACMP_CapsenseInit_TypeDef *init);
|
||||
void ACMP_CapsenseChannelSet(ACMP_TypeDef *acmp, ACMP_Channel_TypeDef channel);
|
||||
void ACMP_ChannelSet(ACMP_TypeDef *acmp, ACMP_Channel_TypeDef negSel, ACMP_Channel_TypeDef posSel);
|
||||
void ACMP_Disable(ACMP_TypeDef *acmp);
|
||||
void ACMP_Enable(ACMP_TypeDef *acmp);
|
||||
void ACMP_GPIOSetup(ACMP_TypeDef *acmp, uint32_t location, bool enable, bool invert);
|
||||
void ACMP_Init(ACMP_TypeDef *acmp, const ACMP_Init_TypeDef *init);
|
||||
void ACMP_Reset(ACMP_TypeDef *acmp);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending ACMP interrupts.
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to ACMP peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending ACMP interrupt source to clear. Use a bitwise logic OR combination
|
||||
* of valid interrupt flags for the ACMP module (ACMP_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void ACMP_IntClear(ACMP_TypeDef *acmp, uint32_t flags)
|
||||
{
|
||||
acmp->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more ACMP interrupts.
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to ACMP peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* ACMP interrupt sources to disable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the ACMP module (ACMP_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void ACMP_IntDisable(ACMP_TypeDef *acmp, uint32_t flags)
|
||||
{
|
||||
acmp->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more ACMP interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using ACMP_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to ACMP peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* ACMP interrupt sources to enable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the ACMP module (ACMP_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void ACMP_IntEnable(ACMP_TypeDef *acmp, uint32_t flags)
|
||||
{
|
||||
acmp->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending ACMP interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to ACMP peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* ACMP interrupt sources pending. A bitwise logic OR combination of valid
|
||||
* interrupt flags for the ACMP module (ACMP_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t ACMP_IntGet(ACMP_TypeDef *acmp)
|
||||
{
|
||||
return(acmp->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get enabled and pending ACMP interrupt flags.
|
||||
* Useful for handling more interrupt sources in the same interrupt handler.
|
||||
*
|
||||
* @param[in] usart
|
||||
* Pointer to ACMP peripheral register block.
|
||||
*
|
||||
* @note
|
||||
* Interrupt flags are not cleared by the use of this function.
|
||||
*
|
||||
* @return
|
||||
* Pending and enabled ACMP interrupt sources.
|
||||
* The return value is the bitwise AND combination of
|
||||
* - the OR combination of enabled interrupt sources in ACMPx_IEN_nnn
|
||||
* register (ACMPx_IEN_nnn) and
|
||||
* - the OR combination of valid interrupt flags of the ACMP module
|
||||
* (ACMPx_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t ACMP_IntGetEnabled(ACMP_TypeDef *acmp)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
/* Store ACMPx->IEN in temporary variable in order to define explicit order
|
||||
* of volatile accesses. */
|
||||
tmp = acmp->IEN;
|
||||
|
||||
/* Bitwise AND of pending and enabled interrupts */
|
||||
return acmp->IF & tmp;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending ACMP interrupts from SW.
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to ACMP peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* ACMP interrupt sources to set to pending. Use a bitwise logic OR
|
||||
* combination of valid interrupt flags for the ACMP module (ACMP_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void ACMP_IntSet(ACMP_TypeDef *acmp, uint32_t flags)
|
||||
{
|
||||
acmp->IFS = flags;
|
||||
}
|
||||
|
||||
/** @} (end addtogroup ACMP) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_ACMP_H */
|
|
@ -0,0 +1,557 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Analog to Digital Converter (ADC) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_ADC_H
|
||||
#define __EFM32_ADC_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup ADC
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Acquisition time (in ADC clock cycles). */
|
||||
typedef enum
|
||||
{
|
||||
adcAcqTime1 = _ADC_SINGLECTRL_AT_1CYCLE, /**< 1 clock cycle. */
|
||||
adcAcqTime2 = _ADC_SINGLECTRL_AT_2CYCLES, /**< 2 clock cycles. */
|
||||
adcAcqTime4 = _ADC_SINGLECTRL_AT_4CYCLES, /**< 4 clock cycles. */
|
||||
adcAcqTime8 = _ADC_SINGLECTRL_AT_8CYCLES, /**< 8 clock cycles. */
|
||||
adcAcqTime16 = _ADC_SINGLECTRL_AT_16CYCLES, /**< 16 clock cycles. */
|
||||
adcAcqTime32 = _ADC_SINGLECTRL_AT_32CYCLES, /**< 32 clock cycles. */
|
||||
adcAcqTime64 = _ADC_SINGLECTRL_AT_64CYCLES, /**< 64 clock cycles. */
|
||||
adcAcqTime128 = _ADC_SINGLECTRL_AT_128CYCLES, /**< 128 clock cycles. */
|
||||
adcAcqTime256 = _ADC_SINGLECTRL_AT_256CYCLES /**< 256 clock cycles. */
|
||||
} ADC_AcqTime_TypeDef;
|
||||
|
||||
|
||||
/** Lowpass filter mode. */
|
||||
typedef enum
|
||||
{
|
||||
/** No filter or decoupling capacitor. */
|
||||
adcLPFilterBypass = _ADC_CTRL_LPFMODE_BYPASS,
|
||||
|
||||
/** On-chip RC filter. */
|
||||
adcLPFilterRC = _ADC_CTRL_LPFMODE_RCFILT,
|
||||
|
||||
/** On-chip decoupling capacitor. */
|
||||
adcLPFilterDeCap = _ADC_CTRL_LPFMODE_DECAP
|
||||
} ADC_LPFilter_TypeDef;
|
||||
|
||||
|
||||
/** Oversample rate select. */
|
||||
typedef enum
|
||||
{
|
||||
/** 2 samples per conversion result. */
|
||||
adcOvsRateSel2 = _ADC_CTRL_OVSRSEL_X2,
|
||||
|
||||
/** 4 samples per conversion result. */
|
||||
adcOvsRateSel4 = _ADC_CTRL_OVSRSEL_X4,
|
||||
|
||||
/** 8 samples per conversion result. */
|
||||
adcOvsRateSel8 = _ADC_CTRL_OVSRSEL_X8,
|
||||
|
||||
/** 16 samples per conversion result. */
|
||||
adcOvsRateSel16 = _ADC_CTRL_OVSRSEL_X16,
|
||||
|
||||
/** 32 samples per conversion result. */
|
||||
adcOvsRateSel32 = _ADC_CTRL_OVSRSEL_X32,
|
||||
|
||||
/** 64 samples per conversion result. */
|
||||
adcOvsRateSel64 = _ADC_CTRL_OVSRSEL_X64,
|
||||
|
||||
/** 128 samples per conversion result. */
|
||||
adcOvsRateSel128 = _ADC_CTRL_OVSRSEL_X128,
|
||||
|
||||
/** 256 samples per conversion result. */
|
||||
adcOvsRateSel256 = _ADC_CTRL_OVSRSEL_X256,
|
||||
|
||||
/** 512 samples per conversion result. */
|
||||
adcOvsRateSel512 = _ADC_CTRL_OVSRSEL_X512,
|
||||
|
||||
/** 1024 samples per conversion result. */
|
||||
adcOvsRateSel1024 = _ADC_CTRL_OVSRSEL_X1024,
|
||||
|
||||
/** 2048 samples per conversion result. */
|
||||
adcOvsRateSel2048 = _ADC_CTRL_OVSRSEL_X2048,
|
||||
|
||||
/** 4096 samples per conversion result. */
|
||||
adcOvsRateSel4096 = _ADC_CTRL_OVSRSEL_X4096
|
||||
} ADC_OvsRateSel_TypeDef;
|
||||
|
||||
|
||||
/** Peripheral Reflex System signal used to trigger single sample. */
|
||||
typedef enum
|
||||
{
|
||||
adcPRSSELCh0 = _ADC_SINGLECTRL_PRSSEL_PRSCH0, /**< PRS channel 0. */
|
||||
adcPRSSELCh1 = _ADC_SINGLECTRL_PRSSEL_PRSCH1, /**< PRS channel 1. */
|
||||
adcPRSSELCh2 = _ADC_SINGLECTRL_PRSSEL_PRSCH2, /**< PRS channel 2. */
|
||||
adcPRSSELCh3 = _ADC_SINGLECTRL_PRSSEL_PRSCH3, /**< PRS channel 3. */
|
||||
adcPRSSELCh4 = _ADC_SINGLECTRL_PRSSEL_PRSCH4, /**< PRS channel 4. */
|
||||
adcPRSSELCh5 = _ADC_SINGLECTRL_PRSSEL_PRSCH5, /**< PRS channel 5. */
|
||||
adcPRSSELCh6 = _ADC_SINGLECTRL_PRSSEL_PRSCH6, /**< PRS channel 6. */
|
||||
adcPRSSELCh7 = _ADC_SINGLECTRL_PRSSEL_PRSCH7 /**< PRS channel 7. */
|
||||
} ADC_PRSSEL_TypeDef;
|
||||
|
||||
|
||||
/** Reference to ADC sample. */
|
||||
typedef enum
|
||||
{
|
||||
/** Internal 1.25V reference. */
|
||||
adcRef1V25 = _ADC_SINGLECTRL_REF_1V25,
|
||||
|
||||
/** Internal 2.5V reference. */
|
||||
adcRef2V5 = _ADC_SINGLECTRL_REF_2V5,
|
||||
|
||||
/** Buffered VDD. */
|
||||
adcRefVDD = _ADC_SINGLECTRL_REF_VDD,
|
||||
|
||||
/** Internal differential 5V reference. */
|
||||
adcRef5VDIFF = _ADC_SINGLECTRL_REF_5VDIFF,
|
||||
|
||||
/** Single ended ext. ref. from pin 6. */
|
||||
adcRefExtSingle = _ADC_SINGLECTRL_REF_EXTSINGLE,
|
||||
|
||||
/** Differential ext. ref. from pin 6 and 7. */
|
||||
adcRef2xExtDiff = _ADC_SINGLECTRL_REF_2XEXTDIFF,
|
||||
|
||||
/** Unbuffered 2xVDD. */
|
||||
adcRef2xVDD = _ADC_SINGLECTRL_REF_2XVDD
|
||||
} ADC_Ref_TypeDef;
|
||||
|
||||
|
||||
/** Sample resolution. */
|
||||
typedef enum
|
||||
{
|
||||
adcRes12Bit = _ADC_SINGLECTRL_RES_12BIT, /**< 12 bit sampling. */
|
||||
adcRes8Bit = _ADC_SINGLECTRL_RES_8BIT, /**< 8 bit sampling. */
|
||||
adcRes6Bit = _ADC_SINGLECTRL_RES_6BIT, /**< 6 bit sampling. */
|
||||
adcResOVS = _ADC_SINGLECTRL_RES_OVS /**< Oversampling. */
|
||||
} ADC_Res_TypeDef;
|
||||
|
||||
|
||||
/** Single sample input selection. */
|
||||
typedef enum
|
||||
{
|
||||
/* Differential mode disabled */
|
||||
adcSingleInpCh0 = _ADC_SINGLECTRL_INPUTSEL_CH0, /**< Channel 0. */
|
||||
adcSingleInpCh1 = _ADC_SINGLECTRL_INPUTSEL_CH1, /**< Channel 1. */
|
||||
adcSingleInpCh2 = _ADC_SINGLECTRL_INPUTSEL_CH2, /**< Channel 2. */
|
||||
adcSingleInpCh3 = _ADC_SINGLECTRL_INPUTSEL_CH3, /**< Channel 3. */
|
||||
adcSingleInpCh4 = _ADC_SINGLECTRL_INPUTSEL_CH4, /**< Channel 4. */
|
||||
adcSingleInpCh5 = _ADC_SINGLECTRL_INPUTSEL_CH5, /**< Channel 5. */
|
||||
adcSingleInpCh6 = _ADC_SINGLECTRL_INPUTSEL_CH6, /**< Channel 6. */
|
||||
adcSingleInpCh7 = _ADC_SINGLECTRL_INPUTSEL_CH7, /**< Channel 7. */
|
||||
adcSingleInpTemp = _ADC_SINGLECTRL_INPUTSEL_TEMP, /**< Temperature reference. */
|
||||
adcSingleInpVDDDiv3 = _ADC_SINGLECTRL_INPUTSEL_VDDDIV3, /**< VDD divided by 3. */
|
||||
adcSingleInpVDD = _ADC_SINGLECTRL_INPUTSEL_VDD, /**< VDD. */
|
||||
adcSingleInpVSS = _ADC_SINGLECTRL_INPUTSEL_VSS, /**< VSS. */
|
||||
adcSingleInpVrefDiv2 = _ADC_SINGLECTRL_INPUTSEL_VREFDIV2, /**< Vref divided by 2. */
|
||||
adcSingleInpDACOut0 = _ADC_SINGLECTRL_INPUTSEL_DAC0OUT0, /**< DAC output 0. */
|
||||
adcSingleInpDACOut1 = _ADC_SINGLECTRL_INPUTSEL_DAC0OUT1, /**< DAC output 1. */
|
||||
/* TBD: Use define when available */
|
||||
adcSingleInpATEST = 15, /**< ATEST. */
|
||||
|
||||
/* Differential mode enabled */
|
||||
adcSingleInpCh0Ch1 = _ADC_SINGLECTRL_INPUTSEL_CH0CH1, /**< Positive Ch0, negative Ch1. */
|
||||
adcSingleInpCh2Ch3 = _ADC_SINGLECTRL_INPUTSEL_CH2CH3, /**< Positive Ch2, negative Ch3. */
|
||||
adcSingleInpCh4Ch5 = _ADC_SINGLECTRL_INPUTSEL_CH4CH5, /**< Positive Ch4, negative Ch5. */
|
||||
adcSingleInpCh6Ch7 = _ADC_SINGLECTRL_INPUTSEL_CH6CH7, /**< Positive Ch6, negative Ch7. */
|
||||
/* TBD: Use define when available */
|
||||
adcSingleInpDiff0 = 4 /**< Differential 0. */
|
||||
} ADC_SingleInput_TypeDef;
|
||||
|
||||
|
||||
/** Acquisition time (in ADC clock cycles). */
|
||||
typedef enum
|
||||
{
|
||||
/** Start single conversion. */
|
||||
adcStartSingle = ADC_CMD_SINGLESTART,
|
||||
|
||||
/** Start scan sequence. */
|
||||
adcStartScan = ADC_CMD_SCANSTART,
|
||||
|
||||
/**
|
||||
* Start scan sequence and single conversion, typically used when tailgating
|
||||
* single conversion after scan sequence.
|
||||
*/
|
||||
adcStartScanAndSingle = ADC_CMD_SCANSTART | ADC_CMD_SINGLESTART
|
||||
} ADC_Start_TypeDef;
|
||||
|
||||
|
||||
/** Warm-up mode. */
|
||||
typedef enum
|
||||
{
|
||||
/** ADC shutdown after each conversion. */
|
||||
adcWarmupNormal = _ADC_CTRL_WARMUPMODE_NORMAL,
|
||||
|
||||
/** Do not warm-up bandgap references. */
|
||||
adcWarmupFastBG = _ADC_CTRL_WARMUPMODE_FASTBG,
|
||||
|
||||
/** Reference selected for scan mode kept warm.*/
|
||||
adcWarmupKeepScanRefWarm = _ADC_CTRL_WARMUPMODE_KEEPSCANREFWARM,
|
||||
|
||||
/** ADC and reference selected for scan mode kept warm.*/
|
||||
adcWarmupKeepADCWarm = _ADC_CTRL_WARMUPMODE_KEEPADCWARM
|
||||
} ADC_Warmup_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** ADC init structure, common for single conversion and scan sequence. */
|
||||
typedef struct
|
||||
{
|
||||
/**
|
||||
* Oversampling rate select. In order to have any effect, oversampling must
|
||||
* be enabled for single/scan mode.
|
||||
*/
|
||||
ADC_OvsRateSel_TypeDef ovsRateSel;
|
||||
|
||||
/** Lowpass or decoupling capacitor filter to use. */
|
||||
ADC_LPFilter_TypeDef lpfMode;
|
||||
|
||||
/** Warm-up mode to use for ADC. */
|
||||
ADC_Warmup_TypeDef warmUpMode;
|
||||
|
||||
/**
|
||||
* Timebase used for ADC warm up. Select N to give (N+1)HFPERCLK cycles.
|
||||
* (Additional delay is added for bandgap references, please refer to the
|
||||
* reference manual.) Normally, N should be selected so that the timebase
|
||||
* is at least 1 us. See ADC_TimebaseCalcDefault() for a way to obtain
|
||||
* a suggested timebase of at least 1 us.
|
||||
*/
|
||||
uint8_t timebase;
|
||||
|
||||
/** Clock division factor N, ADC clock = HFPERCLK / (N + 1). */
|
||||
uint8_t prescale;
|
||||
|
||||
/** Enable/disable conversion tailgating. */
|
||||
bool tailgate;
|
||||
} ADC_Init_TypeDef;
|
||||
|
||||
/** Default config for ADC init structure. */
|
||||
#define ADC_INIT_DEFAULT \
|
||||
{ adcOvsRateSel2, /* 2x oversampling (if enabled). */ \
|
||||
adcLPFilterBypass, /* No input filter selected. */ \
|
||||
adcWarmupNormal, /* ADC shutdown after each conversion. */ \
|
||||
_ADC_CTRL_TIMEBASE_DEFAULT, /* Use HW default value. */ \
|
||||
_ADC_CTRL_PRESC_DEFAULT, /* Use HW default value. */ \
|
||||
false /* Do not use tailgate. */ \
|
||||
}
|
||||
|
||||
|
||||
/** Scan sequence init structure. */
|
||||
typedef struct
|
||||
{
|
||||
/**
|
||||
* Peripheral reflex system trigger selection. Only applicable if @p prsEnable
|
||||
* is enabled.
|
||||
*/
|
||||
ADC_PRSSEL_TypeDef prsSel;
|
||||
|
||||
/** Acquisition time (in ADC clock cycles). */
|
||||
ADC_AcqTime_TypeDef acqTime;
|
||||
|
||||
/**
|
||||
* Sample reference selection. Notice that for external references, the
|
||||
* ADC calibration register must be set explicitly.
|
||||
*/
|
||||
ADC_Ref_TypeDef reference;
|
||||
|
||||
/** Sample resolution. */
|
||||
ADC_Res_TypeDef resolution;
|
||||
|
||||
/**
|
||||
* Input scan selection. If single ended (@p diff is false), use logical
|
||||
* combination of ADC_SCANCTRL_INPUTMASK_CHx defines. If differential input
|
||||
* (@p diff is true), use logical combination of ADC_SCANCTRL_INPUTMASK_CHxCHy
|
||||
* defines. (Notice underscore prefix for defines used.)
|
||||
*/
|
||||
uint32_t input;
|
||||
|
||||
/** Select if single ended or differential input. */
|
||||
bool diff;
|
||||
|
||||
/** Peripheral reflex system trigger enable. */
|
||||
bool prsEnable;
|
||||
|
||||
/** Select if left adjustment should be done. */
|
||||
bool leftAdjust;
|
||||
|
||||
/** Select if continuous conversion until explicit stop. */
|
||||
bool rep;
|
||||
} ADC_InitScan_TypeDef;
|
||||
|
||||
/** Default config for ADC scan init structure. */
|
||||
#define ADC_INITSCAN_DEFAULT \
|
||||
{ adcPRSSELCh0, /* PRS ch0 (if enabled). */ \
|
||||
adcAcqTime1, /* 1 ADC_CLK cycle acquisition time. */ \
|
||||
adcRef1V25, /* 1.25V internal reference. */ \
|
||||
adcRes12Bit, /* 12 bit resolution. */ \
|
||||
0, /* No input selected. */ \
|
||||
false, /* Single ended input. */ \
|
||||
false, /* PRS disabled. */ \
|
||||
false, /* Right adjust. */ \
|
||||
false /* Deactivate conversion after one scan sequence. */ \
|
||||
}
|
||||
|
||||
|
||||
/** Single conversion init structure. */
|
||||
typedef struct
|
||||
{
|
||||
/**
|
||||
* Peripheral reflex system trigger selection. Only applicable if @p prsEnable
|
||||
* is enabled.
|
||||
*/
|
||||
ADC_PRSSEL_TypeDef prsSel;
|
||||
|
||||
/** Acquisition time (in ADC clock cycles). */
|
||||
ADC_AcqTime_TypeDef acqTime;
|
||||
|
||||
/**
|
||||
* Sample reference selection. Notice that for external references, the
|
||||
* ADC calibration register must be set explicitly.
|
||||
*/
|
||||
ADC_Ref_TypeDef reference;
|
||||
|
||||
/** Sample resolution. */
|
||||
ADC_Res_TypeDef resolution;
|
||||
|
||||
/**
|
||||
* Sample input selection, use single ended or differential input according
|
||||
* to setting of @p diff.
|
||||
*/
|
||||
ADC_SingleInput_TypeDef input;
|
||||
|
||||
/** Select if single ended or differential input. */
|
||||
bool diff;
|
||||
|
||||
/** Peripheral reflex system trigger enable. */
|
||||
bool prsEnable;
|
||||
|
||||
/** Select if left adjustment should be done. */
|
||||
bool leftAdjust;
|
||||
|
||||
/** Select if continuous conversion until explicit stop. */
|
||||
bool rep;
|
||||
} ADC_InitSingle_TypeDef;
|
||||
|
||||
/** Default config for ADC single conversion init structure. */
|
||||
#define ADC_INITSINGLE_DEFAULT \
|
||||
{ adcPRSSELCh0, /* PRS ch0 (if enabled). */ \
|
||||
adcAcqTime1, /* 1 ADC_CLK cycle acquisition time. */ \
|
||||
adcRef1V25, /* 1.25V internal reference. */ \
|
||||
adcRes12Bit, /* 12 bit resolution. */ \
|
||||
adcSingleInpCh0, /* CH0 input selected. */ \
|
||||
false, /* Single ended input. */ \
|
||||
false, /* PRS disabled. */ \
|
||||
false, /* Right adjust. */ \
|
||||
false /* Deactivate conversion after one scan sequence. */ \
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get single conversion result.
|
||||
*
|
||||
* @note
|
||||
* Do only use if single conversion data valid.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @return
|
||||
*
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t ADC_DataSingleGet(ADC_TypeDef *adc)
|
||||
{
|
||||
return(adc->SINGLEDATA);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get scan result.
|
||||
*
|
||||
* @note
|
||||
* Do only use if scan data valid.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t ADC_DataScanGet(ADC_TypeDef *adc)
|
||||
{
|
||||
return(adc->SCANDATA);
|
||||
}
|
||||
|
||||
|
||||
void ADC_Init(ADC_TypeDef *adc, const ADC_Init_TypeDef *init);
|
||||
void ADC_InitScan(ADC_TypeDef *adc, const ADC_InitScan_TypeDef *init);
|
||||
void ADC_InitSingle(ADC_TypeDef *adc, const ADC_InitSingle_TypeDef *init);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending ADC interrupts.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending ADC interrupt source to clear. Use a bitwise logic OR combination
|
||||
* of valid interrupt flags for the ADC module (ADC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void ADC_IntClear(ADC_TypeDef *adc, uint32_t flags)
|
||||
{
|
||||
adc->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more ADC interrupts.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* ADC interrupt sources to disable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the ADC module (ADC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void ADC_IntDisable(ADC_TypeDef *adc, uint32_t flags)
|
||||
{
|
||||
adc->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more ADC interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using ADC_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* ADC interrupt sources to enable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the ADC module (ADC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void ADC_IntEnable(ADC_TypeDef *adc, uint32_t flags)
|
||||
{
|
||||
adc->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending ADC interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* ADC interrupt sources pending. A bitwise logic OR combination of valid
|
||||
* interrupt flags for the ADC module (ADC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t ADC_IntGet(ADC_TypeDef *adc)
|
||||
{
|
||||
return(adc->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending ADC interrupts from SW.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* ADC interrupt sources to set to pending. Use a bitwise logic OR combination
|
||||
* of valid interrupt flags for the ADC module (ADC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void ADC_IntSet(ADC_TypeDef *adc, uint32_t flags)
|
||||
{
|
||||
adc->IFS = flags;
|
||||
}
|
||||
|
||||
uint8_t ADC_PrescaleCalc(uint32_t adcFreq, uint32_t hfperFreq);
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Start scan sequence and/or single conversion.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @param[in] cmd
|
||||
* Command indicating which type of sampling to start.
|
||||
******************************************************************************/
|
||||
static __INLINE void ADC_Start(ADC_TypeDef *adc, ADC_Start_TypeDef cmd)
|
||||
{
|
||||
adc->CMD = (uint32_t)cmd;
|
||||
}
|
||||
|
||||
void ADC_Reset(ADC_TypeDef *adc);
|
||||
uint8_t ADC_TimebaseCalc(uint32_t hfperFreq);
|
||||
|
||||
/** @} (end addtogroup ADC) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_ADC_H */
|
|
@ -0,0 +1,228 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Advanced encryption standard (AES) accelerator peripheral API for
|
||||
* EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_AES_H
|
||||
#define __EFM32_AES_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#if defined(AES_COUNT) && (AES_COUNT > 0)
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup AES
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
****************************** TYPEDEFS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* AES counter modification function pointer.
|
||||
* @details
|
||||
* Parameters:
|
||||
* @li ctr - Ptr to byte array (16 bytes) holding counter to be modified.
|
||||
*/
|
||||
typedef void (*AES_CtrFuncPtr_TypeDef)(uint8_t *ctr);
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void AES_CBC128(uint8_t *out,
|
||||
const uint8_t *in,
|
||||
unsigned int len,
|
||||
const uint8_t *key,
|
||||
const uint8_t *iv,
|
||||
bool encrypt);
|
||||
|
||||
void AES_CBC256(uint8_t *out,
|
||||
const uint8_t *in,
|
||||
unsigned int len,
|
||||
const uint8_t *key,
|
||||
const uint8_t *iv,
|
||||
bool encrypt);
|
||||
|
||||
void AES_CFB128(uint8_t *out,
|
||||
const uint8_t *in,
|
||||
unsigned int len,
|
||||
const uint8_t *key,
|
||||
const uint8_t *iv,
|
||||
bool encrypt);
|
||||
|
||||
void AES_CFB256(uint8_t *out,
|
||||
const uint8_t *in,
|
||||
unsigned int len,
|
||||
const uint8_t *key,
|
||||
const uint8_t *iv,
|
||||
bool encrypt);
|
||||
|
||||
void AES_CTR128(uint8_t *out,
|
||||
const uint8_t *in,
|
||||
unsigned int len,
|
||||
const uint8_t *key,
|
||||
uint8_t *ctr,
|
||||
AES_CtrFuncPtr_TypeDef ctrFunc);
|
||||
|
||||
void AES_CTR256(uint8_t *out,
|
||||
const uint8_t *in,
|
||||
unsigned int len,
|
||||
const uint8_t *key,
|
||||
uint8_t *ctr,
|
||||
AES_CtrFuncPtr_TypeDef ctrFunc);
|
||||
|
||||
void AES_CTRUpdate32Bit(uint8_t *ctr);
|
||||
|
||||
void AES_DecryptKey128(uint8_t *out, const uint8_t *in);
|
||||
|
||||
void AES_DecryptKey256(uint8_t *out, const uint8_t *in);
|
||||
|
||||
void AES_ECB128(uint8_t *out,
|
||||
const uint8_t *in,
|
||||
unsigned int len,
|
||||
const uint8_t *key,
|
||||
bool encrypt);
|
||||
|
||||
void AES_ECB256(uint8_t *out,
|
||||
const uint8_t *in,
|
||||
unsigned int len,
|
||||
const uint8_t *key,
|
||||
bool encrypt);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending AES interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending AES interrupt source to clear. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the AES module (AES_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void AES_IntClear(uint32_t flags)
|
||||
{
|
||||
AES->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more AES interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* AES interrupt sources to disable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the AES module (AES_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void AES_IntDisable(uint32_t flags)
|
||||
{
|
||||
AES->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more AES interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using AES_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] flags
|
||||
* AES interrupt sources to enable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the AES module (AES_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void AES_IntEnable(uint32_t flags)
|
||||
{
|
||||
AES->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending AES interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @return
|
||||
* AES interrupt sources pending. A bitwise logic OR combination of valid
|
||||
* interrupt flags for the AES module (AES_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t AES_IntGet(void)
|
||||
{
|
||||
return(AES->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending AES interrupts from SW.
|
||||
*
|
||||
* @param[in] flags
|
||||
* AES interrupt sources to set to pending. Use a bitwise logic OR combination
|
||||
* of valid interrupt flags for the AES module (AES_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void AES_IntSet(uint32_t flags)
|
||||
{
|
||||
AES->IFS = flags;
|
||||
}
|
||||
|
||||
|
||||
void AES_OFB128(uint8_t *out,
|
||||
const uint8_t *in,
|
||||
unsigned int len,
|
||||
const uint8_t *key,
|
||||
const uint8_t *iv);
|
||||
|
||||
void AES_OFB256(uint8_t *out,
|
||||
const uint8_t *in,
|
||||
unsigned int len,
|
||||
const uint8_t *key,
|
||||
const uint8_t *iv);
|
||||
|
||||
|
||||
/** @} (end addtogroup AES) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_AES_H */
|
||||
|
||||
#endif /* defined(AES_COUNT) && (AES_COUNT > 0) */
|
|
@ -0,0 +1,74 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief EFM32 peripheral API "assert" implementation.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*
|
||||
* @details
|
||||
* By default, EFM32 library assert usage is not included in order to reduce
|
||||
* footprint and processing overhead. Further, EFM32 assert usage is decoupled
|
||||
* from ISO C assert handling (NDEBUG usage), to allow a user to use ISO C
|
||||
* assert without including EFM32 assert statements.
|
||||
*
|
||||
* Below are available defines for controlling EFM32 assert inclusion. The defines
|
||||
* are typically defined for a project to be used by the preprocessor.
|
||||
*
|
||||
* @li If DEBUG_EFM is defined, the internal EFM32 library assert handling will
|
||||
* be used, which may be a quite rudimentary implementation.
|
||||
*
|
||||
* @li If DEBUG_EFM_USER is defined instead, the user must provide its own EFM32
|
||||
* assert handling routine (assertEFM()).
|
||||
*
|
||||
* As indicated above, if none of the above defines are used, EFM32 assert
|
||||
* statements are not compiled.
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_ASSERT_H
|
||||
#define __EFM32_ASSERT_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
#if defined(DEBUG_EFM) || defined(DEBUG_EFM_USER)
|
||||
|
||||
/* Due to footprint considerations, we only pass file name and line number, */
|
||||
/* not the assert expression (nor function name (C99)) */
|
||||
void assertEFM(const char *file, int line);
|
||||
#define EFM_ASSERT(expr) ((expr) ? ((void)0) : assertEFM(__FILE__, __LINE__))
|
||||
|
||||
#else
|
||||
|
||||
#define EFM_ASSERT(expr) ((void)0)
|
||||
|
||||
#endif /* defined(DEBUG_EFM) || defined(DEBUG_EFM_USER) */
|
||||
|
||||
/** @endcond */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_ASSERT_H */
|
|
@ -0,0 +1,103 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Bitband Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_BITBAND_H
|
||||
#define __EFM32_BITBAND_H
|
||||
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup BITBAND
|
||||
* @brief BITBAND Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Perform bit-band operation on peripheral memory location.
|
||||
*
|
||||
* @details
|
||||
* Bit-banding provides atomic read-modify-write cycle for single bit
|
||||
* modification. Please refer to the reference manual for further details
|
||||
* about bit-banding.
|
||||
*
|
||||
* @param[in,out] addr Peripheral address location to modify bit in.
|
||||
*
|
||||
* @param[in] bit Bit position to modify, 0-31.
|
||||
*
|
||||
* @param[in] val Value to set bit to, 0 or 1.
|
||||
******************************************************************************/
|
||||
static __INLINE void BITBAND_Peripheral(volatile uint32_t *addr,
|
||||
uint32_t bit,
|
||||
uint32_t val)
|
||||
{
|
||||
uint32_t tmp = BITBAND_PER_BASE + (((uint32_t)addr - PER_MEM_BASE) * 32) + (bit * 4);
|
||||
|
||||
*((volatile uint32_t *)tmp) = (uint32_t)val;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Perform bit-band operation on SRAM memory location.
|
||||
*
|
||||
* @details
|
||||
* Bit-banding provides atomic read-modify-write cycle for single bit
|
||||
* modification. Please refer to the reference manual for further details
|
||||
* about bit-banding.
|
||||
*
|
||||
* @param[in,out] addr SRAM address location to modify bit in.
|
||||
*
|
||||
* @param[in] bit Bit position to modify, 0-31.
|
||||
*
|
||||
* @param[in] val Value to set bit to, 0 or 1.
|
||||
******************************************************************************/
|
||||
static __INLINE void BITBAND_SRAM(uint32_t *addr, uint32_t bit, uint32_t val)
|
||||
{
|
||||
uint32_t tmp = BITBAND_RAM_BASE + (((uint32_t)addr - RAM_MEM_BASE) * 32) + (bit * 4);
|
||||
|
||||
*((volatile uint32_t *)tmp) = (uint32_t)val;
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup BITBAND) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_BITBAND_H */
|
|
@ -0,0 +1,160 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Chip Initialization API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_CHIP_H
|
||||
#define __EFM32_CHIP_H
|
||||
|
||||
#include "efm32.h"
|
||||
#include "efm32_system.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup CHIP
|
||||
* @brief Chip Initialization API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Chip initialization routine for revision errata workarounds
|
||||
*
|
||||
* This init function will configure the EFM32 device to a state where it is
|
||||
* as similar as later revisions as possible, to improve software compatibility
|
||||
* with newer parts. See the device specific errata for details.
|
||||
*****************************************************************************/
|
||||
static __INLINE void CHIP_Init(void)
|
||||
{
|
||||
/* Currently only run time changes for Gecko devices */
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
uint32_t rev;
|
||||
SYSTEM_ChipRevision_TypeDef chipRev;
|
||||
volatile uint32_t *reg;
|
||||
|
||||
rev = *(volatile uint32_t *)(0x0FE081FC);
|
||||
/* Engineering Sample calibration setup */
|
||||
if ((rev >> 24) == 0)
|
||||
{
|
||||
reg = (volatile uint32_t *)0x400CA00C;
|
||||
*reg &= ~(0x70UL);
|
||||
/* DREG */
|
||||
reg = (volatile uint32_t *)0x400C6020;
|
||||
*reg &= ~(0xE0000000UL);
|
||||
*reg |= ~(7UL << 25);
|
||||
}
|
||||
if ((rev >> 24) <= 3)
|
||||
{
|
||||
/* DREG */
|
||||
reg = (volatile uint32_t *)0x400C6020;
|
||||
*reg &= ~(0x00001F80UL);
|
||||
/* Update CMU reset values */
|
||||
reg = (volatile uint32_t *)0x400C8040;
|
||||
*reg = 0;
|
||||
reg = (volatile uint32_t *)0x400C8044;
|
||||
*reg = 0;
|
||||
reg = (volatile uint32_t *)0x400C8058;
|
||||
*reg = 0;
|
||||
reg = (volatile uint32_t *)0x400C8060;
|
||||
*reg = 0;
|
||||
reg = (volatile uint32_t *)0x400C8078;
|
||||
*reg = 0;
|
||||
}
|
||||
|
||||
SYSTEM_ChipRevisionGet(&chipRev);
|
||||
if (chipRev.major == 0x01)
|
||||
{
|
||||
/* Rev A errata handling for EM2/3. Must enable DMA clock in order for EM2/3 */
|
||||
/* to work. This will be fixed in later chip revisions, so only do for rev A. */
|
||||
if (chipRev.minor == 00)
|
||||
{
|
||||
reg = (volatile uint32_t *)0x400C8040;
|
||||
*reg |= 0x2;
|
||||
}
|
||||
|
||||
/* Rev A+B errata handling for I2C when using EM2/3. USART0 clock must be enabled */
|
||||
/* after waking up from EM2/EM3 in order for I2C to work. This will be fixed in */
|
||||
/* later chip revisions, so only do for rev A+B. */
|
||||
if (chipRev.minor <= 0x01)
|
||||
{
|
||||
reg = (volatile uint32_t *)0x400C8044;
|
||||
*reg |= 0x1;
|
||||
}
|
||||
}
|
||||
/* Ensure correct ADC/DAC calibration value */
|
||||
rev = *(volatile uint32_t *)0x0FE081F0;
|
||||
if (rev < 0x4C8ABA00)
|
||||
{
|
||||
uint32_t cal;
|
||||
|
||||
/* Enable ADC/DAC clocks */
|
||||
reg = (volatile uint32_t *)0x400C8044UL;
|
||||
*reg |= (1 << 14 | 1 << 11);
|
||||
|
||||
/* Retrive calibration values */
|
||||
cal = ((*(volatile uint32_t *)(0x0FE081B4UL) & 0x00007F00UL) >>
|
||||
8) << 24;
|
||||
|
||||
cal |= ((*(volatile uint32_t *)(0x0FE081B4UL) & 0x0000007FUL) >>
|
||||
0) << 16;
|
||||
|
||||
cal |= ((*(volatile uint32_t *)(0x0FE081B4UL) & 0x00007F00UL) >>
|
||||
8) << 8;
|
||||
|
||||
cal |= ((*(volatile uint32_t *)(0x0FE081B4UL) & 0x0000007FUL) >>
|
||||
0) << 0;
|
||||
|
||||
/* ADC0->CAL = 1.25 reference */
|
||||
reg = (volatile uint32_t *)0x40002034UL;
|
||||
*reg = cal;
|
||||
|
||||
/* DAC0->CAL = 1.25 reference */
|
||||
reg = (volatile uint32_t *)(0x4000402CUL);
|
||||
cal = *(volatile uint32_t *)0x0FE081C8UL;
|
||||
*reg = cal;
|
||||
|
||||
/* Turn off ADC/DAC clocks */
|
||||
reg = (volatile uint32_t *)0x400C8044UL;
|
||||
*reg &= ~(1 << 14 | 1 << 11);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
/** @} (end addtogroup SYSTEM) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_CHIP_H */
|
|
@ -0,0 +1,819 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Clock management unit (CMU) API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2011 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_CMU_H
|
||||
#define __EFM32_CMU_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
#include "efm32_bitband.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup CMU
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/* Select register ids, for internal use */
|
||||
#define CMU_NOSEL_REG 0
|
||||
#define CMU_HFCLKSEL_REG 1
|
||||
#define CMU_LFACLKSEL_REG 2
|
||||
#define CMU_LFBCLKSEL_REG 3
|
||||
#define CMU_DBGCLKSEL_REG 4
|
||||
#if defined (_EFM32_GIANT_FAMILY)
|
||||
#define CMU_USBCCLKSEL_REG 5
|
||||
#endif
|
||||
|
||||
#define CMU_SEL_REG_POS 0
|
||||
#define CMU_SEL_REG_MASK 0xf
|
||||
|
||||
/* Divisor register ids, for internal use */
|
||||
#define CMU_NODIV_REG 0
|
||||
#define CMU_HFPERCLKDIV_REG 1
|
||||
#define CMU_HFCORECLKDIV_REG 2
|
||||
#define CMU_LFAPRESC0_REG 3
|
||||
#define CMU_LFBPRESC0_REG 4
|
||||
#if defined (_EFM32_GIANT_FAMILY)
|
||||
#define CMU_HFCLKDIV_REG 5
|
||||
#endif
|
||||
#define CMU_DIV_REG_POS 4
|
||||
#define CMU_DIV_REG_MASK 0xf
|
||||
|
||||
/* Enable register ids, for internal use */
|
||||
#define CMU_NO_EN_REG 0
|
||||
#define CMU_HFPERCLKDIV_EN_REG 1
|
||||
#define CMU_HFPERCLKEN0_EN_REG 2
|
||||
#define CMU_HFCORECLKEN0_EN_REG 3
|
||||
#define CMU_LFACLKEN0_EN_REG 4
|
||||
#define CMU_LFBCLKEN0_EN_REG 5
|
||||
#define CMU_PCNT_EN_REG 6
|
||||
|
||||
#define CMU_EN_REG_POS 8
|
||||
#define CMU_EN_REG_MASK 0xf
|
||||
|
||||
/* Enable register bit position, for internal use */
|
||||
#define CMU_EN_BIT_POS 12
|
||||
#define CMU_EN_BIT_MASK 0x1f
|
||||
|
||||
/* Clock branch bitfield position, for internal use */
|
||||
#define CMU_HF_CLK_BRANCH 0
|
||||
#define CMU_HFPER_CLK_BRANCH 1
|
||||
#define CMU_HFCORE_CLK_BRANCH 2
|
||||
#define CMU_LFA_CLK_BRANCH 3
|
||||
#define CMU_RTC_CLK_BRANCH 4
|
||||
#define CMU_LETIMER_CLK_BRANCH 5
|
||||
#define CMU_LCDPRE_CLK_BRANCH 6
|
||||
#define CMU_LCD_CLK_BRANCH 7
|
||||
#define CMU_LESENSE_CLK_BRANCH 8
|
||||
#define CMU_LFB_CLK_BRANCH 9
|
||||
#define CMU_LEUART0_CLK_BRANCH 10
|
||||
#define CMU_LEUART1_CLK_BRANCH 11
|
||||
#define CMU_DBG_CLK_BRANCH 12
|
||||
#define CMU_AUX_CLK_BRANCH 13
|
||||
#define CMU_USBC_CLK_BRANCH 14
|
||||
|
||||
#define CMU_CLK_BRANCH_POS 17
|
||||
#define CMU_CLK_BRANCH_MASK 0x1f
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Clock divisors. These values are valid for prescalers. */
|
||||
#define cmuClkDiv_1 1 /**< Divide clock by 1. */
|
||||
#define cmuClkDiv_2 2 /**< Divide clock by 2. */
|
||||
#define cmuClkDiv_4 4 /**< Divide clock by 4. */
|
||||
#define cmuClkDiv_8 8 /**< Divide clock by 8. */
|
||||
#define cmuClkDiv_16 16 /**< Divide clock by 16. */
|
||||
#define cmuClkDiv_32 32 /**< Divide clock by 32. */
|
||||
#define cmuClkDiv_64 64 /**< Divide clock by 64. */
|
||||
#define cmuClkDiv_128 128 /**< Divide clock by 128. */
|
||||
#define cmuClkDiv_256 256 /**< Divide clock by 256. */
|
||||
#define cmuClkDiv_512 512 /**< Divide clock by 512. */
|
||||
#define cmuClkDiv_1024 1024 /**< Divide clock by 1024. */
|
||||
#define cmuClkDiv_2048 2048 /**< Divide clock by 2048. */
|
||||
#define cmuClkDiv_4096 4096 /**< Divide clock by 4096. */
|
||||
#define cmuClkDiv_8192 8192 /**< Divide clock by 8192. */
|
||||
#define cmuClkDiv_16384 16384 /**< Divide clock by 16384. */
|
||||
#define cmuClkDiv_32768 32768 /**< Divide clock by 32768. */
|
||||
|
||||
/** Clock divider configuration */
|
||||
typedef uint32_t CMU_ClkDiv_TypeDef;
|
||||
|
||||
/** High frequency RC bands. */
|
||||
typedef enum
|
||||
{
|
||||
/** 1MHz RC band. */
|
||||
cmuHFRCOBand_1MHz = _CMU_HFRCOCTRL_BAND_1MHZ,
|
||||
/** 7MHz RC band. */
|
||||
cmuHFRCOBand_7MHz = _CMU_HFRCOCTRL_BAND_7MHZ,
|
||||
/** 11MHz RC band. */
|
||||
cmuHFRCOBand_11MHz = _CMU_HFRCOCTRL_BAND_11MHZ,
|
||||
/** 14MHz RC band. */
|
||||
cmuHFRCOBand_14MHz = _CMU_HFRCOCTRL_BAND_14MHZ,
|
||||
/** 21MHz RC band. */
|
||||
cmuHFRCOBand_21MHz = _CMU_HFRCOCTRL_BAND_21MHZ,
|
||||
/** 28MHz RC band. */
|
||||
cmuHFRCOBand_28MHz = _CMU_HFRCOCTRL_BAND_28MHZ
|
||||
} CMU_HFRCOBand_TypeDef;
|
||||
|
||||
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/** AUX High frequency RC bands. */
|
||||
typedef enum
|
||||
{
|
||||
/** 1MHz RC band. */
|
||||
cmuAUXHFRCOBand_1MHz = _CMU_AUXHFRCOCTRL_BAND_1MHZ,
|
||||
/** 7MHz RC band. */
|
||||
cmuAUXHFRCOBand_7MHz = _CMU_AUXHFRCOCTRL_BAND_7MHZ,
|
||||
/** 11MHz RC band. */
|
||||
cmuAUXHFRCOBand_11MHz = _CMU_AUXHFRCOCTRL_BAND_11MHZ,
|
||||
/** 14MHz RC band. */
|
||||
cmuAUXHFRCOBand_14MHz = _CMU_AUXHFRCOCTRL_BAND_14MHZ,
|
||||
/** 21MHz RC band. */
|
||||
cmuAUXHFRCOBand_21MHz = _CMU_AUXHFRCOCTRL_BAND_21MHZ,
|
||||
/** 28MHz RC band. */
|
||||
cmuAUXHFRCOBand_28MHz = _CMU_AUXHFRCOCTRL_BAND_28MHZ
|
||||
} CMU_AUXHFRCOBand_TypeDef;
|
||||
#endif
|
||||
|
||||
/** Clock points in CMU. Please refer to CMU overview in reference manual. */
|
||||
typedef enum
|
||||
{
|
||||
/*******************/
|
||||
/* HF clock branch */
|
||||
/*******************/
|
||||
|
||||
/** High frequency clock */
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
cmuClock_HF = (CMU_HFCLKDIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_HFCLKSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_NO_EN_REG << CMU_EN_REG_POS) |
|
||||
(0 << CMU_EN_BIT_POS) |
|
||||
(CMU_HF_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#else
|
||||
cmuClock_HF = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_HFCLKSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_NO_EN_REG << CMU_EN_REG_POS) |
|
||||
(0 << CMU_EN_BIT_POS) |
|
||||
(CMU_HF_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Debug clock */
|
||||
cmuClock_DBG = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_DBGCLKSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_NO_EN_REG << CMU_EN_REG_POS) |
|
||||
(0 << CMU_EN_BIT_POS) |
|
||||
(CMU_DBG_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
|
||||
/** AUX clock */
|
||||
cmuClock_AUX = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_NO_EN_REG << CMU_EN_REG_POS) |
|
||||
(0 << CMU_EN_BIT_POS) |
|
||||
(CMU_AUX_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
|
||||
/**********************************/
|
||||
/* HF peripheral clock sub-branch */
|
||||
/**********************************/
|
||||
|
||||
/** High frequency peripheral clock */
|
||||
cmuClock_HFPER = (CMU_HFPERCLKDIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKDIV_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKDIV_HFPERCLKEN_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
|
||||
/** Universal sync/async receiver/transmitter 0 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_USART0_MASK)
|
||||
cmuClock_USART0 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_USART0_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Universal sync/async receiver/transmitter 1 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_USART1_MASK)
|
||||
cmuClock_USART1 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_USART1_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Universal sync/async receiver/transmitter 2 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_USART2_MASK)
|
||||
cmuClock_USART2 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_USART2_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Universal async receiver/transmitter 0 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_UART0_MASK)
|
||||
cmuClock_UART0 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_UART0_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Universal async receiver/transmitter 1 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_UART1_MASK)
|
||||
cmuClock_UART1 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_UART1_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Timer 0 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_TIMER0_MASK)
|
||||
cmuClock_TIMER0 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_TIMER0_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Timer 1 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_TIMER1_MASK)
|
||||
cmuClock_TIMER1 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_TIMER1_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Timer 2 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_TIMER2_MASK)
|
||||
cmuClock_TIMER2 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_TIMER2_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Analog comparator 0 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_ACMP0_MASK)
|
||||
cmuClock_ACMP0 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_ACMP0_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Analog comparator 1 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_ACMP1_MASK)
|
||||
cmuClock_ACMP1 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_ACMP1_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Peripheral reflex system clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_PRS_MASK)
|
||||
cmuClock_PRS = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_PRS_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Digital to analog converter 0 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_DAC0_MASK)
|
||||
cmuClock_DAC0 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_DAC0_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** General purpose input/output clock. */
|
||||
#if defined(GPIO_PRESENT)
|
||||
cmuClock_GPIO = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_GPIO_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Voltage comparator clock. */
|
||||
#if defined(VCMP_PRESENT)
|
||||
cmuClock_VCMP = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_VCMP_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Analog to digital converter 0 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_ADC0_MASK)
|
||||
cmuClock_ADC0 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_ADC0_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** I2C 0 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_I2C0_MASK)
|
||||
cmuClock_I2C0 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_I2C0_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** I2C 1 clock. */
|
||||
#if defined(_CMU_HFPERCLKEN0_I2C1_MASK)
|
||||
cmuClock_I2C1 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFPERCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFPERCLKEN0_I2C1_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFPER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/**********************/
|
||||
/* HF core sub-branch */
|
||||
/**********************/
|
||||
|
||||
/** Core clock */
|
||||
cmuClock_CORE = (CMU_HFCORECLKDIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_NO_EN_REG << CMU_EN_REG_POS) |
|
||||
(0 << CMU_EN_BIT_POS) |
|
||||
(CMU_HFCORE_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
|
||||
/** Advanced encryption standard accelerator clock. */
|
||||
#if defined(AES_PRESENT)
|
||||
cmuClock_AES = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFCORECLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFCORECLKEN0_AES_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFCORE_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Direct memory access controller clock. */
|
||||
#if defined(DMA_PRESENT)
|
||||
cmuClock_DMA = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFCORECLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFCORECLKEN0_DMA_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFCORE_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
/** Low energy clocking module clock. */
|
||||
cmuClock_CORELE = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFCORECLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFCORECLKEN0_LE_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFCORE_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
|
||||
/** External bus interface clock. */
|
||||
#if defined(EBI_PRESENT)
|
||||
cmuClock_EBI = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFCORECLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFCORECLKEN0_EBI_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFCORE_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
#if defined(USB_PRESENT)
|
||||
cmuClock_USBC = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_USBCCLKSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFCORECLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFCORECLKEN0_USBC_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_USBC_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
|
||||
cmuClock_USB = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_HFCORECLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_HFCORECLKEN0_USB_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_HFCORE_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/***************/
|
||||
/* LF A branch */
|
||||
/***************/
|
||||
|
||||
/** Low frequency A clock */
|
||||
cmuClock_LFA = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_LFACLKSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_NO_EN_REG << CMU_EN_REG_POS) |
|
||||
(0 << CMU_EN_BIT_POS) |
|
||||
(CMU_LFA_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
|
||||
/** Real time counter clock. */
|
||||
#if defined(RTC_PRESENT)
|
||||
cmuClock_RTC = (CMU_LFAPRESC0_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_LFACLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_LFACLKEN0_RTC_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_RTC_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Low energy timer 0 clock. */
|
||||
#if defined(_CMU_LFACLKEN0_LETIMER0_MASK)
|
||||
cmuClock_LETIMER0 = (CMU_LFAPRESC0_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_LFACLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_LFACLKEN0_LETIMER0_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_LETIMER_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Liquid crystal display, pre FDIV clock. */
|
||||
#if defined(_CMU_LFACLKEN0_LCD_MASK)
|
||||
cmuClock_LCDpre = (CMU_LFAPRESC0_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_NO_EN_REG << CMU_EN_REG_POS) |
|
||||
(0 << CMU_EN_BIT_POS) |
|
||||
(CMU_LCDPRE_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
|
||||
/** Liquid crystal display clock. Please notice that FDIV prescaler
|
||||
* must be set by special API. */
|
||||
cmuClock_LCD = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_LFACLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_LFACLKEN0_LCD_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_LCD_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Pulse counter 0 clock. */
|
||||
#if defined(_CMU_PCNTCTRL_PCNT0CLKEN_MASK)
|
||||
cmuClock_PCNT0 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_PCNT_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_PCNTCTRL_PCNT0CLKEN_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_LFA_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Pulse counter 1 clock. */
|
||||
#if defined(_CMU_PCNTCTRL_PCNT1CLKEN_MASK)
|
||||
cmuClock_PCNT1 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_PCNT_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_PCNTCTRL_PCNT1CLKEN_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_LFA_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Pulse counter 2 clock. */
|
||||
#if defined(_CMU_PCNTCTRL_PCNT2CLKEN_MASK)
|
||||
cmuClock_PCNT2 = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_PCNT_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_PCNTCTRL_PCNT2CLKEN_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_LFA_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
/** LESENSE clock. */
|
||||
#if defined(_CMU_LFACLKEN0_LESENSE_MASK)
|
||||
cmuClock_LESENSE = (CMU_LFAPRESC0_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_LFACLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_LFACLKEN0_LESENSE_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_LESENSE_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/***************/
|
||||
/* LF B branch */
|
||||
/***************/
|
||||
|
||||
/** Low frequency B clock */
|
||||
cmuClock_LFB = (CMU_NODIV_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_LFBCLKSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_NO_EN_REG << CMU_EN_REG_POS) |
|
||||
(0 << CMU_EN_BIT_POS) |
|
||||
(CMU_LFB_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
|
||||
/** Low energy universal asynchronous receiver/transmitter 0 clock. */
|
||||
#if defined(_CMU_LFBCLKEN0_LEUART0_MASK)
|
||||
cmuClock_LEUART0 = (CMU_LFBPRESC0_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_LFBCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_LFBCLKEN0_LEUART0_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_LEUART0_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
|
||||
/** Low energy universal asynchronous receiver/transmitter 1 clock. */
|
||||
#if defined(_CMU_LFBCLKEN0_LEUART1_MASK)
|
||||
cmuClock_LEUART1 = (CMU_LFBPRESC0_REG << CMU_DIV_REG_POS) |
|
||||
(CMU_NOSEL_REG << CMU_SEL_REG_POS) |
|
||||
(CMU_LFBCLKEN0_EN_REG << CMU_EN_REG_POS) |
|
||||
(_CMU_LFBCLKEN0_LEUART1_SHIFT << CMU_EN_BIT_POS) |
|
||||
(CMU_LEUART1_CLK_BRANCH << CMU_CLK_BRANCH_POS),
|
||||
#endif
|
||||
} CMU_Clock_TypeDef;
|
||||
|
||||
|
||||
/** Oscillator types. */
|
||||
typedef enum
|
||||
{
|
||||
cmuOsc_LFXO, /**< Low frequency crystal oscillator. */
|
||||
cmuOsc_LFRCO, /**< Low frequency RC oscillator. */
|
||||
cmuOsc_HFXO, /**< High frequency crystal oscillator. */
|
||||
cmuOsc_HFRCO, /**< High frequency RC oscillator. */
|
||||
cmuOsc_AUXHFRCO, /**< Auxiliary high frequency RC oscillator. */
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
cmuOsc_ULFRCO /**< Ultra low frequency RC oscillator. */
|
||||
#endif
|
||||
} CMU_Osc_TypeDef;
|
||||
|
||||
|
||||
/** Selectable clock sources. */
|
||||
typedef enum
|
||||
{
|
||||
cmuSelect_Error, /**< Usage error. */
|
||||
cmuSelect_Disabled, /**< Clock selector disabled. */
|
||||
cmuSelect_LFXO, /**< Low frequency crystal oscillator. */
|
||||
cmuSelect_LFRCO, /**< Low frequency RC oscillator. */
|
||||
cmuSelect_HFXO, /**< High frequency crystal oscillator. */
|
||||
cmuSelect_HFRCO, /**< High frequency RC oscillator. */
|
||||
cmuSelect_CORELEDIV2, /**< Core low energy clock divided by 2. */
|
||||
cmuSelect_AUXHFRCO, /**< Auxilliary clock source can be used for debug clock */
|
||||
cmuSelect_HFCLK, /**< Divided HFCLK on Giant for debug clock, undivided on Tiny Gecko and for USBC (not used on Gecko) */
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
cmuSelect_ULFRCO, /**< Ultra low frequency RC oscillator. */
|
||||
#endif
|
||||
} CMU_Select_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void CMU_ClockEnable(CMU_Clock_TypeDef clock, bool enable);
|
||||
uint32_t CMU_ClockFreqGet(CMU_Clock_TypeDef clock);
|
||||
CMU_ClkDiv_TypeDef CMU_ClockDivGet(CMU_Clock_TypeDef clock);
|
||||
CMU_Select_TypeDef CMU_ClockSelectGet(CMU_Clock_TypeDef clock);
|
||||
void CMU_ClockDivSet(CMU_Clock_TypeDef clock, CMU_ClkDiv_TypeDef div);
|
||||
void CMU_ClockSelectSet(CMU_Clock_TypeDef clock, CMU_Select_TypeDef ref);
|
||||
|
||||
CMU_HFRCOBand_TypeDef CMU_HFRCOBandGet(void);
|
||||
void CMU_HFRCOBandSet(CMU_HFRCOBand_TypeDef band);
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
CMU_AUXHFRCOBand_TypeDef CMU_AUXHFRCOBandGet(void);
|
||||
void CMU_AUXHFRCOBandSet(CMU_AUXHFRCOBand_TypeDef band);
|
||||
#endif
|
||||
void CMU_HFRCOStartupDelaySet(uint32_t delay);
|
||||
uint32_t CMU_HFRCOStartupDelayGet(void);
|
||||
|
||||
void CMU_OscillatorEnable(CMU_Osc_TypeDef osc, bool enable, bool wait);
|
||||
uint32_t CMU_OscillatorTuningGet(CMU_Osc_TypeDef osc);
|
||||
void CMU_OscillatorTuningSet(CMU_Osc_TypeDef osc, uint32_t val);
|
||||
|
||||
bool CMU_PCNTClockExternalGet(unsigned int inst);
|
||||
void CMU_PCNTClockExternalSet(unsigned int inst, bool external);
|
||||
|
||||
uint32_t CMU_LCDClkFDIVGet(void);
|
||||
void CMU_LCDClkFDIVSet(uint32_t div);
|
||||
|
||||
void CMU_FreezeEnable(bool enable);
|
||||
uint32_t CMU_Calibrate(uint32_t HFCycles, CMU_Osc_TypeDef reference);
|
||||
void CMU_CalibrateConfig(uint32_t downCycles, CMU_Osc_TypeDef downSel,
|
||||
CMU_Osc_TypeDef upSel);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending CMU interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* CMU interrupt sources to clear.
|
||||
******************************************************************************/
|
||||
static __INLINE void CMU_IntClear(uint32_t flags)
|
||||
{
|
||||
CMU->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more CMU interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* CMU interrupt sources to disable.
|
||||
******************************************************************************/
|
||||
static __INLINE void CMU_IntDisable(uint32_t flags)
|
||||
{
|
||||
CMU->IEN &= ~flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more CMU interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using CMU_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] flags
|
||||
* CMU interrupt sources to enable.
|
||||
******************************************************************************/
|
||||
static __INLINE void CMU_IntEnable(uint32_t flags)
|
||||
{
|
||||
CMU->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending CMU interrupts.
|
||||
*
|
||||
* @return
|
||||
* CMU interrupt sources pending.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t CMU_IntGet(void)
|
||||
{
|
||||
return CMU->IF;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get enabled and pending CMU interrupt flags.
|
||||
*
|
||||
* @details
|
||||
* Useful for handling more interrupt sources in the same interrupt handler.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @return
|
||||
* Pending and enabled CMU interrupt sources.
|
||||
* The return value is the bitwise AND combination of
|
||||
* - the OR combination of enabled interrupt sources in CMU_IEN_nnn
|
||||
* register (CMU_IEN_nnn) and
|
||||
* - the OR combination of valid interrupt flags of the CMU module
|
||||
* (CMU_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t CMU_IntGetEnabled(void)
|
||||
{
|
||||
uint32_t tmp = 0U;
|
||||
|
||||
|
||||
/* Store LESENSE->IEN in temporary variable in order to define explicit order
|
||||
* of volatile accesses. */
|
||||
tmp = CMU->IEN;
|
||||
|
||||
/* Bitwise AND of pending and enabled interrupts */
|
||||
return CMU->IF & tmp;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending CMU interrupts from SW.
|
||||
*
|
||||
* @param[in] flags
|
||||
* CMU interrupt sources to set to pending.
|
||||
*****************************************************************************/
|
||||
static __INLINE void CMU_IntSet(uint32_t flags)
|
||||
{
|
||||
CMU->IFS = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Lock the CMU in order to protect some of its registers against unintended
|
||||
* modification.
|
||||
*
|
||||
* @details
|
||||
* Please refer to the reference manual for CMU registers that will be
|
||||
* locked.
|
||||
*
|
||||
* @note
|
||||
* If locking the CMU registers, they must be unlocked prior to using any
|
||||
* CMU API functions modifying CMU registers protected by the lock.
|
||||
******************************************************************************/
|
||||
static __INLINE void CMU_Lock(void)
|
||||
{
|
||||
CMU->LOCK = CMU_LOCK_LOCKKEY_LOCK;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Unlock the CMU so that writing to locked registers again is possible.
|
||||
******************************************************************************/
|
||||
static __INLINE void CMU_Unlock(void)
|
||||
{
|
||||
CMU->LOCK = CMU_LOCK_LOCKKEY_UNLOCK;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get calibration count register
|
||||
* @note
|
||||
* If continuous calibrartion mode is active, calibration busy will allmost
|
||||
* always be on, and we just need to read the value, where the normal case
|
||||
* would be that this function call has been triggered by the CALRDY
|
||||
* interrupt flag.
|
||||
* @return
|
||||
* Calibration count, the number of UPSEL clocks (see CMU_CalibrateConfig)
|
||||
* in the period of DOWNSEL oscillator clock cycles configured by a previous
|
||||
* write operation to CMU->CALCNT
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t CMU_CalibrateCountGet(void)
|
||||
{
|
||||
/* Wait until calibration completes, UNLESS continuous calibration mode is */
|
||||
/* active */
|
||||
#if defined (_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
if (!(CMU->CALCTRL & CMU_CALCTRL_CONT))
|
||||
{
|
||||
while (CMU->STATUS & CMU_STATUS_CALBSY)
|
||||
;
|
||||
}
|
||||
#else
|
||||
while (CMU->STATUS & CMU_STATUS_CALBSY)
|
||||
;
|
||||
#endif
|
||||
return CMU->CALCNT;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Starts calibration
|
||||
* @note
|
||||
* This call is usually invoked after CMU_CalibrateConfig() and possibly
|
||||
* CMU_CalibrateCont()
|
||||
******************************************************************************/
|
||||
static __INLINE void CMU_CalibrateStart(void)
|
||||
{
|
||||
CMU->CMD = CMU_CMD_CALSTART;
|
||||
}
|
||||
|
||||
|
||||
#if defined (_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Stop the calibration counters
|
||||
******************************************************************************/
|
||||
static __INLINE void CMU_CalibrateStop(void)
|
||||
{
|
||||
CMU->CMD = CMU_CMD_CALSTOP;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configures continuous calibration mode
|
||||
* @param[in] enable
|
||||
* If true, enables continuous calibration, if false disables continuous
|
||||
* calibrartion
|
||||
******************************************************************************/
|
||||
static __INLINE void CMU_CalibrateCont(bool enable)
|
||||
{
|
||||
BITBAND_Peripheral(&(CMU->CALCTRL), _CMU_CALCTRL_CONT_SHIFT, enable);
|
||||
}
|
||||
#endif
|
||||
|
||||
/** @} (end addtogroup CMU) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_CMU_H */
|
|
@ -0,0 +1,109 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief EFM32 general purpose utilities.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2011 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_COMMON_H
|
||||
#define __EFM32_COMMON_H
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup COMMON
|
||||
* @brief EFM32 general purpose utilities.
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
#if !defined(__GNUC__)
|
||||
|
||||
/** Macro for getting minimum value. */
|
||||
#define EFM32_MIN(a, b) ((a) < (b) ? (a) : (b))
|
||||
/** Macro for getting maximum value. */
|
||||
#define EFM32_MAX(a, b) ((a) > (b) ? (a) : (b))
|
||||
|
||||
/** Macros for handling packed structs. */
|
||||
#define STRINGIZE(X) #X
|
||||
#define EFM32_PACK_START(X) _Pragma( STRINGIZE( pack( ##X## ) ) )
|
||||
#define EFM32_PACK_END() _Pragma( "pack()" )
|
||||
#define __attribute__(...)
|
||||
|
||||
/** Macros for handling aligned structs. */
|
||||
#ifdef __CC_ARM
|
||||
#define EFM32_ALIGN(X) __align(X)
|
||||
#endif
|
||||
#ifdef __ICCARM__
|
||||
#define EFM32_ALIGN(X) _Pragma( STRINGIZE( data_alignment=##X## ) )
|
||||
#endif
|
||||
|
||||
#else
|
||||
|
||||
/** Macro for getting minimum value. No sideeffects, a and b are evaluated once only. */
|
||||
#define EFM32_MIN(a, b) ({ __typeof__(a) _a = (a); __typeof__(b) _b = (b); _a < _b ? _a : _b; })
|
||||
/** Macro for getting maximum value. No sideeffects, a and b are evaluated once only. */
|
||||
#define EFM32_MAX(a, b) ({ __typeof__(a) _a = (a); __typeof__(b) _b = (b); _a > _b ? _a : _b; })
|
||||
|
||||
/** Macro for handling packed structs.
|
||||
* @n Use this macro before the struct definition.
|
||||
* @n X denotes the maximum alignment of struct members. X is not supported on
|
||||
* gcc, gcc always use 1 byte maximum alignment.
|
||||
*/
|
||||
#define EFM32_PACK_START( x )
|
||||
|
||||
/** Macro for handling packed structs.
|
||||
* @n Use this macro after the struct definition.
|
||||
* @n On gcc add __attribute__ ((packed)) after the closing } of the struct
|
||||
* definition.
|
||||
*/
|
||||
#define EFM32_PACK_END()
|
||||
|
||||
/** Macro for aligning a variable.
|
||||
* @n Use this macro before the variable definition.
|
||||
* @n X denotes the storage alignment value in bytes.
|
||||
* @n On gcc use __attribute__ ((aligned(X))) before the ; on normal variables.
|
||||
* Use __attribute__ ((aligned(X))) before the opening { on struct variables.
|
||||
*/
|
||||
#define EFM32_ALIGN(X)
|
||||
|
||||
#endif
|
||||
|
||||
/** @} (end addtogroup COMMON) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_COMMON_H */
|
|
@ -0,0 +1,312 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Digital to Analog Converter (DAC) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_DAC_H
|
||||
#define __EFM32_DAC_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup DAC
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/** Validation of DAC register block pointer reference for assert statements. */
|
||||
#define DAC_REF_VALID(ref) ((ref) == DAC0)
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Conversion mode. */
|
||||
typedef enum
|
||||
{
|
||||
dacConvModeContinuous = _DAC_CTRL_CONVMODE_CONTINUOUS, /**< Continuous mode. */
|
||||
dacConvModeSampleHold = _DAC_CTRL_CONVMODE_SAMPLEHOLD, /**< Sample/hold mode. */
|
||||
dacConvModeSampleOff = _DAC_CTRL_CONVMODE_SAMPLEOFF /**< Sample/shut off mode. */
|
||||
} DAC_ConvMode_TypeDef;
|
||||
|
||||
/** Output mode. */
|
||||
typedef enum
|
||||
{
|
||||
dacOutputDisable = _DAC_CTRL_OUTMODE_DISABLE, /**< Output to pin and ADC disabled. */
|
||||
dacOutputPin = _DAC_CTRL_OUTMODE_PIN, /**< Output to pin only. */
|
||||
dacOutputADC = _DAC_CTRL_OUTMODE_ADC, /**< Output to ADC only */
|
||||
dacOutputPinADC = _DAC_CTRL_OUTMODE_PINADC /**< Output to pin and ADC. */
|
||||
} DAC_Output_TypeDef;
|
||||
|
||||
|
||||
/** Peripheral Reflex System signal used to trigger single sample. */
|
||||
typedef enum
|
||||
{
|
||||
dacPRSSELCh0 = _DAC_CH0CTRL_PRSSEL_PRSCH0, /**< PRS channel 0. */
|
||||
dacPRSSELCh1 = _DAC_CH0CTRL_PRSSEL_PRSCH1, /**< PRS channel 1. */
|
||||
dacPRSSELCh2 = _DAC_CH0CTRL_PRSSEL_PRSCH2, /**< PRS channel 2. */
|
||||
dacPRSSELCh3 = _DAC_CH0CTRL_PRSSEL_PRSCH3, /**< PRS channel 3. */
|
||||
dacPRSSELCh4 = _DAC_CH0CTRL_PRSSEL_PRSCH4, /**< PRS channel 4. */
|
||||
dacPRSSELCh5 = _DAC_CH0CTRL_PRSSEL_PRSCH5, /**< PRS channel 5. */
|
||||
dacPRSSELCh6 = _DAC_CH0CTRL_PRSSEL_PRSCH6, /**< PRS channel 6. */
|
||||
dacPRSSELCh7 = _DAC_CH0CTRL_PRSSEL_PRSCH7 /**< PRS channel 7. */
|
||||
} DAC_PRSSEL_TypeDef;
|
||||
|
||||
|
||||
/** Reference voltage for DAC. */
|
||||
typedef enum
|
||||
{
|
||||
dacRef1V25 = _DAC_CTRL_REFSEL_1V25, /**< Internal 1.25V bandgap reference. */
|
||||
dacRef2V5 = _DAC_CTRL_REFSEL_2V5, /**< Internal 2.5V bandgap reference. */
|
||||
dacRefVDD = _DAC_CTRL_REFSEL_VDD /**< VDD reference. */
|
||||
} DAC_Ref_TypeDef;
|
||||
|
||||
|
||||
/** Refresh interval. */
|
||||
typedef enum
|
||||
{
|
||||
dacRefresh8 = _DAC_CTRL_REFRSEL_8CYCLES, /**< Refresh every 8 prescaled cycles. */
|
||||
dacRefresh16 = _DAC_CTRL_REFRSEL_16CYCLES, /**< Refresh every 16 prescaled cycles. */
|
||||
dacRefresh32 = _DAC_CTRL_REFRSEL_32CYCLES, /**< Refresh every 32 prescaled cycles. */
|
||||
dacRefresh64 = _DAC_CTRL_REFRSEL_64CYCLES /**< Refresh every 64 prescaled cycles. */
|
||||
} DAC_Refresh_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** DAC init structure, common for both channels. */
|
||||
typedef struct
|
||||
{
|
||||
/** Refresh interval. Only used if REFREN bit set for a DAC channel. */
|
||||
DAC_Refresh_TypeDef refresh;
|
||||
|
||||
/** Reference voltage to use. */
|
||||
DAC_Ref_TypeDef reference;
|
||||
|
||||
/** Output mode */
|
||||
DAC_Output_TypeDef outMode;
|
||||
|
||||
/** Conversion mode. */
|
||||
DAC_ConvMode_TypeDef convMode;
|
||||
|
||||
/**
|
||||
* Prescaler used to get DAC clock. Derived as follows:
|
||||
* DACclk=HFPERclk/(2^prescale). The DAC clock should be <= 1MHz.
|
||||
*/
|
||||
uint8_t prescale;
|
||||
|
||||
/** Enable/disable use of low pass filter on output. */
|
||||
bool lpEnable;
|
||||
|
||||
/** Enable/disable reset of prescaler on ch0 start. */
|
||||
bool ch0ResetPre;
|
||||
|
||||
/** Enable/disable output enable control by CH1 PRS signal. */
|
||||
bool outEnablePRS;
|
||||
|
||||
/** Enable/disable sine mode. */
|
||||
bool sineEnable;
|
||||
|
||||
/** Select if single ended or differential mode. */
|
||||
bool diff;
|
||||
} DAC_Init_TypeDef;
|
||||
|
||||
/** Default config for DAC init structure. */
|
||||
#define DAC_INIT_DEFAULT \
|
||||
{ dacRefresh8, /* Refresh every 8 prescaled cycles. */ \
|
||||
dacRef1V25, /* 1.25V internal reference. */ \
|
||||
dacOutputPin, /* Output to pin only. */ \
|
||||
dacConvModeContinuous, /* Continuous mode. */ \
|
||||
0, /* No prescaling. */ \
|
||||
false, /* Do not enable low pass filter. */ \
|
||||
false, /* Do not reset prescaler on ch0 start. */ \
|
||||
false, /* DAC output enable always on. */ \
|
||||
false, /* Disable sine mode. */ \
|
||||
false /* Single ended mode. */ \
|
||||
}
|
||||
|
||||
|
||||
/** DAC channel init structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Enable channel. */
|
||||
bool enable;
|
||||
|
||||
/**
|
||||
* Peripheral reflex system trigger enable. If false, channel is triggered
|
||||
* by writing to CHnDATA.
|
||||
*/
|
||||
bool prsEnable;
|
||||
|
||||
/**
|
||||
* Enable/disable automatic refresh of channel. Refresh interval must be
|
||||
* defined in common control init, please see DAC_Init().
|
||||
*/
|
||||
bool refreshEnable;
|
||||
|
||||
/**
|
||||
* Peripheral reflex system trigger selection. Only applicable if @p prsEnable
|
||||
* is enabled.
|
||||
*/
|
||||
DAC_PRSSEL_TypeDef prsSel;
|
||||
} DAC_InitChannel_TypeDef;
|
||||
|
||||
/** Default config for DAC channel init structure. */
|
||||
#define DAC_INITCHANNEL_DEFAULT \
|
||||
{ false, /* Leave channel disabled when init done. */ \
|
||||
false, /* Disable PRS triggering. */ \
|
||||
false, /* Channel not refreshed automatically. */ \
|
||||
dacPRSSELCh0 /* Select PRS ch0 (if PRS triggering enabled). */ \
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void DAC_Enable(DAC_TypeDef *dac, unsigned int ch, bool enable);
|
||||
void DAC_Init(DAC_TypeDef *dac, const DAC_Init_TypeDef *init);
|
||||
void DAC_InitChannel(DAC_TypeDef *dac,
|
||||
const DAC_InitChannel_TypeDef *init,
|
||||
unsigned int ch);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending DAC interrupts.
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to DAC peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending DAC interrupt source to clear. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the DAC module (DAC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void DAC_IntClear(DAC_TypeDef *dac, uint32_t flags)
|
||||
{
|
||||
dac->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more DAC interrupts.
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to DAC peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* DAC interrupt sources to disable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the DAC module (DAC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void DAC_IntDisable(DAC_TypeDef *dac, uint32_t flags)
|
||||
{
|
||||
dac->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more DAC interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using DAC_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to DAC peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* DAC interrupt sources to enable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the DAC module (DAC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void DAC_IntEnable(DAC_TypeDef *dac, uint32_t flags)
|
||||
{
|
||||
dac->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending DAC interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to DAC peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* DAC interrupt sources pending. A bitwise logic OR combination of valid
|
||||
* interrupt flags for the DAC module (DAC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t DAC_IntGet(DAC_TypeDef *dac)
|
||||
{
|
||||
return(dac->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending DAC interrupts from SW.
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to DAC peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* DAC interrupt sources to set to pending. Use a bitwise logic OR combination
|
||||
* of valid interrupt flags for the DAC module (DAC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void DAC_IntSet(DAC_TypeDef *dac, uint32_t flags)
|
||||
{
|
||||
dac->IFS = flags;
|
||||
}
|
||||
|
||||
uint8_t DAC_PrescaleCalc(uint32_t dacFreq, uint32_t hfperFreq);
|
||||
void DAC_Reset(DAC_TypeDef *dac);
|
||||
|
||||
/** @} (end addtogroup DAC) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_DAC_H */
|
|
@ -0,0 +1,84 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Debug (DBG) API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_DBG_H
|
||||
#define __EFM32_DBG_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup DBG
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Check if a debugger is connected (and debug session activated)
|
||||
*
|
||||
* @details
|
||||
* Used to make run-time decisions depending on whether a debug session
|
||||
* has been active since last reset, ie using a debug probe or similar. In
|
||||
* some cases special handling is required in that scenario.
|
||||
*
|
||||
* @return
|
||||
* true if a debug session is active since last reset, otherwise false.
|
||||
******************************************************************************/
|
||||
static __INLINE bool DBG_Connected(void)
|
||||
{
|
||||
if (CoreDebug->DHCSR & CoreDebug_DHCSR_C_DEBUGEN_Msk)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
}
|
||||
|
||||
|
||||
void DBG_SWOEnable(unsigned int location);
|
||||
|
||||
/** @} (end addtogroup DBG) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_DBG_H */
|
|
@ -0,0 +1,457 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Direct memory access (DMA) API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#ifndef __EFM32_DMA_H
|
||||
#define __EFM32_DMA_H
|
||||
|
||||
#include <stdio.h>
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup DMA
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/**
|
||||
* Amount source/destination address should be incremented for each data
|
||||
* transfer.
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
dmaDataInc1 = _DMA_CTRL_SRC_INC_BYTE, /**< Increment address 1 byte. */
|
||||
dmaDataInc2 = _DMA_CTRL_SRC_INC_HALFWORD, /**< Increment address 2 bytes. */
|
||||
dmaDataInc4 = _DMA_CTRL_SRC_INC_WORD, /**< Increment address 4 bytes. */
|
||||
dmaDataIncNone = _DMA_CTRL_SRC_INC_NONE /**< Do not increment address. */
|
||||
} DMA_DataInc_TypeDef;
|
||||
|
||||
|
||||
/** Data sizes (in number of bytes) to be read/written by DMA transfer. */
|
||||
typedef enum
|
||||
{
|
||||
dmaDataSize1 = _DMA_CTRL_SRC_SIZE_BYTE, /**< 1 byte DMA transfer size. */
|
||||
dmaDataSize2 = _DMA_CTRL_SRC_SIZE_HALFWORD, /**< 2 byte DMA transfer size. */
|
||||
dmaDataSize4 = _DMA_CTRL_SRC_SIZE_WORD /**< 4 byte DMA transfer size. */
|
||||
} DMA_DataSize_TypeDef;
|
||||
|
||||
|
||||
/** Type of DMA transfer. */
|
||||
typedef enum
|
||||
{
|
||||
/** Basic DMA cycle. */
|
||||
dmaCycleCtrlBasic = _DMA_CTRL_CYCLE_CTRL_BASIC,
|
||||
/** Auto-request DMA cycle. */
|
||||
dmaCycleCtrlAuto = _DMA_CTRL_CYCLE_CTRL_AUTO,
|
||||
/** Ping-pong DMA cycle. */
|
||||
dmaCycleCtrlPingPong = _DMA_CTRL_CYCLE_CTRL_PINGPONG,
|
||||
/** Memory scatter-gather DMA cycle. */
|
||||
dmaCycleCtrlMemScatterGather = _DMA_CTRL_CYCLE_CTRL_MEM_SCATTER_GATHER,
|
||||
/** Peripheral scatter-gather DMA cycle. */
|
||||
dmaCycleCtrlPerScatterGather = _DMA_CTRL_CYCLE_CTRL_PER_SCATTER_GATHER
|
||||
} DMA_CycleCtrl_TypeDef;
|
||||
|
||||
|
||||
/** Number of transfers before controller does new arbitration. */
|
||||
typedef enum
|
||||
{
|
||||
dmaArbitrate1 = _DMA_CTRL_R_POWER_1, /**< Arbitrate after 1 DMA transfer. */
|
||||
dmaArbitrate2 = _DMA_CTRL_R_POWER_2, /**< Arbitrate after 2 DMA transfers. */
|
||||
dmaArbitrate4 = _DMA_CTRL_R_POWER_4, /**< Arbitrate after 4 DMA transfers. */
|
||||
dmaArbitrate8 = _DMA_CTRL_R_POWER_8, /**< Arbitrate after 8 DMA transfers. */
|
||||
dmaArbitrate16 = _DMA_CTRL_R_POWER_16, /**< Arbitrate after 16 DMA transfers. */
|
||||
dmaArbitrate32 = _DMA_CTRL_R_POWER_32, /**< Arbitrate after 32 DMA transfers. */
|
||||
dmaArbitrate64 = _DMA_CTRL_R_POWER_64, /**< Arbitrate after 64 DMA transfers. */
|
||||
dmaArbitrate128 = _DMA_CTRL_R_POWER_128, /**< Arbitrate after 128 DMA transfers. */
|
||||
dmaArbitrate256 = _DMA_CTRL_R_POWER_256, /**< Arbitrate after 256 DMA transfers. */
|
||||
dmaArbitrate512 = _DMA_CTRL_R_POWER_512, /**< Arbitrate after 512 DMA transfers. */
|
||||
dmaArbitrate1024 = _DMA_CTRL_R_POWER_1024 /**< Arbitrate after 1024 DMA transfers. */
|
||||
} DMA_ArbiterConfig_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* DMA interrupt callback function pointer.
|
||||
* @details
|
||||
* Parameters:
|
||||
* @li channel - The DMA channel the callback function is invoked for.
|
||||
* @li primary - Indicates if callback is invoked for completion of primary
|
||||
* (true) or alternate (false) descriptor. This is mainly useful for
|
||||
* ping-pong DMA cycles, in order to know which descriptor to refresh.
|
||||
* @li user - User definable reference that may be used to pass information
|
||||
* to be used by the callback handler. If used, the referenced data must be
|
||||
* valid at the point when the interrupt handler invokes the callback.
|
||||
* If callback changes any data in the provided user structure, remember
|
||||
* that those changes are done in interrupt context, and proper protection
|
||||
* of data may be required.
|
||||
*/
|
||||
typedef void (*DMA_FuncPtr_TypeDef)(unsigned int channel, bool primary, void *user);
|
||||
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* Callback structure that can be used to define DMA complete actions.
|
||||
* @details
|
||||
* A reference to this structure is only stored in the primary descriptor
|
||||
* for a channel (if callback feature is used). If callback is required
|
||||
* for both primary and alternate descriptor completion, this must be
|
||||
* handled by one common callback, using the provided 'primary' parameter
|
||||
* with the callback function.
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
/**
|
||||
* Pointer to callback function to invoke when DMA transfer cycle done.
|
||||
* Notice that this function is invoked in interrupt context, and therefore
|
||||
* should be short and non-blocking.
|
||||
*/
|
||||
DMA_FuncPtr_TypeDef cbFunc;
|
||||
|
||||
/** User defined pointer to provide with callback function. */
|
||||
void *userPtr;
|
||||
|
||||
/**
|
||||
* For internal use only: Indicates if next callback applies to primary
|
||||
* or alternate descriptor completion. Mainly useful for ping-pong DMA
|
||||
* cycles. Set this value to 0 prior to configuring callback handling.
|
||||
*/
|
||||
uint8_t primary;
|
||||
} DMA_CB_TypeDef;
|
||||
|
||||
|
||||
/** Configuration structure for a channel. */
|
||||
typedef struct
|
||||
{
|
||||
/**
|
||||
* Select if channel priority is in the high or default priority group
|
||||
* with respect to arbitration. Within a priority group, lower numbered
|
||||
* channels have higher priority than higher numbered channels.
|
||||
*/
|
||||
bool highPri;
|
||||
|
||||
/**
|
||||
* Select if interrupt shall be enabled for channel (triggering interrupt
|
||||
* handler when dma_done signal is asserted). It should normally be
|
||||
* enabled if using the callback feature for a channel, and disabled if
|
||||
* not using the callback feature.
|
||||
*/
|
||||
bool enableInt;
|
||||
|
||||
/**
|
||||
* Channel control specifying the source of DMA signals. If accessing
|
||||
* peripherals, use one of the DMAREQ_nnn defines available for the
|
||||
* peripheral. Set it to 0 for memory-to-memory DMA cycles.
|
||||
*/
|
||||
uint32_t select;
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* User definable callback handling configuration.
|
||||
* @details
|
||||
* Please refer to structure definition for details. The callback
|
||||
* is invoked when the specified DMA cycle is complete (when dma_done
|
||||
* signal asserted). The callback is invoked in interrupt context,
|
||||
* and should be efficient and non-blocking. Set to NULL to not
|
||||
* use the callback feature.
|
||||
* @note
|
||||
* The referenced structure is used by the interrupt handler, and must
|
||||
* be available until no longer used. Thus, in most cases it should
|
||||
* not be located on the stack.
|
||||
*/
|
||||
DMA_CB_TypeDef *cb;
|
||||
} DMA_CfgChannel_TypeDef;
|
||||
|
||||
|
||||
/**
|
||||
* Configuration structure for primary or alternate descriptor
|
||||
* (not used for scatter-gather DMA cycles).
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
/** Destination increment size for each DMA transfer */
|
||||
DMA_DataInc_TypeDef dstInc;
|
||||
|
||||
/** Source increment size for each DMA transfer */
|
||||
DMA_DataInc_TypeDef srcInc;
|
||||
|
||||
/** DMA transfer unit size. */
|
||||
DMA_DataSize_TypeDef size;
|
||||
|
||||
/**
|
||||
* Arbitration rate, ie number of DMA transfers done before rearbitration
|
||||
* takes place.
|
||||
*/
|
||||
DMA_ArbiterConfig_TypeDef arbRate;
|
||||
|
||||
/**
|
||||
* HPROT signal state, please refer to reference manual, DMA chapter for
|
||||
* further details. Normally set to 0 if protection is not an issue.
|
||||
* The following bits are available:
|
||||
* @li bit 0 - HPROT[1] control for source read accesses,
|
||||
* privileged/non-privileged access
|
||||
* @li bit 3 - HPROT[1] control for destination write accesses,
|
||||
* privileged/non-privileged access
|
||||
*/
|
||||
uint8_t hprot;
|
||||
} DMA_CfgDescr_TypeDef;
|
||||
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/**
|
||||
* Configuration structure for loop mode
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
/** Enable repeated loop */
|
||||
bool enable;
|
||||
/** Width of transfer, reload value for nMinus1 */
|
||||
uint16_t nMinus1;
|
||||
} DMA_CfgLoop_TypeDef;
|
||||
|
||||
|
||||
/**
|
||||
* Configuration structure for rectangular copy
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
/** DMA channel destination stride (width of destination image, distance between lines) */
|
||||
uint16_t dstStride;
|
||||
/** DMA channel source stride (width of source image, distance between lines) */
|
||||
uint16_t srcStride;
|
||||
/** 2D copy height */
|
||||
uint16_t height;
|
||||
} DMA_CfgRect_TypeDef;
|
||||
#endif
|
||||
|
||||
|
||||
/** Configuration structure for alternate scatter-gather descriptor. */
|
||||
typedef struct
|
||||
{
|
||||
/** Pointer to location to transfer data from. */
|
||||
void *src;
|
||||
|
||||
/** Pointer to location to transfer data to. */
|
||||
void *dst;
|
||||
|
||||
/** Destination increment size for each DMA transfer */
|
||||
DMA_DataInc_TypeDef dstInc;
|
||||
|
||||
/** Source increment size for each DMA transfer */
|
||||
DMA_DataInc_TypeDef srcInc;
|
||||
|
||||
/** DMA transfer unit size. */
|
||||
DMA_DataSize_TypeDef size;
|
||||
|
||||
/**
|
||||
* Arbitration rate, ie number of DMA transfers done before rearbitration
|
||||
* takes place.
|
||||
*/
|
||||
DMA_ArbiterConfig_TypeDef arbRate;
|
||||
|
||||
/** Number of DMA transfers minus 1 to do. Must be <= 1023. */
|
||||
uint16_t nMinus1;
|
||||
|
||||
/**
|
||||
* HPROT signal state, please refer to reference manual, DMA chapter for
|
||||
* further details. Normally set to 0 if protection is not an issue.
|
||||
* The following bits are available:
|
||||
* @li bit 0 - HPROT[1] control for source read accesses,
|
||||
* privileged/non-privileged access
|
||||
* @li bit 3 - HPROT[1] control for destination write accesses,
|
||||
* privileged/non-privileged access
|
||||
*/
|
||||
uint8_t hprot;
|
||||
|
||||
/** Specify if a memory or peripheral scatter-gather DMA cycle. Notice
|
||||
* that this parameter should be the same for all alternate
|
||||
* descriptors.
|
||||
* @li true - this is a peripheral scatter-gather cycle
|
||||
* @li false - this is a memory scatter-gather cycle
|
||||
*/
|
||||
bool peripheral;
|
||||
} DMA_CfgDescrSGAlt_TypeDef;
|
||||
|
||||
|
||||
/** DMA init structure */
|
||||
typedef struct
|
||||
{
|
||||
/**
|
||||
* HPROT signal state when accessing the primary/alternate
|
||||
* descriptors. Normally set to 0 if protection is not an issue.
|
||||
* The following bits are available:
|
||||
* @li bit 0 - HPROT[1] control for descriptor accesses (ie when
|
||||
* the DMA controller accesses the channel control block itself),
|
||||
* privileged/non-privileged access
|
||||
*/
|
||||
uint8_t hprot;
|
||||
|
||||
/**
|
||||
* Pointer to the controlblock in memory holding descriptors (channel
|
||||
* control data structures). This memory must be properly aligned
|
||||
* according to requirements.
|
||||
*
|
||||
* Alignment requirements are
|
||||
* a) 5 bits base requirement, bits [4:0]
|
||||
* b) Add the number of bits needed to represent the wanted number
|
||||
* of channels
|
||||
* c) Align structure with this number of bits set to zero
|
||||
*
|
||||
* Examples: 4 channels, 5 + 2 (channels 0 to 3) = 7 bits
|
||||
* 7 bit alignment, 64 byte address alignment
|
||||
* 8 channels, 5 + 3 (channels 0 to 7) = 8 bits
|
||||
* 8 bit alignment, 256 byte address alignment
|
||||
* 12 channels, 5 + 4 (channels 0 to 11) = 9 bits
|
||||
* 9 bit alignment, 512 byte address alignment
|
||||
*
|
||||
* Please refer to the reference manual, DMA chapter for more details.
|
||||
*
|
||||
* It is possible to provide a smaller memory block, only covering
|
||||
* those channels actually used, if not all available channels are used.
|
||||
* Ie, if only using 4 channels (0-3), both primary and alternate
|
||||
* structures, then only 16*2*4 = 128 bytes must be provided. This
|
||||
* implementation has however no check if later exceeding such a limit
|
||||
* by configuring for instance channel 4, in which case memory overwrite
|
||||
* of some other data will occur.
|
||||
*/
|
||||
DMA_DESCRIPTOR_TypeDef *controlBlock;
|
||||
} DMA_Init_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void DMA_ActivateAuto(unsigned int channel,
|
||||
bool primary,
|
||||
void *dst,
|
||||
void *src,
|
||||
unsigned int nMinus1);
|
||||
void DMA_ActivateBasic(unsigned int channel,
|
||||
bool primary,
|
||||
bool useBurst,
|
||||
void *dst,
|
||||
void *src,
|
||||
unsigned int nMinus1);
|
||||
void DMA_ActivatePingPong(unsigned int channel,
|
||||
bool useBurst,
|
||||
void *primDst,
|
||||
void *primSrc,
|
||||
unsigned int primNMinus1,
|
||||
void *altDst,
|
||||
void *altSrc,
|
||||
unsigned int altNMinus1);
|
||||
void DMA_ActivateScatterGather(unsigned int channel,
|
||||
bool useBurst,
|
||||
DMA_DESCRIPTOR_TypeDef *altDescr,
|
||||
unsigned int count);
|
||||
void DMA_CfgChannel(unsigned int channel, DMA_CfgChannel_TypeDef *cfg);
|
||||
void DMA_CfgDescr(unsigned int channel,
|
||||
bool primary,
|
||||
DMA_CfgDescr_TypeDef *cfg);
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
void DMA_CfgLoop(unsigned int channel, DMA_CfgLoop_TypeDef *cfg);
|
||||
void DMA_CfgRect(unsigned int channel, DMA_CfgRect_TypeDef *cfg);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear Loop configuration for channel
|
||||
*
|
||||
* @param[in] channel
|
||||
* Channel to reset loop configuration for
|
||||
******************************************************************************/
|
||||
static __INLINE void DMA_ResetLoop(unsigned int channel)
|
||||
{
|
||||
/* Clean loop copy operation */
|
||||
switch(channel)
|
||||
{
|
||||
case 0:
|
||||
DMA->LOOP0 = _DMA_LOOP0_RESETVALUE;
|
||||
break;
|
||||
case 1:
|
||||
DMA->LOOP1 = _DMA_LOOP1_RESETVALUE;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear Rect/2D DMA configuration for channel
|
||||
*
|
||||
* @param[in] channel
|
||||
* Channel to reset loop configuration for
|
||||
******************************************************************************/
|
||||
static __INLINE void DMA_ResetRect(unsigned int channel)
|
||||
{
|
||||
(void) channel;
|
||||
|
||||
/* Clear rect copy operation */
|
||||
DMA->RECT0 = _DMA_RECT0_RESETVALUE;
|
||||
}
|
||||
#endif
|
||||
void DMA_CfgDescrScatterGather(DMA_DESCRIPTOR_TypeDef *descr,
|
||||
unsigned int indx,
|
||||
DMA_CfgDescrSGAlt_TypeDef *cfg);
|
||||
bool DMA_ChannelEnabled(unsigned int channel);
|
||||
void DMA_Init(DMA_Init_TypeDef *init);
|
||||
void DMA_IRQHandler(void);
|
||||
void DMA_RefreshPingPong(unsigned int channel,
|
||||
bool primary,
|
||||
bool useBurst,
|
||||
void *dst,
|
||||
void *src,
|
||||
unsigned int nMinus1,
|
||||
bool last);
|
||||
void DMA_Reset(void);
|
||||
|
||||
/** @} (end addtogroup DMA) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_DMA_H */
|
|
@ -0,0 +1,789 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief External Bus Iterface (EBI) peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_EBI_H
|
||||
#define __EFM32_EBI_H
|
||||
|
||||
#include "efm32.h"
|
||||
|
||||
#if defined(EBI_COUNT) && (EBI_COUNT > 0)
|
||||
#include "efm32_assert.h"
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EBI
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @verbatim
|
||||
*
|
||||
* --------- ---------
|
||||
* | EBI | /| |\ | Ext. |
|
||||
* | | / --------- \ | Async |
|
||||
* |(EFM32)| \ --------- / | Device|
|
||||
* | | \| |/ | |
|
||||
* --------- ---------
|
||||
* Parallel interface
|
||||
*
|
||||
* @endverbatim
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
#define EBI_BANK0 (uint32_t)(1 << 1) /**< EBI address bank 0 */
|
||||
#define EBI_BANK1 (uint32_t)(1 << 2) /**< EBI address bank 1 */
|
||||
#define EBI_BANK2 (uint32_t)(1 << 3) /**< EBI address bank 2 */
|
||||
#define EBI_BANK3 (uint32_t)(1 << 4) /**< EBI address bank 3 */
|
||||
|
||||
#define EBI_CS0 (uint32_t)(1 << 1) /**< EBI chip select line 0 */
|
||||
#define EBI_CS1 (uint32_t)(1 << 2) /**< EBI chip select line 1 */
|
||||
#define EBI_CS2 (uint32_t)(1 << 3) /**< EBI chip select line 2 */
|
||||
#define EBI_CS3 (uint32_t)(1 << 4) /**< EBI chip select line 3 */
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** EBI Mode of operation */
|
||||
typedef enum
|
||||
{
|
||||
/** 8 data bits, 8 address bits */
|
||||
ebiModeD8A8 = EBI_CTRL_MODE_D8A8,
|
||||
/** 16 data bits, 16 address bits, using address latch enable */
|
||||
ebiModeD16A16ALE = EBI_CTRL_MODE_D16A16ALE,
|
||||
/** 8 data bits, 24 address bits, using address latch enable */
|
||||
ebiModeD8A24ALE = EBI_CTRL_MODE_D8A24ALE,
|
||||
/** Mode D16 */
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
ebiModeD16 = EBI_CTRL_MODE_D16,
|
||||
#endif
|
||||
} EBI_Mode_TypeDef;
|
||||
|
||||
/** EBI Polarity configuration */
|
||||
typedef enum
|
||||
{
|
||||
/** Active Low */
|
||||
ebiActiveLow = 0,
|
||||
/** Active High */
|
||||
ebiActiveHigh = 1
|
||||
} EBI_Polarity_TypeDef;
|
||||
|
||||
/** EBI Pin Line types */
|
||||
typedef enum
|
||||
{
|
||||
/** Address Ready line */
|
||||
ebiLineARDY,
|
||||
/** Address Latch Enable line */
|
||||
ebiLineALE,
|
||||
/** Write Enable line */
|
||||
ebiLineWE,
|
||||
/** Read Enable line */
|
||||
ebiLineRE,
|
||||
/** Chip Select line */
|
||||
ebiLineCS,
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** BL line */
|
||||
ebiLineBL,
|
||||
#endif
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** TFT VSYNC line */
|
||||
ebiLineTFTVSync,
|
||||
/** TFT HSYNC line */
|
||||
ebiLineTFTHSync,
|
||||
/** TFT Data enable line */
|
||||
ebiLineTFTDataEn,
|
||||
/** TFT DCLK line */
|
||||
ebiLineTFTDClk,
|
||||
/** TFT Chip select line */
|
||||
ebiLineTFTCS,
|
||||
#endif
|
||||
} EBI_Line_TypeDef;
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** Address Pin Enable, lower limit - lower range of pins to enable */
|
||||
typedef enum
|
||||
{
|
||||
/** Adress lines EBI_A[0] and upwards are enabled by APEN */
|
||||
ebiALowA0 = EBI_ROUTE_ALB_A0,
|
||||
/** Adress lines EBI_A[8] and upwards are enabled by APEN */
|
||||
ebiALowA8 = EBI_ROUTE_ALB_A8,
|
||||
/** Adress lines EBI_A[16] and upwards are enabled by APEN */
|
||||
ebiALowA16 = EBI_ROUTE_ALB_A16,
|
||||
/** Adress lines EBI_A[24] and upwards are enabled by APEN */
|
||||
ebiALowA24 = EBI_ROUTE_ALB_A24,
|
||||
} EBI_ALow_TypeDef;
|
||||
|
||||
/** Adress Pin Enable, high limit - higher limit of pins to enable */
|
||||
typedef enum
|
||||
{
|
||||
/** All EBI_A pins are disabled */
|
||||
ebiAHighA0 = EBI_ROUTE_APEN_A0,
|
||||
/** All EBI_A[4:ALow] are enabled */
|
||||
ebiAHighA5 = EBI_ROUTE_APEN_A5,
|
||||
/** All EBI_A[5:ALow] are enabled */
|
||||
ebiAHighA6 = EBI_ROUTE_APEN_A6,
|
||||
/** All EBI_A[6:ALow] are enabled */
|
||||
ebiAHighA7 = EBI_ROUTE_APEN_A7,
|
||||
/** All EBI_A[7:ALow] are enabled */
|
||||
ebiAHighA8 = EBI_ROUTE_APEN_A8,
|
||||
/** All EBI_A[8:ALow] are enabled */
|
||||
ebiAHighA9 = EBI_ROUTE_APEN_A9,
|
||||
/** All EBI_A[9:ALow] are enabled */
|
||||
ebiAHighA10 = EBI_ROUTE_APEN_A10,
|
||||
/** All EBI_A[10:ALow] are enabled */
|
||||
ebiAHighA11 = EBI_ROUTE_APEN_A11,
|
||||
/** All EBI_A[11:ALow] are enabled */
|
||||
ebiAHighA12 = EBI_ROUTE_APEN_A12,
|
||||
/** All EBI_A[12:ALow] are enabled */
|
||||
ebiAHighA13 = EBI_ROUTE_APEN_A13,
|
||||
/** All EBI_A[13:ALow] are enabled */
|
||||
ebiAHighA14 = EBI_ROUTE_APEN_A14,
|
||||
/** All EBI_A[14:ALow] are enabled */
|
||||
ebiAHighA15 = EBI_ROUTE_APEN_A15,
|
||||
/** All EBI_A[15:ALow] are enabled */
|
||||
ebiAHighA16 = EBI_ROUTE_APEN_A16,
|
||||
/** All EBI_A[16:ALow] are enabled */
|
||||
ebiAHighA17 = EBI_ROUTE_APEN_A17,
|
||||
/** All EBI_A[17:ALow] are enabled */
|
||||
ebiAHighA18 = EBI_ROUTE_APEN_A18,
|
||||
/** All EBI_A[18:ALow] are enabled */
|
||||
ebiAHighA19 = EBI_ROUTE_APEN_A19,
|
||||
/** All EBI_A[19:ALow] are enabled */
|
||||
ebiAHighA20 = EBI_ROUTE_APEN_A20,
|
||||
/** All EBI_A[20:ALow] are enabled */
|
||||
ebiAHighA21 = EBI_ROUTE_APEN_A21,
|
||||
/** All EBI_A[21:ALow] are enabled */
|
||||
ebiAHighA22 = EBI_ROUTE_APEN_A22,
|
||||
/** All EBI_A[22:ALow] are enabled */
|
||||
ebiAHighA23 = EBI_ROUTE_APEN_A23,
|
||||
/** All EBI_A[23:ALow] are enabled */
|
||||
ebiAHighA24 = EBI_ROUTE_APEN_A24,
|
||||
/** All EBI_A[24:ALow] are enabled */
|
||||
ebiAHighA25 = EBI_ROUTE_APEN_A25,
|
||||
/** All EBI_A[25:ALow] are enabled */
|
||||
ebiAHighA26 = EBI_ROUTE_APEN_A26,
|
||||
/** All EBI_A[26:ALow] are enabled */
|
||||
ebiAHighA27 = EBI_ROUTE_APEN_A27,
|
||||
/** All EBI_A[27:ALow] are enabled */
|
||||
ebiAHighA28 = EBI_ROUTE_APEN_A28,
|
||||
} EBI_AHigh_TypeDef;
|
||||
|
||||
/** EBI I/O Alternate Pin Location */
|
||||
typedef enum {
|
||||
/** EBI PIN I/O Location 0 */
|
||||
ebiLocation0 = EBI_ROUTE_LOCATION_LOC0,
|
||||
/** EBI PIN I/O Location 1 */
|
||||
ebiLocation1 = EBI_ROUTE_LOCATION_LOC1,
|
||||
/** EBI PIN I/O Location 2 */
|
||||
ebiLocation2 = EBI_ROUTE_LOCATION_LOC2,
|
||||
/** EBI PIN I/O Location 3 */
|
||||
// ebiLocation3 = EBI_ROUTE_LOCATION_LOC3,
|
||||
} EBI_Location_TypeDef;
|
||||
#endif
|
||||
|
||||
/* TFT support */
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** EBI TFT Graphics Bank Select */
|
||||
typedef enum
|
||||
{
|
||||
/** Memory BANK0 contains frame buffer */
|
||||
ebiTFTBank0 = EBI_TFTCTRL_BANKSEL_BANK0,
|
||||
/** Memory BANK1 contains frame buffer */
|
||||
ebiTFTBank1 = EBI_TFTCTRL_BANKSEL_BANK1,
|
||||
/** Memory BANK2 contains frame buffer */
|
||||
ebiTFTBank2 = EBI_TFTCTRL_BANKSEL_BANK2,
|
||||
/** Memory BANK3 contains frame buffer */
|
||||
ebiTFTBank3 = EBI_TFTCTRL_BANKSEL_BANK3
|
||||
} EBI_TFTBank_TypeDef;
|
||||
|
||||
/** Masking and Alpha blending source color*/
|
||||
typedef enum
|
||||
{
|
||||
/** Use memory as source color for masking/alpha blending */
|
||||
ebiTFTColorSrcMem = EBI_TFTCTRL_COLOR1SRC_MEM,
|
||||
/** Use PIXEL1 register as source color for masking/alpha blending */
|
||||
ebiTFTColorSrcPixel1 = EBI_TFTCTRL_COLOR1SRC_PIXEL1,
|
||||
} EBI_TFTColorSrc_TypeDef;
|
||||
|
||||
/** Bus Data Interleave Mode */
|
||||
typedef enum
|
||||
{
|
||||
/** Unlimited interleaved accesses per EBI_DCLK period. Can cause jitter */
|
||||
ebiTFTInterleaveUnlimited = EBI_TFTCTRL_INTERLEAVE_UNLIMITED,
|
||||
/** Allow 1 interleaved access per EBI_DCLK period */
|
||||
ebiTFTInterleaveOnePerDClk = EBI_TFTCTRL_INTERLEAVE_ONEPERDCLK,
|
||||
/** Only allow accesses during porch periods */
|
||||
ebiTFTInterleavePorch = EBI_TFTCTRL_INTERLEAVE_PORCH,
|
||||
} EBI_TFTInterleave_TypeDef;
|
||||
|
||||
/** Control frame base pointer copy */
|
||||
typedef enum
|
||||
{
|
||||
/** Trigger update of frame buffer pointer on vertical sync */
|
||||
ebiTFTFrameBufTriggerVSync = EBI_TFTCTRL_FBCTRIG_VSYNC,
|
||||
/** Trigger update of frame buffer pointer on horizontal sync */
|
||||
ebiTFTFrameBufTriggerHSync = EBI_TFTCTRL_FBCTRIG_HSYNC,
|
||||
} EBI_TFTFrameBufTrigger_TypeDef;
|
||||
|
||||
/** Control of mask and alpha blending mode */
|
||||
typedef enum
|
||||
{
|
||||
/** Masking and blending are disabled */
|
||||
ebiTFTMBDisabled = EBI_TFTCTRL_MASKBLEND_DISABLED,
|
||||
/** Internal masking */
|
||||
ebiTFTMBIMask = EBI_TFTCTRL_MASKBLEND_IMASK,
|
||||
/** Internal alpha blending */
|
||||
ebiTFTMBIAlpha = EBI_TFTCTRL_MASKBLEND_IALPHA,
|
||||
/** Internal masking and alpha blending are enabled */
|
||||
ebiTFTMBIMaskAlpha = EBI_TFTCTRL_MASKBLEND_IMASKIALPHA,
|
||||
/** External masking */
|
||||
ebiTFTMBEMask = EBI_TFTCTRL_MASKBLEND_EMASK,
|
||||
/** External alpha blending */
|
||||
ebiTFTMBEAlpha = EBI_TFTCTRL_MASKBLEND_EALPHA,
|
||||
/** External masking and alpha blending */
|
||||
ebiTFTMBEMaskAlpha = EBI_TFTCTRL_MASKBLEND_EMASKEALPHA,
|
||||
} EBI_TFTMaskBlend_TypeDef;
|
||||
|
||||
/** TFT Direct Drive mode */
|
||||
typedef enum
|
||||
{
|
||||
/** Disabled */
|
||||
ebiTFTDDModeDisabled = EBI_TFTCTRL_DD_DISABLED,
|
||||
/** Direct Drive from internal memory */
|
||||
ebiTFTDDModeInternal = EBI_TFTCTRL_DD_INTERNAL,
|
||||
/** Direct Drive from external memory */
|
||||
ebiTFTDDModeExternal = EBI_TFTCTRL_DD_EXTERNAL,
|
||||
} EBI_TFTDDMode_TypeDef;
|
||||
|
||||
/** TFT Data Increment Width */
|
||||
typedef enum
|
||||
{
|
||||
/** Pixel increments are 1 byte at a time */
|
||||
ebiTFTWidthByte = EBI_TFTCTRL_WIDTH_BYTE,
|
||||
/** Pixel increments are 2 bytes (half word) */
|
||||
ebiTFTWidthHalfWord = EBI_TFTCTRL_WIDTH_HALFWORD,
|
||||
} EBI_TFTWidth_TypeDef;
|
||||
|
||||
#endif
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** EBI Initialization structure */
|
||||
typedef struct
|
||||
{
|
||||
/** EBI operation mode, data and address limits */
|
||||
EBI_Mode_TypeDef mode;
|
||||
/** Address Ready pin polarity, active high or low */
|
||||
EBI_Polarity_TypeDef ardyPolarity;
|
||||
/** Address Latch Enable pin polarity, active high or low */
|
||||
EBI_Polarity_TypeDef alePolarity;
|
||||
/** Write Enable pin polarity, active high or low */
|
||||
EBI_Polarity_TypeDef wePolarity;
|
||||
/** Read Enable pin polarity, active high or low */
|
||||
EBI_Polarity_TypeDef rePolarity;
|
||||
/** Chip Select pin polarity, active high or low */
|
||||
EBI_Polarity_TypeDef csPolarity;
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** Byte Lane pin polaritym, active high or low */
|
||||
EBI_Polarity_TypeDef blPolarity;
|
||||
/** Flag to enable or disable Byte Lane support */
|
||||
bool blEnable;
|
||||
/** Flag to enable or disable idle state insertion between transfers */
|
||||
bool noIdle;
|
||||
#endif
|
||||
/** Flag to enable or disable Address Ready support */
|
||||
bool ardyEnable;
|
||||
/** Set to turn off 32 cycle timeout ability */
|
||||
bool ardyDisableTimeout;
|
||||
/** Mask of flags which selects address banks to configure EBI_BANK<0-3> */
|
||||
uint32_t banks;
|
||||
/** Mask of flags which selects chip select lines to configure EBI_CS<0-3> */
|
||||
uint32_t csLines;
|
||||
/** Number of cycles address is held after Adress Latch Enable is asserted */
|
||||
int addrSetupCycles;
|
||||
/** Number of cycles address is driven onto the ADDRDAT bus before ALE is asserted */
|
||||
int addrHoldCycles;
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** Enable or disables half cycle duration of the ALE strobe in the last address setup cycle */
|
||||
bool addrHalfALE;
|
||||
#endif
|
||||
/** Number of cycles for address setup before REn is asserted */
|
||||
int readSetupCycles;
|
||||
/** Number of cycles REn is held active */
|
||||
int readStrobeCycles;
|
||||
/** Number of cycles CSn is held active after REn is deasserted */
|
||||
int readHoldCycles;
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** Enable or disable page mode reads */
|
||||
bool readPageMode;
|
||||
/** Enables or disable prefetching from sequential addresses */
|
||||
bool readPrefetch;
|
||||
/** Enabled or disables half cycle duration of the REn signal in the last strobe cycle */
|
||||
bool readHalfRE;
|
||||
#endif
|
||||
/** Number of cycles for address setup before WEn is asserted */
|
||||
int writeSetupCycles;
|
||||
/** Number of cycles WEn is held active */
|
||||
int writeStrobeCycles;
|
||||
/** Number of cycles CSn is held active after WEn is deasserted */
|
||||
int writeHoldCycles;
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** Enable or disable the write buffer */
|
||||
bool writeBufferDisable;
|
||||
/** Enables or disables half cycle duration of the WEn signal in the last strobe cycle */
|
||||
bool writeHalfWE;
|
||||
/** Lower address pin limit to enable */
|
||||
EBI_ALow_TypeDef aLow;
|
||||
/** High address pin limit to enable */
|
||||
EBI_AHigh_TypeDef aHigh;
|
||||
/** Pin Location */
|
||||
EBI_Location_TypeDef location;
|
||||
#endif
|
||||
/** Flag, if EBI should be enabled after configuration */
|
||||
bool enable;
|
||||
} EBI_Init_TypeDef;
|
||||
|
||||
/** Default config for EBI init structures */
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
#define EBI_INIT_DEFAULT \
|
||||
{ ebiModeD8A8, /* 8 bit address, 8 bit data */ \
|
||||
ebiActiveLow, /* ARDY polarity */ \
|
||||
ebiActiveLow, /* ALE polarity */ \
|
||||
ebiActiveLow, /* WE polarity */ \
|
||||
ebiActiveLow, /* RE polarity */ \
|
||||
ebiActiveLow, /* CS polarity */ \
|
||||
ebiActiveLow, /* BL polarity */ \
|
||||
false, /* enable BL */ \
|
||||
false, /* enable NOIDLE */ \
|
||||
false, /* enable ARDY */ \
|
||||
false, /* don't disable ARDY timeout */ \
|
||||
EBI_BANK0, /* enable bank 0 */ \
|
||||
EBI_CS0, /* enable chip select 0 */ \
|
||||
0, /* addr setup cycles */ \
|
||||
1, /* addr hold cycles */ \
|
||||
false, /* do not enable half cycle ALE strobe */ \
|
||||
0, /* read setup cycles */ \
|
||||
0, /* read strobe cycles */ \
|
||||
0, /* read hold cycles */ \
|
||||
false, /* disable page mode */ \
|
||||
false, /* disable prefetch */ \
|
||||
false, /* do not enable half cycle REn strobe */ \
|
||||
0, /* write setup cycles */ \
|
||||
0, /* write strobe cycles */ \
|
||||
1, /* write hold cycles */ \
|
||||
false, /* do not disable the write buffer */ \
|
||||
false, /* do not enable halc cycle WEn strobe */ \
|
||||
ebiALowA0, /* ALB - Low bound, address lines */ \
|
||||
ebiAHighA0, /* APEN - High bound, address lines */ \
|
||||
ebiLocation0, /* Use Location 0 */ \
|
||||
true, /* enable EBI */ \
|
||||
}
|
||||
#else
|
||||
#define EBI_INIT_DEFAULT \
|
||||
{ ebiModeD8A8, /* 8 bit address, 8 bit data */ \
|
||||
ebiActiveLow, /* ARDY polarity */ \
|
||||
ebiActiveLow, /* ALE polarity */ \
|
||||
ebiActiveLow, /* WE polarity */ \
|
||||
ebiActiveLow, /* RE polarity */ \
|
||||
ebiActiveLow, /* CS polarity */ \
|
||||
false, /* enable ARDY */ \
|
||||
false, /* don't disable ARDY timeout */ \
|
||||
EBI_BANK0, /* enable bank 0 */ \
|
||||
EBI_CS0, /* enable chip select 0 */ \
|
||||
0, /* addr setup cycles */ \
|
||||
1, /* addr hold cycles */ \
|
||||
0, /* read setup cycles */ \
|
||||
0, /* read strobe cycles */ \
|
||||
0, /* read hold cycles */ \
|
||||
0, /* write setup cycles */ \
|
||||
0, /* write strobe cycles */ \
|
||||
1, /* write hold cycles */ \
|
||||
true, /* enable EBI */ \
|
||||
}
|
||||
#endif
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
|
||||
/** TFT Initialization structure */
|
||||
typedef struct
|
||||
{
|
||||
/** External memory bank for driving display */
|
||||
EBI_TFTBank_TypeDef bank;
|
||||
/** Width */
|
||||
EBI_TFTWidth_TypeDef width;
|
||||
/** Color source for masking and alpha blending */
|
||||
EBI_TFTColorSrc_TypeDef colSrc;
|
||||
/** Bus Interleave mode */
|
||||
EBI_TFTInterleave_TypeDef interleave;
|
||||
/** Trigger for updating frame buffer pointer */
|
||||
EBI_TFTFrameBufTrigger_TypeDef fbTrigger;
|
||||
/** Drive DCLK from negative clock edge of internal clock */
|
||||
bool shiftDClk;
|
||||
/** Masking and alpha blending mode */
|
||||
EBI_TFTMaskBlend_TypeDef maskBlend;
|
||||
/** TFT Direct Drive mode */
|
||||
EBI_TFTDDMode_TypeDef driveMode;
|
||||
/** TFT Polarity for Chip Select (CS) Line */
|
||||
EBI_Polarity_TypeDef csPolarity;
|
||||
/** TFT Polarity for Data Clock (DCLK) Line */
|
||||
EBI_Polarity_TypeDef dclkPolarity;
|
||||
/** TFT Polarity for Data Enable (DATAEN) Line */
|
||||
EBI_Polarity_TypeDef dataenPolarity;
|
||||
/** TFT Polarity for Horizontal Sync (HSYNC) Line */
|
||||
EBI_Polarity_TypeDef hsyncPolarity;
|
||||
/** TFT Polarity for Vertical Sync (VSYNC) Line */
|
||||
EBI_Polarity_TypeDef vsyncPolarity;
|
||||
/** Horizontal size in pixels */
|
||||
int hsize;
|
||||
/** Horizontal Front Porch Size */
|
||||
int hPorchFront;
|
||||
/** Horizontal Back Porch Size */
|
||||
int hPorchBack;
|
||||
/** Horizontal Synchronization Pulse Width */
|
||||
int hPulseWidth;
|
||||
/** Vertical size in pixels */
|
||||
int vsize;
|
||||
/** Vertical Front Porch Size */
|
||||
int vPorchFront;
|
||||
/** Vertical Back Porch Size */
|
||||
int vPorchBack;
|
||||
/** Vertical Synchronization Pulse Width */
|
||||
int vPulseWidth;
|
||||
/** TFT Frame Buffer address, offset to EBI bank base address */
|
||||
uint32_t addressOffset;
|
||||
/** TFT DCLK period in internal cycles */
|
||||
int dclkPeriod;
|
||||
/** Starting position of External Direct Drive relative to DCLK inactive edge */
|
||||
int startPosition;
|
||||
/** Number of cycles RGB data is driven before active edge of DCLK */
|
||||
int setupCycles;
|
||||
/** Number of cycles RGB data is held after active edge of DCLK */
|
||||
int holdCycles;
|
||||
} EBI_TFTInit_TypeDef;
|
||||
|
||||
#define EBI_TFTINIT_DEFAULT \
|
||||
{ ebiTFTBank0, /* Select EBI Bank 0 */ \
|
||||
ebiTFTWidthHalfWord, /* Select 2-byte increments */ \
|
||||
ebiTFTColorSrcMem, /* Use memory as source for mask/blending */ \
|
||||
ebiTFTInterleaveUnlimited, /* Unlimited interleaved accesses */ \
|
||||
ebiTFTFrameBufTriggerVSync, /* VSYNC as frame buffer update trigger */ \
|
||||
false, /* Drive DCLK from negative edge of internal clock */ \
|
||||
ebiTFTMBDisabled, /* No masking and alpha blending enabled */ \
|
||||
ebiTFTDDModeExternal, /* Drive from external memory */ \
|
||||
ebiActiveLow, /* CS Active Low polarity */ \
|
||||
ebiActiveLow, /* DCLK Active Low polarity */ \
|
||||
ebiActiveLow, /* DATAEN Active Low polarity */ \
|
||||
ebiActiveLow, /* HSYNC Active Low polarity */ \
|
||||
ebiActiveLow, /* VSYNC Active Low polarity */ \
|
||||
320, /* Horizontal size in pixels */ \
|
||||
1, /* Horizontal Front Porch */ \
|
||||
29, /* Horizontal Back Porch */ \
|
||||
2, /* Horizontal Synchronization Pulse Width */ \
|
||||
240, /* Vertical size in pixels */ \
|
||||
1, /* Vertical Front Porch */ \
|
||||
4, /* Vertical Back Porch */ \
|
||||
2, /* Vertical Synchronization Pulse Width */ \
|
||||
0x0000, /* Address offset to EBI memory base */ \
|
||||
5, /* DCLK Period */ \
|
||||
2, /* DCLK Start */ \
|
||||
1, /* DCLK Setup cycles */ \
|
||||
1, /* DCLK Hold cycles */ \
|
||||
}
|
||||
|
||||
#endif
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void EBI_Init(const EBI_Init_TypeDef *ebiInit);
|
||||
void EBI_Disable(void);
|
||||
uint32_t EBI_BankAddress(uint32_t bank);
|
||||
void EBI_BankEnable(uint32_t banks, bool enable);
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
void EBI_TFTInit(const EBI_TFTInit_TypeDef *ebiTFTInit);
|
||||
void EBI_TFTSizeSet(uint32_t horizontal, uint32_t vertical);
|
||||
void EBI_TFTHPorchSet(int front, int back, int pulseWidth);
|
||||
void EBI_TFTVPorchSet(int front, int back, int pulseWidth);
|
||||
void EBI_TFTTimingSet(int dclkPeriod, int start, int setup, int hold);
|
||||
#endif
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/* This functionality is only available on devices with independent timing support */
|
||||
void EBI_BankReadTimingSet(uint32_t bank, int setupCycles, int strobeCycles, int holdCycles);
|
||||
void EBI_BankReadTimingConfig(uint32_t bank, bool pageMode, bool prefetch, bool halfRE);
|
||||
|
||||
void EBI_BankWriteTimingSet(uint32_t bank, int setupCycles, int strobeCycles, int holdCycles);
|
||||
void EBI_BankWriteTimingConfig(uint32_t bank, bool writeBufDisable, bool halfWE);
|
||||
|
||||
void EBI_BankAddressTimingSet(uint32_t bank, int setupCycles, int holdCycles);
|
||||
void EBI_BankAddressTimingConfig(uint32_t bank, bool halfALE);
|
||||
|
||||
void EBI_BankPolaritySet(uint32_t bank, EBI_Line_TypeDef line, EBI_Polarity_TypeDef polarity);
|
||||
void EBI_BankByteLaneEnable(uint32_t bank, bool enable);
|
||||
void EBI_BankPage(uint32_t bank, bool enable);
|
||||
void EBI_AltMapEnable(bool enable);
|
||||
|
||||
/* TBD: NAND support */
|
||||
/* TBD: ECC support */
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable or disable TFT Direct Drive
|
||||
*
|
||||
* @param[in] mode
|
||||
* Drive from Internal or External memory, or Disable Direct Drive
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_TFTEnable(EBI_TFTDDMode_TypeDef mode)
|
||||
{
|
||||
EBI->TFTCTRL = (EBI->TFTCTRL & ~(_EBI_TFTCTRL_DD_MASK)) | (uint32_t) mode;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure frame buffer pointer
|
||||
*
|
||||
* @param[in] address
|
||||
* Frame pointer address, as offset by EBI base address
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_TFTFrameBaseSet(uint32_t address)
|
||||
{
|
||||
EBI->TFTFRAMEBASE = (uint32_t) address;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief Set TFT Pixel Color 0 or 1
|
||||
*
|
||||
* @param[in] pixel
|
||||
* Which pixel instance to set
|
||||
* @param[in] color
|
||||
* Color of pixel, 16-bit value
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_TFTPixelSet(int pixel, uint32_t color)
|
||||
{
|
||||
EFM_ASSERT(pixel == 0 || pixel == 1);
|
||||
|
||||
if (pixel == 0)
|
||||
{
|
||||
EBI->TFTPIXEL0 = color;
|
||||
}
|
||||
if (pixel == 1)
|
||||
{
|
||||
EBI->TFTPIXEL1 = color;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief Masking and Blending Mode Set
|
||||
*
|
||||
* @param[in] alpha
|
||||
* 8-bit value indicating blending factor
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_TFTMaskBlendMode(EBI_TFTMaskBlend_TypeDef maskBlend)
|
||||
{
|
||||
EBI->TFTCTRL = (EBI->TFTCTRL & (~_EBI_TFTCTRL_MASKBLEND_MASK))|maskBlend;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief Set TFT Alpha Blending Factor
|
||||
*
|
||||
* @param[in] alpha
|
||||
* 8-bit value indicating blending factor
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_TFTAlphaBlendSet(uint8_t alpha)
|
||||
{
|
||||
EBI->TFTALPHA = alpha;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief Set TFT mask value
|
||||
* Data accesses that matches this value are suppressed
|
||||
* @param[in] mask
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_TFTMaskSet(uint32_t mask)
|
||||
{
|
||||
EBI->TFTMASK = mask;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief Get current vertical position counter
|
||||
* @return
|
||||
* Returns the current line position for the visible part of a frame
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t EBI_TFTVCount(void)
|
||||
{
|
||||
return((EBI->TFTSTATUS & _EBI_TFTSTATUS_VCNT_MASK) >> _EBI_TFTSTATUS_VCNT_SHIFT);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief Get current horizontal position counter
|
||||
* @return
|
||||
* Returns the current horizontal pixel position within a visible line
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t EBI_TFTHCount(void)
|
||||
{
|
||||
return((EBI->TFTSTATUS & _EBI_TFTSTATUS_HCNT_MASK) >> _EBI_TFTSTATUS_HCNT_SHIFT);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief Set Frame Buffer Trigger
|
||||
* Frame buffer pointer will be updated either on each horizontal line (hsync)
|
||||
* or vertical update (vsync)(
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_TFTFBTriggerSet(EBI_TFTFrameBufTrigger_TypeDef sync)
|
||||
{
|
||||
EBI->TFTCTRL = ((EBI->TFTCTRL & ~_EBI_TFTCTRL_FBCTRIG_MASK)|sync);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief Set horizontal TFT stride value in number of bytes
|
||||
*
|
||||
* @param[in] nbytes
|
||||
* Number of bytes to add to frame buffer pointer after each horizontal line
|
||||
* update
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_TFTHStrideSet(uint32_t nbytes)
|
||||
{
|
||||
EFM_ASSERT(nbytes < 0x1000);
|
||||
|
||||
EBI->TFTSTRIDE = (EBI->TFTSTRIDE & ~(_EBI_TFTSTRIDE_HSTRIDE_MASK))|
|
||||
(nbytes<<_EBI_TFTSTRIDE_HSTRIDE_SHIFT);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending EBI interrupts.
|
||||
* @param[in] flags
|
||||
* Pending EBI interrupt source to clear. Use a logical OR combination
|
||||
* of valid interrupt flags for the EBI module (EBI_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_IntClear(uint32_t flags)
|
||||
{
|
||||
EBI->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending EBI interrupts from SW.
|
||||
*
|
||||
* @param[in] flags
|
||||
* EBI interrupt sources to set to pending. Use a logical OR combination of
|
||||
* valid interrupt flags for the EBI module (EBI_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_IntSet(uint32_t flags)
|
||||
{
|
||||
EBI->IFS = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more EBI interrupts
|
||||
*
|
||||
* @param[in] flags
|
||||
* EBI interrupt sources to disable. Use logical OR combination of valid
|
||||
* interrupt flags for the EBI module (EBI_IF_nnn)
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_IntDisable(uint32_t flags)
|
||||
{
|
||||
EBI->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more EBI interrupts
|
||||
*
|
||||
* @param[in] flags
|
||||
* EBI interrupt sources to enable. Use logical OR combination of valid
|
||||
* interrupt flags for the EBI module (EBI_IF_nnn)
|
||||
******************************************************************************/
|
||||
static __INLINE void EBI_IntEnable(uint32_t flags)
|
||||
{
|
||||
EBI->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending EBI interrupt flags
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function
|
||||
*
|
||||
* @return
|
||||
* EBI interrupt sources pending, a logical combination of valid EBI
|
||||
* interrupt flags, EBI_IF_nnn
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t EBI_IntGet(void)
|
||||
{
|
||||
return(EBI->IF);
|
||||
}
|
||||
#endif
|
||||
|
||||
void EBI_ChipSelectEnable(uint32_t banks, bool enable);
|
||||
void EBI_ReadTimingSet(int setupCycles, int strobeCycles, int holdCycles);
|
||||
void EBI_WriteTimingSet(int setupCycles, int strobeCycles, int holdCycles);
|
||||
void EBI_AddressTimingSet(int setupCycles, int holdCycles);
|
||||
void EBI_PolaritySet(EBI_Line_TypeDef line, EBI_Polarity_TypeDef polarity);
|
||||
|
||||
/** @} (end addtogroup EBI) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* defined(EBI_COUNT) && (EBI_COUNT > 0) */
|
||||
|
||||
#endif /* __EFM32_EBI_H */
|
|
@ -0,0 +1,287 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Energy management unit (EMU) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_EMU_H
|
||||
#define __EFM32_EMU_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
#include "efm32_bitband.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EMU
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** EM4 duty oscillator */
|
||||
typedef enum
|
||||
{
|
||||
/** Select ULFRCO as duty oscillator in EM4 */
|
||||
emuEM4Osc_ULFRCO = EMU_EM4CONF_OSC_ULFRCO,
|
||||
/** Select LFXO as duty oscillator in EM4 */
|
||||
emuEM4Osc_LFXO = EMU_EM4CONF_OSC_LFXO,
|
||||
/** Select LFRCO as duty oscillator in EM4 */
|
||||
emuEM4Osc_LFRCO = EMU_EM4CONF_OSC_LFRCO
|
||||
} EMU_EM4Osc_TypeDef;
|
||||
|
||||
/** Backup Power Voltage Probe types */
|
||||
typedef enum
|
||||
{
|
||||
/** Disable voltage probe */
|
||||
emuProbe_Disable = EMU_BUCTRL_PROBE_DISABLE,
|
||||
/** Connect probe to VDD_DREG */
|
||||
emuProbe_VDDDReg = EMU_BUCTRL_PROBE_VDDDREG,
|
||||
/** Connect probe to BU_IN */
|
||||
emuProbe_BUIN = EMU_BUCTRL_PROBE_BUIN,
|
||||
/** Connect probe to BU_OUT */
|
||||
emuProbe_BUOUT = EMU_BUCTRL_PROBE_BUOUT
|
||||
} EMU_Probe_TypeDef;
|
||||
|
||||
/** Backup Power Domain resistor selection */
|
||||
typedef enum
|
||||
{
|
||||
/** Main power and backup power connected with RES0 series resistance */
|
||||
emuRes_Res0 = EMU_PWRCONF_PWRRES_RES0,
|
||||
/** Main power and backup power connected with RES1 series resistance */
|
||||
emuRes_Res1 = EMU_PWRCONF_PWRRES_RES1,
|
||||
/** Main power and backup power connected with RES2 series resistance */
|
||||
emuRes_Res2 = EMU_PWRCONF_PWRRES_RES2,
|
||||
/** Main power and backup power connected with RES3 series resistance */
|
||||
emuRes_Res3 = EMU_PWRCONF_PWRRES_RES3,
|
||||
} EMU_Resistor_TypeDef;
|
||||
|
||||
/** Backup Power Domain power connection */
|
||||
typedef enum
|
||||
{
|
||||
/** No connection between main and backup power */
|
||||
emuPower_None = EMU_BUINACT_PWRCON_NONE,
|
||||
/** Main power and backup power connected through diode,
|
||||
allowing current from backup to main only */
|
||||
emuPower_BUMain = EMU_BUINACT_PWRCON_BUMAIN,
|
||||
/** Main power and backup power connected through diode,
|
||||
allowing current from main to backup only */
|
||||
emuPower_MainBU = EMU_BUINACT_PWRCON_MAINBU,
|
||||
/** Main power and backup power connected without diode */
|
||||
emuPower_NoDiode = EMU_BUINACT_PWRCON_NODIODE,
|
||||
} EMU_Power_TypeDef;
|
||||
#endif
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** Energy Mode 4 initialization structure */
|
||||
typedef struct
|
||||
{
|
||||
/** Lock configuration of regulator, BOD and oscillator */
|
||||
bool lockConfig;
|
||||
/** EM4 duty oscillator */
|
||||
EMU_EM4Osc_TypeDef osc;
|
||||
/** Wake up on EM4 BURTC interrupt */
|
||||
bool buRtcWakeup;
|
||||
/** Enable EM4 voltage regulator */
|
||||
bool vreg;
|
||||
} EMU_EM4Init_TypeDef;
|
||||
|
||||
/** Default initialization of EM4 configuration */
|
||||
#define EMU_EM4INIT_DEFAULT \
|
||||
{ false, /* Dont't lock configuration after it's been set */ \
|
||||
emuEM4Osc_ULFRCO, /* Use default ULFRCO oscillator */ \
|
||||
true, /* Wake up on EM4 BURTC interrupt */ \
|
||||
true, /* Enable VREG */ \
|
||||
}
|
||||
|
||||
/** Backup Power Domain Initialization structure */
|
||||
typedef struct
|
||||
{
|
||||
/* Backup Power Domain power configuration */
|
||||
|
||||
/** Voltage probe select, selects ADC voltage */
|
||||
EMU_Probe_TypeDef probe;
|
||||
/** Enable BOD calibration mode */
|
||||
bool bodCal;
|
||||
/** Enable BU_STAT status pin for active BU mode */
|
||||
bool statusPinEnable;
|
||||
|
||||
/* Backup Power Domain connection configuration */
|
||||
/** Power domain resistor */
|
||||
EMU_Resistor_TypeDef resistor;
|
||||
/** BU_VOUT strong enable */
|
||||
bool voutStrong;
|
||||
/** BU_VOUT medium enable */
|
||||
bool voutMed;
|
||||
/** BU_VOUT weak enable */
|
||||
bool voutWeak;
|
||||
|
||||
/* Backup Power Domain inactive configuration */
|
||||
/** Power connection, when not in Backup Mode */
|
||||
EMU_Power_TypeDef inactivePower;
|
||||
/** Threshold range for backup BOD sensing on VDD_DREG, when not in Backup Mode */
|
||||
uint32_t inactiveThresRange;
|
||||
/** Threshold for backup BOD sesning on VDD_DREG, when not in Backup Mode */
|
||||
uint32_t inactiveThreshold;
|
||||
|
||||
/* Backup Power Domain active configuration */
|
||||
/** Power connection, when in Backup Mode */
|
||||
EMU_Power_TypeDef activePower;
|
||||
/** Threshold range for backup BOD sensing when in Backup Mode */
|
||||
uint32_t activeThresRange;
|
||||
/** Threshold for backup BOD sesning on VDD_DREG, when in Backup Mode */
|
||||
uint32_t activeThreshold;
|
||||
|
||||
/** Enable backup power domain, and release reset, enable BU_VIN pin */
|
||||
bool enable;
|
||||
} EMU_BUPDInit_TypeDef;
|
||||
|
||||
/** Default */
|
||||
#define EMU_BUPDINIT_DEFAULT \
|
||||
{ emuProbe_Disable, /* Do not enable voltage probe */ \
|
||||
false, /* Disable BOD calibration mode */ \
|
||||
false, /* Disable BU_STAT pin for backup mode indication */ \
|
||||
\
|
||||
emuRes_Res0, /* RES0 series resistance between main and backup power */ \
|
||||
false, /* Don't enable strong switch */ \
|
||||
false, /* Don't enable medium switch */ \
|
||||
false, /* Don't enable weak switch */ \
|
||||
\
|
||||
emuPower_None, /* No connection between main and backup power (inactive mode) */ \
|
||||
0, /* Default threshold range for backup BOD sense (inactive mode) */ \
|
||||
0, /* Default threshold for backup BOD snese (inactive mode) */ \
|
||||
\
|
||||
emuPower_None, /* No connection between main and backup power (active mode) */ \
|
||||
0, /* Default threshold range for backup BOD sense (active mode) */ \
|
||||
0, /* Default threshold for backup BOD snese (active mode) */ \
|
||||
\
|
||||
true /* Enable BUPD enter on BOD, enable BU_VIN pin, release BU reset */ \
|
||||
}
|
||||
#endif
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enter energy mode 1 (EM1).
|
||||
******************************************************************************/
|
||||
static __INLINE void EMU_EnterEM1(void)
|
||||
{
|
||||
/* Just enter Cortex-M3 sleep mode */
|
||||
SCB->SCR &= ~SCB_SCR_SLEEPDEEP_Msk;
|
||||
__WFI();
|
||||
}
|
||||
|
||||
|
||||
void EMU_EnterEM2(bool restore);
|
||||
void EMU_EnterEM3(bool restore);
|
||||
void EMU_EnterEM4(void);
|
||||
void EMU_MemPwrDown(uint32_t blocks);
|
||||
void EMU_UpdateOscConfig(void);
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
void EMU_EM4Init(EMU_EM4Init_TypeDef *em4init);
|
||||
void EMU_BUPDInit(EMU_BUPDInit_TypeDef *budpdInit);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable BU_VIN support
|
||||
* @param[in] enable
|
||||
* If true, enables BU_VIN input pin support, if false disables it
|
||||
******************************************************************************/
|
||||
static __INLINE void EMU_BUPinEnable(bool enable)
|
||||
{
|
||||
BITBAND_Peripheral(&(EMU->ROUTE), _EMU_ROUTE_BUVINPEN_SHIFT, enable);
|
||||
}
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Lock the EMU in order to protect all its registers against unintended
|
||||
* modification.
|
||||
*
|
||||
* @note
|
||||
* If locking the EMU registers, they must be unlocked prior to using any
|
||||
* EMU API functions modifying EMU registers. An exception to this is the
|
||||
* energy mode entering API (EMU_EnterEMn()), which can be used when the
|
||||
* EMU registers are locked.
|
||||
******************************************************************************/
|
||||
static __INLINE void EMU_Lock(void)
|
||||
{
|
||||
EMU->LOCK = EMU_LOCK_LOCKKEY_LOCK;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Unlock the EMU so that writing to locked registers again is possible.
|
||||
******************************************************************************/
|
||||
static __INLINE void EMU_Unlock(void)
|
||||
{
|
||||
EMU->LOCK = EMU_LOCK_LOCKKEY_UNLOCK;
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Block entering EM2 or higher number energy modes.
|
||||
******************************************************************************/
|
||||
static __INLINE void EMU_EM2Block(void)
|
||||
{
|
||||
BITBAND_Peripheral(&(EMU->CTRL), _EMU_CTRL_EM2BLOCK_SHIFT, 1U);
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Unblock entering EM2 or higher number energy modes.
|
||||
******************************************************************************/
|
||||
static __INLINE void EMU_EM2UnBlock(void)
|
||||
{
|
||||
BITBAND_Peripheral(&(EMU->CTRL), _EMU_CTRL_EM2BLOCK_SHIFT, 0U);
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup EMU) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_EMU_H */
|
|
@ -0,0 +1,439 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief General Purpose IO (GPIO) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_GPIO_H
|
||||
#define __EFM32_GPIO_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
#include "efm32_bitband.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup GPIO
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** GPIO ports identificator. */
|
||||
typedef enum
|
||||
{
|
||||
gpioPortA = 0, /**< Port A */
|
||||
gpioPortB = 1, /**< Port B */
|
||||
gpioPortC = 2, /**< Port C */
|
||||
gpioPortD = 3, /**< Port D */
|
||||
gpioPortE = 4, /**< Port E */
|
||||
gpioPortF = 5 /**< Port F */
|
||||
} GPIO_Port_TypeDef;
|
||||
|
||||
/** GPIO drive mode. */
|
||||
typedef enum
|
||||
{
|
||||
/** Default 6mA */
|
||||
gpioDriveModeStandard = GPIO_P_CTRL_DRIVEMODE_STANDARD,
|
||||
/** 0.5 mA */
|
||||
gpioDriveModeLowest = GPIO_P_CTRL_DRIVEMODE_LOWEST,
|
||||
/** 20 mA */
|
||||
gpioDriveModeHigh = GPIO_P_CTRL_DRIVEMODE_HIGH,
|
||||
/** 2 mA */
|
||||
gpioDriveModeLow = GPIO_P_CTRL_DRIVEMODE_LOW
|
||||
} GPIO_DriveMode_TypeDef;
|
||||
|
||||
/** Pin mode. For more details on each mode, please refer to the EFM32
|
||||
* reference manual. */
|
||||
typedef enum
|
||||
{
|
||||
/** Input disabled. Pullup if DOUT is set. */
|
||||
gpioModeDisabled = _GPIO_P_MODEL_MODE0_DISABLED,
|
||||
/** Input enabled. Filter if DOUT is set */
|
||||
gpioModeInput = _GPIO_P_MODEL_MODE0_INPUT,
|
||||
/** Input enabled. DOUT determines pull direction */
|
||||
gpioModeInputPull = _GPIO_P_MODEL_MODE0_INPUTPULL,
|
||||
/** Input enabled with filter. DOUT determines pull direction */
|
||||
gpioModeInputPullFilter = _GPIO_P_MODEL_MODE0_INPUTPULLFILTER,
|
||||
/** Push-pull output */
|
||||
gpioModePushPull = _GPIO_P_MODEL_MODE0_PUSHPULL,
|
||||
/** Push-pull output with drive-strength set by DRIVEMODE */
|
||||
gpioModePushPullDrive = _GPIO_P_MODEL_MODE0_PUSHPULLDRIVE,
|
||||
/** Wired-or output */
|
||||
gpioModeWiredOr = _GPIO_P_MODEL_MODE0_WIREDOR,
|
||||
/** Wired-or output with pull-down */
|
||||
gpioModeWiredOrPullDown = _GPIO_P_MODEL_MODE0_WIREDORPULLDOWN,
|
||||
/** Open-drain output */
|
||||
gpioModeWiredAnd = _GPIO_P_MODEL_MODE0_WIREDAND,
|
||||
/** Open-drain output with filter */
|
||||
gpioModeWiredAndFilter = _GPIO_P_MODEL_MODE0_WIREDANDFILTER,
|
||||
/** Open-drain output with pullup */
|
||||
gpioModeWiredAndPullUp = _GPIO_P_MODEL_MODE0_WIREDANDPULLUP,
|
||||
/** Open-drain output with filter and pullup */
|
||||
gpioModeWiredAndPullUpFilter = _GPIO_P_MODEL_MODE0_WIREDANDPULLUPFILTER,
|
||||
/** Open-drain output with drive-strength set by DRIVEMODE */
|
||||
gpioModeWiredAndDrive = _GPIO_P_MODEL_MODE0_WIREDANDDRIVE,
|
||||
/** Open-drain output with filter and drive-strength set by DRIVEMODE */
|
||||
gpioModeWiredAndDriveFilter = _GPIO_P_MODEL_MODE0_WIREDANDDRIVEFILTER,
|
||||
/** Open-drain output with pullup and drive-strength set by DRIVEMODE */
|
||||
gpioModeWiredAndDrivePullUp = _GPIO_P_MODEL_MODE0_WIREDANDDRIVEPULLUP,
|
||||
/** Open-drain output with filter, pullup and drive-strength set by DRIVEMODE */
|
||||
gpioModeWiredAndDrivePullUpFilter = _GPIO_P_MODEL_MODE0_WIREDANDDRIVEPULLUPFILTER
|
||||
} GPIO_Mode_TypeDef;
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void GPIO_DbgLocationSet(unsigned int location);
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
static __INLINE void GPIO_EM4SetPinRetention(bool enable);
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable/disable serial wire clock pin.
|
||||
*
|
||||
* @note
|
||||
* Disabling SWDClk will disable the debug interface, which may result in
|
||||
* a lockout if done early in startup (before debugger is able to halt core).
|
||||
*
|
||||
* @param[in] enable
|
||||
* @li false - disable serial wire clock.
|
||||
* @li true - enable serial wire clock (default after reset).
|
||||
******************************************************************************/
|
||||
static __INLINE void GPIO_DbgSWDClkEnable(bool enable)
|
||||
{
|
||||
BITBAND_Peripheral(&(GPIO->ROUTE), _GPIO_ROUTE_SWCLKPEN_SHIFT, (unsigned int)enable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable/disable serial wire data pin.
|
||||
*
|
||||
* @note
|
||||
* Disabling SWDClk will disable the debug interface, which may result in
|
||||
* a lockout if done early in startup (before debugger is able to halt core).
|
||||
*
|
||||
* @param[in] enable
|
||||
* @li false - disable serial wire data pin.
|
||||
* @li true - enable serial wire data pin (default after reset).
|
||||
******************************************************************************/
|
||||
static __INLINE void GPIO_DbgSWDIOEnable(bool enable)
|
||||
{
|
||||
BITBAND_Peripheral(&(GPIO->ROUTE), _GPIO_ROUTE_SWDIOPEN_SHIFT, (unsigned int)enable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable/Disable serial wire output pin.
|
||||
*
|
||||
* @note
|
||||
* Enabling this pin is not sufficient to fully enable serial wire output
|
||||
* which is also dependent on issues outside the GPIO module. Please refer to
|
||||
* DBG_SWOEnable().
|
||||
*
|
||||
* @param[in] enable
|
||||
* @li false - disable serial wire viewer pin (default after reset).
|
||||
* @li true - enable serial wire viewer pin.
|
||||
******************************************************************************/
|
||||
static __INLINE void GPIO_DbgSWOEnable(bool enable)
|
||||
{
|
||||
BITBAND_Peripheral(&(GPIO->ROUTE), _GPIO_ROUTE_SWOPEN_SHIFT, (unsigned int)enable);
|
||||
}
|
||||
|
||||
|
||||
void GPIO_DriveModeSet(GPIO_Port_TypeDef port, GPIO_DriveMode_TypeDef mode);
|
||||
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Disable GPIO pin wake-up from EM4.
|
||||
*
|
||||
* @param[in] pinmask
|
||||
* Bitmask containing the bitwise logic OR of which GPIO pin(s) to disable.
|
||||
* Refer to Reference Manuals for pinmask to GPIO port/pin mapping.
|
||||
*****************************************************************************/
|
||||
static __INLINE void GPIO_EM4DisablePinWakeup(uint32_t pinmask)
|
||||
{
|
||||
EFM_ASSERT((pinmask & ~_GPIO_EM4WUEN_MASK) == 0);
|
||||
|
||||
GPIO->EM4WUEN &= ~pinmask;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Enable GPIO pin wake-up from EM4. When the function exits,
|
||||
* EM4 mode can be safely entered.
|
||||
*
|
||||
* @note
|
||||
* It is assumed that the GPIO pin modes are set correctly.
|
||||
* Valid modes are @ref gpioModeInput and @ref gpioModeInputPull.
|
||||
*
|
||||
* @param[in] pinmask
|
||||
* Bitmask containing the bitwise logic OR of which GPIO pin(s) to enable.
|
||||
* Refer to Reference Manuals for pinmask to GPIO port/pin mapping.
|
||||
* @param[in] polaritymask
|
||||
* Bitmask containing the bitwise logic OR of GPIO pin(s) wake-up polarity.
|
||||
* Refer to Reference Manuals for pinmask to GPIO port/pin mapping.
|
||||
*****************************************************************************/
|
||||
static __INLINE void GPIO_EM4EnablePinWakeup(uint32_t pinmask,
|
||||
uint32_t polaritymask)
|
||||
{
|
||||
EFM_ASSERT((pinmask & ~_GPIO_EM4WUEN_MASK) == 0);
|
||||
EFM_ASSERT((polaritymask & ~_GPIO_EM4WUPOL_MASK) == 0);
|
||||
|
||||
GPIO->EM4WUPOL &= ~pinmask; /* Set wakeup polarity */
|
||||
GPIO->EM4WUPOL |= pinmask & polaritymask;
|
||||
GPIO->EM4WUEN |= pinmask; /* Enable wakeup */
|
||||
|
||||
GPIO_EM4SetPinRetention(true); /* Enable pin retention */
|
||||
|
||||
GPIO->CMD = GPIO_CMD_EM4WUCLR; /* Clear wake-up logic */
|
||||
}
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Check which GPIO pin(s) that caused a wake-up from EM4.
|
||||
*
|
||||
* @return
|
||||
* Bitmask containing the bitwise logic OR of which GPIO pin(s) caused the
|
||||
* wake-up. Refer to Reference Manuals for pinmask to GPIO port/pin mapping.
|
||||
*****************************************************************************/
|
||||
static __INLINE uint32_t GPIO_EM4GetPinWakeupCause(void)
|
||||
{
|
||||
return GPIO->EM4WUCAUSE & _GPIO_EM4WUCAUSE_MASK;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Enable GPIO pin retention of output enable, output value, pull enable and
|
||||
* pull direction in EM4.
|
||||
*
|
||||
* @param[in] enable
|
||||
* @li true - enable EM4 pin retention.
|
||||
* @li false - disable EM4 pin retention.
|
||||
*****************************************************************************/
|
||||
static __INLINE void GPIO_EM4SetPinRetention(bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
GPIO->CTRL |= GPIO_CTRL_EM4RET;
|
||||
}
|
||||
else
|
||||
{
|
||||
GPIO->CTRL &= ~GPIO_CTRL_EM4RET;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable/disable input sensing.
|
||||
*
|
||||
* @details
|
||||
* Disabling input sensing if not used, can save some energy consumption.
|
||||
*
|
||||
* @param[in] val
|
||||
* Bitwise logic OR of one or more of:
|
||||
* @li GPIO_INSENSE_INTSENSE - interrupt input sensing.
|
||||
* @li GPIO_INSENSE_PRSSENSE - peripheral reflex system input sensing.
|
||||
*
|
||||
* @param[in] mask
|
||||
* Mask containing bitwise logic OR of bits similar as for @p val used to indicate
|
||||
* which input sense options to disable/enable.
|
||||
******************************************************************************/
|
||||
static __INLINE void GPIO_InputSenseSet(uint32_t val, uint32_t mask)
|
||||
{
|
||||
GPIO->INSENSE = (GPIO->INSENSE & ~mask) | (val & mask);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending GPIO interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Bitwise logic OR of GPIO interrupt sources to clear.
|
||||
******************************************************************************/
|
||||
static __INLINE void GPIO_IntClear(uint32_t flags)
|
||||
{
|
||||
GPIO->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
void GPIO_IntConfig(GPIO_Port_TypeDef port,
|
||||
unsigned int pin,
|
||||
bool risingEdge,
|
||||
bool fallingEdge,
|
||||
bool enable);
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more GPIO interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* GPIO interrupt sources to disable.
|
||||
******************************************************************************/
|
||||
static __INLINE void GPIO_IntDisable(uint32_t flags)
|
||||
{
|
||||
GPIO->IEN &= ~flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more GPIO interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using GPIO_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] flags
|
||||
* GPIO interrupt sources to enable.
|
||||
******************************************************************************/
|
||||
static __INLINE void GPIO_IntEnable(uint32_t flags)
|
||||
{
|
||||
GPIO->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending GPIO interrupts.
|
||||
*
|
||||
* @return
|
||||
* GPIO interrupt sources pending.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t GPIO_IntGet(void)
|
||||
{
|
||||
return(GPIO->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get enabled and pending GPIO interrupt flags.
|
||||
* Useful for handling more interrupt sources in the same interrupt handler.
|
||||
*
|
||||
* @note
|
||||
* Interrupt flags are not cleared by the use of this function.
|
||||
*
|
||||
* @return
|
||||
* Pending and enabled GPIO interrupt sources.
|
||||
* The return value is the bitwise AND combination of
|
||||
* - the OR combination of enabled interrupt sources in GPIO_IEN register
|
||||
* and
|
||||
* - the OR combination of valid interrupt flags in GPIO_IF register.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t GPIO_IntGetEnabled(void)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
/* Store GPIO->IEN in temporary variable in order to define explicit order
|
||||
* of volatile accesses. */
|
||||
tmp = GPIO->IEN;
|
||||
|
||||
/* Bitwise AND of pending and enabled interrupts */
|
||||
return GPIO->IF & tmp;
|
||||
}
|
||||
|
||||
|
||||
/**************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending GPIO interrupts from SW.
|
||||
*
|
||||
* @param[in] flags
|
||||
* GPIO interrupt sources to set to pending.
|
||||
*****************************************************************************/
|
||||
static __INLINE void GPIO_IntSet(uint32_t flags)
|
||||
{
|
||||
GPIO->IFS = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Locks the GPIO configuration.
|
||||
******************************************************************************/
|
||||
static __INLINE void GPIO_Lock(void)
|
||||
{
|
||||
GPIO->LOCK = GPIO_LOCK_LOCKKEY_LOCK;
|
||||
}
|
||||
|
||||
|
||||
unsigned int GPIO_PinInGet(GPIO_Port_TypeDef port, unsigned int pin);
|
||||
void GPIO_PinModeSet(GPIO_Port_TypeDef port,
|
||||
unsigned int pin,
|
||||
GPIO_Mode_TypeDef mode,
|
||||
unsigned int out);
|
||||
void GPIO_PinOutClear(GPIO_Port_TypeDef port, unsigned int pin);
|
||||
unsigned int GPIO_PinOutGet(GPIO_Port_TypeDef port, unsigned int pin);
|
||||
void GPIO_PinOutSet(GPIO_Port_TypeDef port, unsigned int pin);
|
||||
void GPIO_PinOutToggle(GPIO_Port_TypeDef port, unsigned int pin);
|
||||
|
||||
uint32_t GPIO_PortInGet(GPIO_Port_TypeDef port);
|
||||
void GPIO_PortOutClear(GPIO_Port_TypeDef port, uint32_t pins);
|
||||
uint32_t GPIO_PortOutGet(GPIO_Port_TypeDef port);
|
||||
void GPIO_PortOutSet(GPIO_Port_TypeDef port, uint32_t pins);
|
||||
void GPIO_PortOutSetVal(GPIO_Port_TypeDef port, uint32_t val, uint32_t mask);
|
||||
void GPIO_PortOutToggle(GPIO_Port_TypeDef port, uint32_t pins);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Unlocks the GPIO configuration.
|
||||
******************************************************************************/
|
||||
static __INLINE void GPIO_Unlock(void)
|
||||
{
|
||||
GPIO->LOCK = GPIO_LOCK_LOCKKEY_UNLOCK;
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup GPIO) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_GPIO_H */
|
|
@ -0,0 +1,483 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Inter-intergrated circuit (I2C) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_I2C_H
|
||||
#define __EFM32_I2C_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup I2C
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* Standard mode max frequency assuming using 4:4 ratio for Nlow:Nhigh.
|
||||
* @details
|
||||
* From I2C specification: Min Tlow = 4.7us, min Thigh = 4.0us,
|
||||
* max Trise=1.0us, max Tfall=0.3us. Since ratio is 4:4, have to use
|
||||
* worst case value of Tlow or Thigh as base.
|
||||
*
|
||||
* 1/(Tlow + Thigh + 1us + 0.3us) = 1/(4.7 + 4.7 + 1.3)us = 93458Hz
|
||||
*/
|
||||
#define I2C_FREQ_STANDARD_MAX 93500
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* Fast mode max frequency assuming using 6:3 ratio for Nlow:Nhigh.
|
||||
* @details
|
||||
* From I2C specification: Min Tlow = 1.3us, min Thigh = 0.6us,
|
||||
* max Trise=0.3us, max Tfall=0.3us. Since ratio is 6:3, have to use
|
||||
* worst case value of Tlow or 2xThigh as base.
|
||||
*
|
||||
* 1/(Tlow + Thigh + 0.3us + 0.3us) = 1/(1.3 + 0.65 + 0.6)us = 392157Hz
|
||||
*/
|
||||
#define I2C_FREQ_FAST_MAX 392500
|
||||
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* Fast mode+ max frequency assuming using 11:6 ratio for Nlow:Nhigh.
|
||||
* @details
|
||||
* From I2C specification: Min Tlow = 0.5us, min Thigh = 0.26us,
|
||||
* max Trise=0.012us, max Tfall=0.12us. Since ratio is 11:6, have to use
|
||||
* worst case value of Tlow or (11/6)xThigh as base.
|
||||
*
|
||||
* 1/(Tlow + Thigh + 0.12us + 0.12us) = 1/(0.5 + 0.273 + 0.24)us = 987167Hz
|
||||
*/
|
||||
#define I2C_FREQ_FASTPLUS_MAX 987500
|
||||
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* Indicate plain write sequence: S+ADDR(W)+DATA0+P.
|
||||
* @details
|
||||
* @li S - Start
|
||||
* @li ADDR(W) - address with W/R bit cleared
|
||||
* @li DATA0 - Data taken from buffer with index 0
|
||||
* @li P - Stop
|
||||
*/
|
||||
#define I2C_FLAG_WRITE 0x0001
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* Indicate plain read sequence: S+ADDR(R)+DATA0+P.
|
||||
* @details
|
||||
* @li S - Start
|
||||
* @li ADDR(R) - address with W/R bit set
|
||||
* @li DATA0 - Data read into buffer with index 0
|
||||
* @li P - Stop
|
||||
*/
|
||||
#define I2C_FLAG_READ 0x0002
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* Indicate combined write/read sequence: S+ADDR(W)+DATA0+Sr+ADDR(R)+DATA1+P.
|
||||
* @details
|
||||
* @li S - Start
|
||||
* @li Sr - Repeated start
|
||||
* @li ADDR(W) - address with W/R bit cleared
|
||||
* @li ADDR(R) - address with W/R bit set
|
||||
* @li DATAn - Data written from/read into buffer with index n
|
||||
* @li P - Stop
|
||||
*/
|
||||
#define I2C_FLAG_WRITE_READ 0x0004
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* Indicate write sequence using two buffers: S+ADDR(W)+DATA0+DATA1+P.
|
||||
* @details
|
||||
* @li S - Start
|
||||
* @li ADDR(W) - address with W/R bit cleared
|
||||
* @li DATAn - Data written from buffer with index n
|
||||
* @li P - Stop
|
||||
*/
|
||||
#define I2C_FLAG_WRITE_WRITE 0x0008
|
||||
|
||||
/** Use 10 bit address. */
|
||||
#define I2C_FLAG_10BIT_ADDR 0x0010
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Clock low to high ratio settings. */
|
||||
typedef enum
|
||||
{
|
||||
i2cClockHLRStandard = _I2C_CTRL_CLHR_STANDARD, /**< Ratio is 4:4 */
|
||||
i2cClockHLRAsymetric = _I2C_CTRL_CLHR_ASYMMETRIC, /**< Ratio is 6:3 */
|
||||
i2cClockHLRFast = _I2C_CTRL_CLHR_FAST /**< Ratio is 11:3 */
|
||||
} I2C_ClockHLR_TypeDef;
|
||||
|
||||
|
||||
/** Return codes for single master mode transfer function. */
|
||||
typedef enum
|
||||
{
|
||||
/* In progress code (>0) */
|
||||
i2cTransferInProgress = 1, /**< Transfer in progress. */
|
||||
|
||||
/* Complete code (=0) */
|
||||
i2cTransferDone = 0, /**< Transfer completed successfully. */
|
||||
|
||||
/* Transfer error codes (<0) */
|
||||
i2cTransferNack = -1, /**< NACK received during transfer. */
|
||||
i2cTransferBusErr = -2, /**< Bus error during transfer (misplaced START/STOP). */
|
||||
i2cTransferArbLost = -3, /**< Arbitration lost during transfer. */
|
||||
i2cTransferUsageFault = -4, /**< Usage fault. */
|
||||
i2cTransferSwFault = -5 /**< SW fault. */
|
||||
} I2C_TransferReturn_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** I2C initialization structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Enable I2C peripheral when init completed. */
|
||||
bool enable;
|
||||
|
||||
/** Set to master (true) or slave (false) mode */
|
||||
bool master;
|
||||
|
||||
/**
|
||||
* I2C reference clock assumed when configuring bus frequency setup.
|
||||
* Set it to 0 if currently configurated reference clock shall be used
|
||||
* This parameter is only applicable if operating in master mode.
|
||||
*/
|
||||
uint32_t refFreq;
|
||||
|
||||
/**
|
||||
* (Max) I2C bus frequency to use. This parameter is only applicable
|
||||
* if operating in master mode.
|
||||
*/
|
||||
uint32_t freq;
|
||||
|
||||
/** Clock low/high ratio control. */
|
||||
I2C_ClockHLR_TypeDef clhr;
|
||||
} I2C_Init_TypeDef;
|
||||
|
||||
/** Suggested default config for I2C init structure. */
|
||||
#define I2C_INIT_DEFAULT \
|
||||
{ true, /* Enable when init done */ \
|
||||
true, /* Set to master mode */ \
|
||||
0, /* Use currently configured reference clock */ \
|
||||
I2C_FREQ_STANDARD_MAX, /* Set to standard rate assuring being */ \
|
||||
/* within I2C spec */ \
|
||||
i2cClockHLRStandard /* Set to use 4:4 low/high duty cycle */ \
|
||||
}
|
||||
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* Master mode transfer message structure used to define a complete
|
||||
* I2C transfer sequence (from start to stop).
|
||||
* @details
|
||||
* The structure allows for defining the following types of sequences,
|
||||
* please refer to defines for sequence details.
|
||||
* @li #I2C_FLAG_READ - data read into buf[0].data
|
||||
* @li #I2C_FLAG_WRITE - data written from buf[0].data
|
||||
* @li #I2C_FLAG_WRITE_READ - data written from buf[0].data and read
|
||||
* into buf[1].data
|
||||
* @li #I2C_FLAG_WRITE_WRITE - data written from buf[0].data and
|
||||
* buf[1].data
|
||||
*/
|
||||
typedef struct
|
||||
{
|
||||
/**
|
||||
* @brief
|
||||
* Address to use after (repeated) start.
|
||||
* @details
|
||||
* Layout details, A = address bit, X = don't care bit (set to 0):
|
||||
* @li 7 bit address - use format AAAA AAAX.
|
||||
* @li 10 bit address - use format XXXX XAAX AAAA AAAA
|
||||
*/
|
||||
uint16_t addr;
|
||||
|
||||
/** Flags defining sequence type and details, see I2C_FLAG_... defines. */
|
||||
uint16_t flags;
|
||||
|
||||
/**
|
||||
* Buffers used to hold data to send from or receive into depending
|
||||
* on sequence type.
|
||||
*/
|
||||
struct
|
||||
{
|
||||
/** Buffer used for data to transmit/receive, must be @p len long. */
|
||||
uint8_t *data;
|
||||
|
||||
/**
|
||||
* Number of bytes in @p data to send or receive. Notice that when
|
||||
* receiving data to this buffer, at least 1 byte must be received.
|
||||
* Setting @p len to 0 in the receive case is considered a usage fault.
|
||||
* Transmitting 0 bytes is legal, in which case only the address
|
||||
* is transmitted after the start condition.
|
||||
*/
|
||||
uint16_t len;
|
||||
} buf[2];
|
||||
} I2C_TransferSeq_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
uint32_t I2C_BusFreqGet(I2C_TypeDef *i2c);
|
||||
void I2C_BusFreqSet(I2C_TypeDef *i2c,
|
||||
uint32_t refFreq,
|
||||
uint32_t freq,
|
||||
I2C_ClockHLR_TypeDef type);
|
||||
void I2C_Enable(I2C_TypeDef *i2c, bool enable);
|
||||
void I2C_Init(I2C_TypeDef *i2c, const I2C_Init_TypeDef *init);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending I2C interrupts.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending I2C interrupt source to clear. Use a bitwse logic OR combination of
|
||||
* valid interrupt flags for the I2C module (I2C_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void I2C_IntClear(I2C_TypeDef *i2c, uint32_t flags)
|
||||
{
|
||||
i2c->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more I2C interrupts.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* I2C interrupt sources to disable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the I2C module (I2C_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void I2C_IntDisable(I2C_TypeDef *i2c, uint32_t flags)
|
||||
{
|
||||
i2c->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more I2C interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using I2C_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* I2C interrupt sources to enable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the I2C module (I2C_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void I2C_IntEnable(I2C_TypeDef *i2c, uint32_t flags)
|
||||
{
|
||||
i2c->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending I2C interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* I2C interrupt sources pending. A bitwise logic OR combination of valid
|
||||
* interrupt flags for the I2C module (I2C_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t I2C_IntGet(I2C_TypeDef *i2c)
|
||||
{
|
||||
return(i2c->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending I2C interrupts from SW.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* I2C interrupt sources to set to pending. Use a bitwise logic OR combination
|
||||
* of valid interrupt flags for the I2C module (I2C_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void I2C_IntSet(I2C_TypeDef *i2c, uint32_t flags)
|
||||
{
|
||||
i2c->IFS = flags;
|
||||
}
|
||||
|
||||
void I2C_Reset(I2C_TypeDef *i2c);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get slave address used for I2C peripheral (when operating in slave mode).
|
||||
*
|
||||
* @details
|
||||
* For 10 bit addressing mode, the address is split in two bytes, and only
|
||||
* the first byte setting is fetched, effectively only controlling the 2 most
|
||||
* significant bits of the 10 bit address. Full handling of 10 bit addressing
|
||||
* in slave mode requires additional SW handling.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* I2C slave address in use. The 7 most significant bits define the actual
|
||||
* address, the least significant bit is reserved and always returned as 0.
|
||||
******************************************************************************/
|
||||
static __INLINE uint8_t I2C_SlaveAddressGet(I2C_TypeDef *i2c)
|
||||
{
|
||||
return((uint8_t)(i2c->SADDR));
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set slave address to use for I2C peripheral (when operating in slave mode).
|
||||
*
|
||||
* @details
|
||||
* For 10 bit addressing mode, the address is split in two bytes, and only
|
||||
* the first byte is set, effectively only controlling the 2 most significant
|
||||
* bits of the 10 bit address. Full handling of 10 bit addressing in slave
|
||||
* mode requires additional SW handling.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @param[in] addr
|
||||
* I2C slave address to use. The 7 most significant bits define the actual
|
||||
* address, the least significant bit is reserved and always set to 0.
|
||||
******************************************************************************/
|
||||
static __INLINE void I2C_SlaveAddressSet(I2C_TypeDef *i2c, uint8_t addr)
|
||||
{
|
||||
i2c->SADDR = (uint32_t)addr & 0xfe;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get slave address mask used for I2C peripheral (when operating in slave
|
||||
* mode).
|
||||
*
|
||||
* @details
|
||||
* The address mask defines how the comparator works. A bit position with
|
||||
* value 0 means that the corresponding slave address bit is ignored during
|
||||
* comparison (don't care). A bit position with value 1 means that the
|
||||
* corresponding slave address bit must match.
|
||||
*
|
||||
* For 10 bit addressing mode, the address is split in two bytes, and only
|
||||
* the mask for the first address byte is fetched, effectively only
|
||||
* controlling the 2 most significant bits of the 10 bit address.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* I2C slave address mask in use. The 7 most significant bits define the
|
||||
* actual address mask, the least significant bit is reserved and always
|
||||
* returned as 0.
|
||||
******************************************************************************/
|
||||
static __INLINE uint8_t I2C_SlaveAddressMaskGet(I2C_TypeDef *i2c)
|
||||
{
|
||||
return((uint8_t)(i2c->SADDRMASK));
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set slave address mask used for I2C peripheral (when operating in slave
|
||||
* mode).
|
||||
*
|
||||
* @details
|
||||
* The address mask defines how the comparator works. A bit position with
|
||||
* value 0 means that the corresponding slave address bit is ignored during
|
||||
* comparison (don't care). A bit position with value 1 means that the
|
||||
* corresponding slave address bit must match.
|
||||
*
|
||||
* For 10 bit addressing mode, the address is split in two bytes, and only
|
||||
* the mask for the first address byte is set, effectively only controlling
|
||||
* the 2 most significant bits of the 10 bit address.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @param[in] mask
|
||||
* I2C slave address mask to use. The 7 most significant bits define the
|
||||
* actual address mask, the least significant bit is reserved and should
|
||||
* be 0.
|
||||
******************************************************************************/
|
||||
static __INLINE void I2C_SlaveAddressMaskSet(I2C_TypeDef *i2c, uint8_t mask)
|
||||
{
|
||||
i2c->SADDRMASK = (uint32_t)mask & 0xfe;
|
||||
}
|
||||
|
||||
|
||||
I2C_TransferReturn_TypeDef I2C_Transfer(I2C_TypeDef *i2c);
|
||||
I2C_TransferReturn_TypeDef I2C_TransferInit(I2C_TypeDef *i2c,
|
||||
I2C_TransferSeq_TypeDef *seq);
|
||||
|
||||
/** @} (end addtogroup I2C) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_I2C_H */
|
|
@ -0,0 +1,110 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Interrupt enable/disable unit API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2011 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_INT_H
|
||||
#define __EFM32_INT_H
|
||||
|
||||
#include "efm32.h"
|
||||
|
||||
extern uint32_t INT_LockCnt;
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup INT
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable interrupts.
|
||||
*
|
||||
* @return
|
||||
* The resulting interrupt nesting level.
|
||||
*
|
||||
* @details
|
||||
* Disable interrupts and increment lock level counter.
|
||||
*
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t INT_Disable(void)
|
||||
{
|
||||
__disable_irq();
|
||||
if (INT_LockCnt < UINT32_MAX)
|
||||
{
|
||||
INT_LockCnt++;
|
||||
}
|
||||
|
||||
return INT_LockCnt;
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable interrupts.
|
||||
*
|
||||
* @return
|
||||
* The resulting interrupt nesting level.
|
||||
*
|
||||
* @details
|
||||
* Decrement interrupt lock level counter and enable interrupts if counter
|
||||
* reached zero.
|
||||
*
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t INT_Enable(void)
|
||||
{
|
||||
uint32_t retVal;
|
||||
|
||||
if (INT_LockCnt > 0)
|
||||
{
|
||||
INT_LockCnt--;
|
||||
retVal = INT_LockCnt;
|
||||
if (retVal == 0)
|
||||
{
|
||||
__enable_irq();
|
||||
}
|
||||
return retVal;
|
||||
}
|
||||
else
|
||||
{
|
||||
return 0;
|
||||
}
|
||||
}
|
||||
|
||||
/** @} (end addtogroup INT) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_INT_H */
|
|
@ -0,0 +1,627 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Liquid Crystal Display (LCD) peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_LCD_H
|
||||
#define __EFM32_LCD_H
|
||||
|
||||
#include "efm32.h"
|
||||
|
||||
#if defined(LCD_COUNT) && (LCD_COUNT > 0)
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup LCD
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** MUX setting */
|
||||
typedef enum
|
||||
{
|
||||
/** Static (segments can be multiplexed with LCD_COM[0]) */
|
||||
lcdMuxStatic = LCD_DISPCTRL_MUX_STATIC,
|
||||
/** Duplex / 1/2 Duty cycle (segments can be multiplexed with LCD_COM[0:1]) */
|
||||
lcdMuxDuplex = LCD_DISPCTRL_MUX_DUPLEX,
|
||||
/** Triplex / 1/3 Duty cycle (segments can be multiplexed with LCD_COM[0:2]) */
|
||||
lcdMuxTriplex = LCD_DISPCTRL_MUX_TRIPLEX,
|
||||
/** Quadruplex / 1/4 Duty cycle (segments can be multiplexed with LCD_COM[0:3]) */
|
||||
lcdMuxQuadruplex = LCD_DISPCTRL_MUX_QUADRUPLEX,
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/** Sextaplex / 1/6 Duty cycle (segments can be multiplexed with LCD_COM[0:5]) */
|
||||
lcdMuxSextaplex = LCD_DISPCTRL_MUXE_MUXE | LCD_DISPCTRL_MUX_DUPLEX,
|
||||
/** Octaplex / 1/6 Duty cycle (segments can be multiplexed with LCD_COM[0:5]) */
|
||||
lcdMuxOctaplex = LCD_DISPCTRL_MUXE_MUXE | LCD_DISPCTRL_MUX_QUADRUPLEX
|
||||
#endif
|
||||
} LCD_Mux_TypeDef;
|
||||
|
||||
/** Bias setting */
|
||||
typedef enum
|
||||
{
|
||||
/** Static (2 levels) */
|
||||
lcdBiasStatic = LCD_DISPCTRL_BIAS_STATIC,
|
||||
/** 1/2 Bias (3 levels) */
|
||||
lcdBiasOneHalf = LCD_DISPCTRL_BIAS_ONEHALF,
|
||||
/** 1/3 Bias (4 levels) */
|
||||
lcdBiasOneThird = LCD_DISPCTRL_BIAS_ONETHIRD,
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/** 1/4 Bias (5 levels) */
|
||||
lcdBiasOneFourth = LCD_DISPCTRL_BIAS_ONEFOURTH,
|
||||
#endif
|
||||
} LCD_Bias_TypeDef;
|
||||
|
||||
/** Wave type */
|
||||
typedef enum
|
||||
{
|
||||
/** Low power optimized waveform output */
|
||||
lcdWaveLowPower = LCD_DISPCTRL_WAVE_LOWPOWER,
|
||||
/** Regular waveform output */
|
||||
lcdWaveNormal = LCD_DISPCTRL_WAVE_NORMAL
|
||||
} LCD_Wave_TypeDef;
|
||||
|
||||
/** VLCD Voltage Source */
|
||||
typedef enum
|
||||
{
|
||||
/** VLCD Powered by VDD */
|
||||
lcdVLCDSelVDD = LCD_DISPCTRL_VLCDSEL_VDD,
|
||||
/** VLCD Powered by external VDD / Voltage Boost */
|
||||
lcdVLCDSelVExtBoost = LCD_DISPCTRL_VLCDSEL_VEXTBOOST
|
||||
} LCD_VLCDSel_TypeDef;
|
||||
|
||||
/** Contrast Configuration */
|
||||
typedef enum
|
||||
{
|
||||
/** Contrast is adjusted relative to VDD (VLCD) */
|
||||
lcdConConfVLCD = LCD_DISPCTRL_CONCONF_VLCD,
|
||||
/** Contrast is adjusted relative to Ground */
|
||||
lcdConConfGND = LCD_DISPCTRL_CONCONF_GND
|
||||
} LCD_ConConf_TypeDef;
|
||||
|
||||
/** Voltage Boost Level - Datasheets document setting for each part number */
|
||||
typedef enum
|
||||
{
|
||||
lcdVBoostLevel0 = LCD_DISPCTRL_VBLEV_LEVEL0, /**< Voltage boost LEVEL0 */
|
||||
lcdVBoostLevel1 = LCD_DISPCTRL_VBLEV_LEVEL1, /**< Voltage boost LEVEL1 */
|
||||
lcdVBoostLevel2 = LCD_DISPCTRL_VBLEV_LEVEL2, /**< Voltage boost LEVEL2 */
|
||||
lcdVBoostLevel3 = LCD_DISPCTRL_VBLEV_LEVEL3, /**< Voltage boost LEVEL3 */
|
||||
lcdVBoostLevel4 = LCD_DISPCTRL_VBLEV_LEVEL4, /**< Voltage boost LEVEL4 */
|
||||
lcdVBoostLevel5 = LCD_DISPCTRL_VBLEV_LEVEL5, /**< Voltage boost LEVEL5 */
|
||||
lcdVBoostLevel6 = LCD_DISPCTRL_VBLEV_LEVEL6, /**< Voltage boost LEVEL6 */
|
||||
lcdVBoostLevel7 = LCD_DISPCTRL_VBLEV_LEVEL7 /**< Voltage boost LEVEL7 */
|
||||
} LCD_VBoostLevel_TypeDef;
|
||||
|
||||
/** Frame Counter Clock Prescaler, FC-CLK = FrameRate (Hz) / this factor */
|
||||
typedef enum
|
||||
{
|
||||
/** Prescale Div 1 */
|
||||
lcdFCPrescDiv1 = LCD_BACTRL_FCPRESC_DIV1,
|
||||
/** Prescale Div 2 */
|
||||
lcdFCPrescDiv2 = LCD_BACTRL_FCPRESC_DIV2,
|
||||
/** Prescale Div 4 */
|
||||
lcdFCPrescDiv4 = LCD_BACTRL_FCPRESC_DIV4,
|
||||
/** Prescale Div 8 */
|
||||
lcdFCPrescDiv8 = LCD_BACTRL_FCPRESC_DIV8
|
||||
} LCD_FCPreScale_TypeDef;
|
||||
|
||||
/** Segment selection */
|
||||
typedef enum
|
||||
{
|
||||
/** Select segment lines 0 to 3 */
|
||||
lcdSegment0_3 = (1 << 0),
|
||||
/** Select segment lines 4 to 7 */
|
||||
lcdSegment4_7 = (1 << 1),
|
||||
/** Select segment lines 8 to 11 */
|
||||
lcdSegment8_11 = (1 << 2),
|
||||
/** Select segment lines 12 to 15 */
|
||||
lcdSegment12_15 = (1 << 3),
|
||||
/** Select segment lines 16 to 19 */
|
||||
lcdSegment16_19 = (1 << 4),
|
||||
/** Select segment lines 20 to 23 */
|
||||
lcdSegment20_23 = (1 << 5),
|
||||
#if defined(_EFM32_TINY_FAMILY)
|
||||
/** Select all segment lines */
|
||||
lcdSegmentAll = (0x003f)
|
||||
#endif
|
||||
#if defined(_EFM32_GECKO_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/** Select segment lines 24 to 27 */
|
||||
lcdSegment24_27 = (1 << 6),
|
||||
/** Select segment lines 28 to 31 */
|
||||
lcdSegment28_31 = (1 << 7),
|
||||
/** Select segment lines 32 to 35 */
|
||||
lcdSegment32_35 = (1 << 8),
|
||||
/** Select segment lines 36 to 39 */
|
||||
lcdSegment36_39 = (1 << 9),
|
||||
/** Select all segment lines */
|
||||
lcdSegmentAll = (0x03ff)
|
||||
#endif
|
||||
} LCD_SegmentRange_TypeDef;
|
||||
|
||||
/** Update Data Control */
|
||||
typedef enum
|
||||
{
|
||||
/** Regular update, data transfer done immediately */
|
||||
lcdUpdateCtrlRegular = LCD_CTRL_UDCTRL_REGULAR,
|
||||
/** Data transfer done at Frame Counter event */
|
||||
lcdUpdateCtrlFCEvent = LCD_CTRL_UDCTRL_FCEVENT,
|
||||
/** Data transfer done at Frame Start */
|
||||
lcdUpdateCtrlFrameStart = LCD_CTRL_UDCTRL_FRAMESTART
|
||||
} LCD_UpdateCtrl_TypeDef;
|
||||
|
||||
/** Animation Shift operation; none, left or right */
|
||||
typedef enum
|
||||
{
|
||||
/** No shift */
|
||||
lcdAnimShiftNone = _LCD_BACTRL_AREGASC_NOSHIFT,
|
||||
/** Shift segment bits left */
|
||||
lcdAnimShiftLeft = _LCD_BACTRL_AREGASC_SHIFTLEFT,
|
||||
/** Shift segment bits right */
|
||||
lcdAnimShiftRight = _LCD_BACTRL_AREGASC_SHIFTRIGHT
|
||||
} LCD_AnimShift_TypeDef;
|
||||
|
||||
/** Animation Logic Control, how AReg and BReg should be combined */
|
||||
typedef enum
|
||||
{
|
||||
/** Use bitwise logic AND to mix animation register A (AREGA) and B (AREGB) */
|
||||
lcdAnimLogicAnd = LCD_BACTRL_ALOGSEL_AND,
|
||||
/** Use bitwise logic OR to mix animation register A (AREGA) and B (AREGB) */
|
||||
lcdAnimLogicOr = LCD_BACTRL_ALOGSEL_OR
|
||||
} LCD_AnimLogic_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** LCD Animation Configuration */
|
||||
typedef struct
|
||||
{
|
||||
/** Enable Animation at end of initialization */
|
||||
bool enable;
|
||||
/** Initial Animation Register A Value */
|
||||
uint32_t AReg;
|
||||
/** Shift operation of Animation Register A */
|
||||
LCD_AnimShift_TypeDef AShift;
|
||||
/** Initial Animation Register B Value */
|
||||
uint32_t BReg;
|
||||
/** Shift operation of Animation Register B */
|
||||
LCD_AnimShift_TypeDef BShift;
|
||||
/** A and B Logical Operation to use for mixing and outputting resulting segments */
|
||||
LCD_AnimLogic_TypeDef animLogic;
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** Number of first segment to animate. Options are 0 or 8 for Giant/Leopard. End is startSeg+7 */
|
||||
int startSeg;
|
||||
#endif
|
||||
} LCD_AnimInit_TypeDef;
|
||||
|
||||
/** LCD Frame Control Initialization */
|
||||
typedef struct
|
||||
{
|
||||
/** Enable at end */
|
||||
bool enable;
|
||||
/** Frame Counter top value */
|
||||
uint32_t top;
|
||||
/** Frame Counter clock prescaler */
|
||||
LCD_FCPreScale_TypeDef prescale;
|
||||
} LCD_FrameCountInit_TypeDef;
|
||||
|
||||
/** LCD Controller Initialization structure */
|
||||
typedef struct
|
||||
{
|
||||
/** Enable controller at end of initialization */
|
||||
bool enable;
|
||||
/** Mux configuration */
|
||||
LCD_Mux_TypeDef mux;
|
||||
/** Bias configuration */
|
||||
LCD_Bias_TypeDef bias;
|
||||
/** Wave configuration */
|
||||
LCD_Wave_TypeDef wave;
|
||||
/** VLCD Select */
|
||||
LCD_VLCDSel_TypeDef vlcd;
|
||||
/** Contrast Configuration */
|
||||
LCD_ConConf_TypeDef contrast;
|
||||
} LCD_Init_TypeDef;
|
||||
|
||||
/** Default config for LCD init structure, enables 160 segments */
|
||||
#define LCD_INIT_DEFAULT \
|
||||
{ true, \
|
||||
lcdMuxQuadruplex, \
|
||||
lcdBiasOneThird, \
|
||||
lcdWaveLowPower, \
|
||||
lcdVLCDSelVDD, \
|
||||
lcdConConfVLCD \
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void LCD_Init(const LCD_Init_TypeDef *lcdInit);
|
||||
void LCD_VLCDSelect(LCD_VLCDSel_TypeDef vlcd);
|
||||
void LCD_UpdateCtrl(LCD_UpdateCtrl_TypeDef ud);
|
||||
void LCD_FrameCountInit(const LCD_FrameCountInit_TypeDef *fcInit);
|
||||
void LCD_AnimInit(const LCD_AnimInit_TypeDef *animInit);
|
||||
|
||||
void LCD_SegmentRangeEnable(LCD_SegmentRange_TypeDef segment, bool enable);
|
||||
void LCD_SegmentSet(int com, int bit, bool enable);
|
||||
void LCD_SegmentSetLow(int com, uint32_t mask, uint32_t bits);
|
||||
#if defined(_EFM32_GECKO_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
void LCD_SegmentSetHigh(int com, uint32_t mask, uint32_t bits);
|
||||
#endif
|
||||
void LCD_ContrastSet(int level);
|
||||
void LCD_VBoostSet(LCD_VBoostLevel_TypeDef vboost);
|
||||
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
void LCD_BiasSegmentSet(int segment, int biasLevel);
|
||||
void LCD_BiasComSet(int com, int biasLevel);
|
||||
#endif
|
||||
|
||||
static __INLINE void LCD_Enable(bool enable);
|
||||
static __INLINE void LCD_AnimEnable(bool enable);
|
||||
static __INLINE void LCD_BlinkEnable(bool enable);
|
||||
static __INLINE void LCD_BlankEnable(bool enable);
|
||||
static __INLINE void LCD_FrameCountEnable(bool enable);
|
||||
static __INLINE int LCD_AnimState(void);
|
||||
static __INLINE int LCD_BlinkState(void);
|
||||
static __INLINE void LCD_FreezeEnable(bool enable);
|
||||
static __INLINE uint32_t LCD_SyncBusyGet(void);
|
||||
static __INLINE void LCD_SyncBusyDelay(uint32_t flags);
|
||||
static __INLINE uint32_t LCD_IntGet(void);
|
||||
static __INLINE uint32_t LCD_IntGetEnabled(void);
|
||||
static __INLINE void LCD_IntSet(uint32_t flags);
|
||||
static __INLINE void LCD_IntEnable(uint32_t flags);
|
||||
static __INLINE void LCD_IntDisable(uint32_t flags);
|
||||
static __INLINE void LCD_IntClear(uint32_t flags);
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
static __INLINE void LCD_DSCEnable(bool enable);
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable or disable LCD controller
|
||||
*
|
||||
* @param[in] enable
|
||||
* If true, enables LCD controller with current configuration, if false
|
||||
* disables LCD controller. CMU clock for LCD must be enabled for correct
|
||||
* operation.
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_Enable(bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
LCD->CTRL |= LCD_CTRL_EN;
|
||||
}
|
||||
else
|
||||
{
|
||||
LCD->CTRL &= ~(LCD_CTRL_EN);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enables or disables LCD Animation feature
|
||||
*
|
||||
* @param[in] enable
|
||||
* Boolean true enables animation, false disables animation
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_AnimEnable(bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
LCD->BACTRL |= LCD_BACTRL_AEN;
|
||||
}
|
||||
else
|
||||
{
|
||||
LCD->BACTRL &= ~(LCD_BACTRL_AEN);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enables or disables LCD blink
|
||||
*
|
||||
* @param[in] enable
|
||||
* Boolean true enables blink, false disables blink
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_BlinkEnable(bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
LCD->BACTRL |= LCD_BACTRL_BLINKEN;
|
||||
}
|
||||
else
|
||||
{
|
||||
LCD->BACTRL &= ~(LCD_BACTRL_BLINKEN);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disables all segments, while keeping segment state
|
||||
*
|
||||
* @param[in] enable
|
||||
* Boolean true clears all segments, boolean false restores all segment lines
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_BlankEnable(bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
LCD->BACTRL |= LCD_BACTRL_BLANK;
|
||||
}
|
||||
else
|
||||
{
|
||||
LCD->BACTRL &= ~(LCD_BACTRL_BLANK);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enables or disables LCD Frame Control
|
||||
*
|
||||
* @param[in] enable
|
||||
* Boolean true enables frame counter, false disables frame counter
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_FrameCountEnable(bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
LCD->BACTRL |= LCD_BACTRL_FCEN;
|
||||
}
|
||||
else
|
||||
{
|
||||
LCD->BACTRL &= ~(LCD_BACTRL_FCEN);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Returns current animation state
|
||||
*
|
||||
* @return
|
||||
* Animation state, in range 0-15
|
||||
******************************************************************************/
|
||||
static __INLINE int LCD_AnimState(void)
|
||||
{
|
||||
return (int)(LCD->STATUS & _LCD_STATUS_ASTATE_MASK) >> _LCD_STATUS_ASTATE_SHIFT;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Returns current blink state
|
||||
*
|
||||
* @return
|
||||
* Return value is 1 if segments are enabled, 0 if disabled
|
||||
******************************************************************************/
|
||||
static __INLINE int LCD_BlinkState(void)
|
||||
{
|
||||
return (int)(LCD->STATUS & _LCD_STATUS_BLINK_MASK) >> _LCD_STATUS_BLINK_SHIFT;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* When set, LCD registers will not be updated until cleared,
|
||||
*
|
||||
* @param[in] enable
|
||||
* When enable is true, update is stopped, when false all registers are
|
||||
* updated
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_FreezeEnable(bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
LCD->FREEZE = LCD_FREEZE_REGFREEZE_FREEZE;
|
||||
}
|
||||
else
|
||||
{
|
||||
LCD->FREEZE = LCD_FREEZE_REGFREEZE_UPDATE;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Returns SYNCBUSY bits, indicating which registers have pending updates
|
||||
*
|
||||
* @return
|
||||
* Bit fields for LCD registers which have pending updates
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t LCD_SyncBusyGet(void)
|
||||
{
|
||||
return(LCD->SYNCBUSY);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Polls LCD SYNCBUSY flags, until flag has been cleared
|
||||
*
|
||||
* @param[in] flags
|
||||
* Bit fields for LCD registers that shall be updated before we continue
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_SyncBusyDelay(uint32_t flags)
|
||||
{
|
||||
while (LCD->SYNCBUSY & flags)
|
||||
;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending LCD interrupt flags
|
||||
*
|
||||
* @return
|
||||
* Pending LCD interrupt sources. Returns a set of interrupt flags OR-ed
|
||||
* together for multiple interrupt sources in the LCD module (LCD_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t LCD_IntGet(void)
|
||||
{
|
||||
return(LCD->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get enabled and pending LCD interrupt flags.
|
||||
*
|
||||
* @details
|
||||
* Useful for handling more interrupt sources in the same interrupt handler.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @return
|
||||
* Pending and enabled LCD interrupt sources.
|
||||
* The return value is the bitwise AND combination of
|
||||
* - the OR combination of enabled interrupt sources in LCD_IEN_nnn
|
||||
* register (LCD_IEN_nnn) and
|
||||
* - the bitwise OR combination of valid interrupt flags of the LCD module
|
||||
* (LCD_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t LCD_IntGetEnabled(void)
|
||||
{
|
||||
uint32_t tmp = 0U;
|
||||
|
||||
/* Store LCD->IEN in temporary variable in order to define explicit order
|
||||
* of volatile accesses. */
|
||||
tmp = LCD->IEN;
|
||||
|
||||
/* Bitwise AND of pending and enabled interrupts */
|
||||
return LCD->IF & tmp;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending LCD interrupts from SW.
|
||||
*
|
||||
* @param[in] flags
|
||||
* LCD interrupt sources to set to pending. Use a set of interrupt flags
|
||||
* OR-ed together to set multiple interrupt sources for the LCD module
|
||||
* (LCD_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_IntSet(uint32_t flags)
|
||||
{
|
||||
LCD->IFS = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable LCD interrupts
|
||||
*
|
||||
* @param[in] flags
|
||||
* LCD interrupt sources to enable. Use a set of interrupt flags OR-ed
|
||||
* together to set multiple interrupt sources for the LCD module
|
||||
* (LCD_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_IntEnable(uint32_t flags)
|
||||
{
|
||||
LCD->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable LCD interrupts
|
||||
*
|
||||
* @param[in] flags
|
||||
* LCD interrupt sources to disable. Use a set of interrupt flags OR-ed
|
||||
* together to disable multiple interrupt sources for the LCD module
|
||||
* (LCD_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_IntDisable(uint32_t flags)
|
||||
{
|
||||
LCD->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more interrupt flags
|
||||
*
|
||||
* @param[in] flags
|
||||
* LCD interrupt sources to clear. Use a set of interrupt flags OR-ed
|
||||
* together to clear multiple interrupt sources for the LCD module
|
||||
* (LCD_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_IntClear(uint32_t flags)
|
||||
{
|
||||
LCD->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable or disable LCD Direct Segment Control
|
||||
*
|
||||
* @param[in] enable
|
||||
* If true, enables LCD controller Direct Segment Control
|
||||
* Segment and COM line bias levels needs to be set explicitly with the
|
||||
* LCD_BiasSegmentSet() and LCD_BiasComSet() function calls.
|
||||
******************************************************************************/
|
||||
static __INLINE void LCD_DSCEnable(bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
LCD->CTRL |= LCD_CTRL_DSC;
|
||||
}
|
||||
else
|
||||
{
|
||||
LCD->CTRL &= ~(LCD_CTRL_DSC);
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/** @} (end addtogroup LCD) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* defined(LCD_COUNT) && (LCD_COUNT > 0) */
|
||||
|
||||
#endif /* __EFM32_LCD_H */
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,259 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Low Energy Timer (LETIMER) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_LETIMER_H
|
||||
#define __EFM32_LETIMER_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup LETIMER
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Repeat mode. */
|
||||
typedef enum
|
||||
{
|
||||
/** Count until stopped by SW. */
|
||||
letimerRepeatFree = _LETIMER_CTRL_REPMODE_FREE,
|
||||
/** Count REP0 times. */
|
||||
letimerRepeatOneshot = _LETIMER_CTRL_REPMODE_ONESHOT,
|
||||
/**
|
||||
* Count REP0 times, if REP1 has been written to, it is loaded into
|
||||
* REP0 when REP0 is about to be decremented to 0.
|
||||
*/
|
||||
letimerRepeatBuffered = _LETIMER_CTRL_REPMODE_BUFFERED,
|
||||
/**
|
||||
* Run as long as both REP0 and REP1 are not 0. Both REP0 and REP1
|
||||
* are decremented when counter underflows.
|
||||
*/
|
||||
letimerRepeatDouble = _LETIMER_CTRL_REPMODE_DOUBLE
|
||||
} LETIMER_RepeatMode_TypeDef;
|
||||
|
||||
|
||||
/** Underflow action on output. */
|
||||
typedef enum
|
||||
{
|
||||
/** No output action. */
|
||||
letimerUFOANone = _LETIMER_CTRL_UFOA0_NONE,
|
||||
/** Toggle output when counter underflows. */
|
||||
letimerUFOAToggle = _LETIMER_CTRL_UFOA0_TOGGLE,
|
||||
/** Hold output one LETIMER clock cycle when counter underflows. */
|
||||
letimerUFOAPulse = _LETIMER_CTRL_UFOA0_PULSE,
|
||||
/** Set output idle when counter underflows, and active when matching COMP1. */
|
||||
letimerUFOAPwm = _LETIMER_CTRL_UFOA0_PWM
|
||||
} LETIMER_UFOA_TypeDef;
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** LETIMER initialization structure. */
|
||||
typedef struct
|
||||
{
|
||||
bool enable; /**< Start counting when init completed. */
|
||||
bool debugRun; /**< Counter shall keep running during debug halt. */
|
||||
bool rtcComp0Enable; /**< Start counting on RTC COMP0 match. */
|
||||
bool rtcComp1Enable; /**< Start counting on RTC COMP1 match. */
|
||||
bool comp0Top; /**< Load COMP0 register into CNT when counter underflows. */
|
||||
bool bufTop; /**< Load COMP1 into COMP0 when REP0 reaches 0. */
|
||||
uint8_t out0Pol; /**< Idle value for output 0. */
|
||||
uint8_t out1Pol; /**< Idle value for output 1. */
|
||||
LETIMER_UFOA_TypeDef ufoa0; /**< Underflow output 0 action. */
|
||||
LETIMER_UFOA_TypeDef ufoa1; /**< Underflow output 1 action. */
|
||||
LETIMER_RepeatMode_TypeDef repMode; /**< Repeat mode. */
|
||||
} LETIMER_Init_TypeDef;
|
||||
|
||||
/** Default config for LETIMER init structure. */
|
||||
#define LETIMER_INIT_DEFAULT \
|
||||
{ true, /* Enable timer when init complete. */ \
|
||||
false, /* Stop counter during debug halt. */ \
|
||||
false, /* Do not start counting on RTC COMP0 match. */ \
|
||||
false, /* Do not start counting on RTC COMP1 match. */ \
|
||||
false, /* Do not load COMP0 into CNT on underflow. */ \
|
||||
false, /* Do not load COMP1 into COMP0 when REP0 reaches 0. */ \
|
||||
0, /* Idle value 0 for output 0. */ \
|
||||
0, /* Idle value 0 for output 1. */ \
|
||||
letimerUFOANone, /* No action on underflow on output 0. */ \
|
||||
letimerUFOANone, /* No action on underflow on output 1. */ \
|
||||
letimerRepeatFree /* Count until stopped by SW. */ \
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
uint32_t LETIMER_CompareGet(LETIMER_TypeDef *letimer, unsigned int comp);
|
||||
void LETIMER_CompareSet(LETIMER_TypeDef *letimer,
|
||||
unsigned int comp,
|
||||
uint32_t value);
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get LETIMER counter value.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Current LETIMER counter value.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t LETIMER_CounterGet(LETIMER_TypeDef *letimer)
|
||||
{
|
||||
return(letimer->CNT);
|
||||
}
|
||||
|
||||
|
||||
void LETIMER_Enable(LETIMER_TypeDef *letimer, bool enable);
|
||||
void LETIMER_FreezeEnable(LETIMER_TypeDef *letimer, bool enable);
|
||||
void LETIMER_Init(LETIMER_TypeDef *letimer, const LETIMER_Init_TypeDef *init);
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending LETIMER interrupts.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending LETIMER interrupt source to clear. Use a bitwise logic OR
|
||||
* combination of valid interrupt flags for the LETIMER module
|
||||
* (LETIMER_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LETIMER_IntClear(LETIMER_TypeDef *letimer, uint32_t flags)
|
||||
{
|
||||
letimer->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more LETIMER interrupts.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* LETIMER interrupt sources to disable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the LETIMER module (LETIMER_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LETIMER_IntDisable(LETIMER_TypeDef *letimer, uint32_t flags)
|
||||
{
|
||||
letimer->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more LETIMER interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using LETIMER_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* LETIMER interrupt sources to enable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the LETIMER module (LETIMER_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LETIMER_IntEnable(LETIMER_TypeDef *letimer, uint32_t flags)
|
||||
{
|
||||
letimer->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending LETIMER interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* LETIMER interrupt sources pending. A bitwise logic OR combination of
|
||||
* valid interrupt flags for the LETIMER module (LETIMER_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t LETIMER_IntGet(LETIMER_TypeDef *letimer)
|
||||
{
|
||||
return(letimer->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending LETIMER interrupts from SW.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* LETIMER interrupt sources to set to pending. Use a bitwise logic OR
|
||||
* combination of valid interrupt flags for the LETIMER module (LETIMER_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LETIMER_IntSet(LETIMER_TypeDef *letimer, uint32_t flags)
|
||||
{
|
||||
letimer->IFS = flags;
|
||||
}
|
||||
|
||||
uint32_t LETIMER_RepeatGet(LETIMER_TypeDef *letimer, unsigned int rep);
|
||||
void LETIMER_RepeatSet(LETIMER_TypeDef *letimer,
|
||||
unsigned int rep,
|
||||
uint32_t value);
|
||||
void LETIMER_Reset(LETIMER_TypeDef *letimer);
|
||||
|
||||
|
||||
/** @} (end addtogroup LETIMER) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_LETIMER_H */
|
|
@ -0,0 +1,255 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Low Energy Universal Asynchronous Receiver/Transmitter (LEUART)
|
||||
* peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_LEUART_H
|
||||
#define __EFM32_LEUART_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup LEUART
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Databit selection. */
|
||||
typedef enum
|
||||
{
|
||||
leuartDatabits8 = LEUART_CTRL_DATABITS_EIGHT, /**< 8 databits. */
|
||||
leuartDatabits9 = LEUART_CTRL_DATABITS_NINE /**< 9 databits. */
|
||||
} LEUART_Databits_TypeDef;
|
||||
|
||||
|
||||
/** Enable selection. */
|
||||
typedef enum
|
||||
{
|
||||
/** Disable both receiver and transmitter. */
|
||||
leuartDisable = 0x0,
|
||||
|
||||
/** Enable receiver only, transmitter disabled. */
|
||||
leuartEnableRx = LEUART_CMD_RXEN,
|
||||
|
||||
/** Enable transmitter only, receiver disabled. */
|
||||
leuartEnableTx = LEUART_CMD_TXEN,
|
||||
|
||||
/** Enable both receiver and transmitter. */
|
||||
leuartEnable = (LEUART_CMD_RXEN | LEUART_CMD_TXEN)
|
||||
} LEUART_Enable_TypeDef;
|
||||
|
||||
|
||||
/** Parity selection. */
|
||||
typedef enum
|
||||
{
|
||||
leuartNoParity = LEUART_CTRL_PARITY_NONE, /**< No parity. */
|
||||
leuartEvenParity = LEUART_CTRL_PARITY_EVEN, /**< Even parity. */
|
||||
leuartOddParity = LEUART_CTRL_PARITY_ODD /**< Odd parity. */
|
||||
} LEUART_Parity_TypeDef;
|
||||
|
||||
|
||||
/** Stopbits selection. */
|
||||
typedef enum
|
||||
{
|
||||
leuartStopbits1 = LEUART_CTRL_STOPBITS_ONE, /**< 1 stopbits. */
|
||||
leuartStopbits2 = LEUART_CTRL_STOPBITS_TWO /**< 2 stopbits. */
|
||||
} LEUART_Stopbits_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Init structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Specifies whether TX and/or RX shall be enabled when init completed. */
|
||||
LEUART_Enable_TypeDef enable;
|
||||
|
||||
/**
|
||||
* LEUART reference clock assumed when configuring baudrate setup. Set
|
||||
* it to 0 if currently configurated reference clock shall be used.
|
||||
*/
|
||||
uint32_t refFreq;
|
||||
|
||||
/** Desired baudrate. */
|
||||
uint32_t baudrate;
|
||||
|
||||
/** Number of databits in frame. */
|
||||
LEUART_Databits_TypeDef databits;
|
||||
|
||||
/** Parity mode to use. */
|
||||
LEUART_Parity_TypeDef parity;
|
||||
|
||||
/** Number of stopbits to use. */
|
||||
LEUART_Stopbits_TypeDef stopbits;
|
||||
} LEUART_Init_TypeDef;
|
||||
|
||||
/** Default config for LEUART init structure. */
|
||||
#define LEUART_INIT_DEFAULT \
|
||||
{ leuartEnable, /* Enable RX/TX when init completed. */ \
|
||||
0, /* Use current configured reference clock for configuring baudrate. */ \
|
||||
9600, /* 9600 bits/s. */ \
|
||||
leuartDatabits8, /* 8 databits. */ \
|
||||
leuartNoParity, /* No parity. */ \
|
||||
leuartStopbits1 /* 1 stopbit. */ \
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
uint32_t LEUART_BaudrateCalc(uint32_t refFreq, uint32_t clkdiv);
|
||||
uint32_t LEUART_BaudrateGet(LEUART_TypeDef *leuart);
|
||||
void LEUART_BaudrateSet(LEUART_TypeDef *leuart,
|
||||
uint32_t refFreq,
|
||||
uint32_t baudrate);
|
||||
void LEUART_Enable(LEUART_TypeDef *leuart, LEUART_Enable_TypeDef enable);
|
||||
void LEUART_FreezeEnable(LEUART_TypeDef *leuart, bool enable);
|
||||
void LEUART_Init(LEUART_TypeDef *leuart, LEUART_Init_TypeDef *init);
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending LEUART interrupts.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending LEUART interrupt source to clear. Use a bitwise logic OR
|
||||
* combination of valid interrupt flags for the LEUART module (LEUART_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LEUART_IntClear(LEUART_TypeDef *leuart, uint32_t flags)
|
||||
{
|
||||
leuart->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more LEUART interrupts.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* LEUART interrupt sources to disable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the LEUART module (LEUART_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LEUART_IntDisable(LEUART_TypeDef *leuart, uint32_t flags)
|
||||
{
|
||||
leuart->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more LEUART interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using LEUART_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* LEUART interrupt sources to enable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the LEUART module (LEUART_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LEUART_IntEnable(LEUART_TypeDef *leuart, uint32_t flags)
|
||||
{
|
||||
leuart->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending LEUART interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* LEUART interrupt sources pending. A bitwise logic OR combination of valid
|
||||
* interrupt flags for the LEUART module (LEUART_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t LEUART_IntGet(LEUART_TypeDef *leuart)
|
||||
{
|
||||
return(leuart->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending LEUART interrupts from SW.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* LEUART interrupt sources to set to pending. Use a bitwise logic OR
|
||||
* combination of valid interrupt flags for the LEUART module (LEUART_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void LEUART_IntSet(LEUART_TypeDef *leuart, uint32_t flags)
|
||||
{
|
||||
leuart->IFS = flags;
|
||||
}
|
||||
|
||||
void LEUART_Reset(LEUART_TypeDef *leuart);
|
||||
uint8_t LEUART_Rx(LEUART_TypeDef *leuart);
|
||||
uint16_t LEUART_RxExt(LEUART_TypeDef *leuart);
|
||||
void LEUART_Tx(LEUART_TypeDef *leuart, uint8_t data);
|
||||
void LEUART_TxExt(LEUART_TypeDef *leuart, uint16_t data);
|
||||
|
||||
|
||||
/** @} (end addtogroup LEUART) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_LEUART_H */
|
|
@ -0,0 +1,236 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Memory protection unit (MPU) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_MPU_H
|
||||
#define __EFM32_MPU_H
|
||||
|
||||
#include "efm32.h"
|
||||
|
||||
#if defined(__MPU_PRESENT) && (__MPU_PRESENT == 1)
|
||||
#include "efm32_assert.h"
|
||||
|
||||
#include <stdbool.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup MPU
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/** @anchor MPU_CTRL_PRIVDEFENA
|
||||
* Argument to MPU_enable(). Enables priviledged
|
||||
* access to default memory map. */
|
||||
#define MPU_CTRL_PRIVDEFENA MPU_CTRL_PRIVDEFENA_Msk
|
||||
|
||||
/** @anchor MPU_CTRL_HFNMIENA
|
||||
* Argument to MPU_enable(). Enables MPU during hard fault,
|
||||
* NMI, and FAULTMASK handlers. */
|
||||
#define MPU_CTRL_HFNMIENA MPU_CTRL_HFNMIENA_Msk
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/**
|
||||
* Size of an MPU region.
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
mpuRegionSize32b = 4, /**< 32 byte region size. */
|
||||
mpuRegionSize64b = 5, /**< 64 byte region size. */
|
||||
mpuRegionSize128b = 6, /**< 128 byte region size. */
|
||||
mpuRegionSize256b = 7, /**< 256 byte region size. */
|
||||
mpuRegionSize512b = 8, /**< 512 byte region size. */
|
||||
mpuRegionSize1Kb = 9, /**< 1K byte region size. */
|
||||
mpuRegionSize2Kb = 10, /**< 2K byte region size. */
|
||||
mpuRegionSize4Kb = 11, /**< 4K byte region size. */
|
||||
mpuRegionSize8Kb = 12, /**< 8K byte region size. */
|
||||
mpuRegionSize16Kb = 13, /**< 16K byte region size. */
|
||||
mpuRegionSize32Kb = 14, /**< 32K byte region size. */
|
||||
mpuRegionSize64Kb = 15, /**< 64K byte region size. */
|
||||
mpuRegionSize128Kb = 16, /**< 128K byte region size. */
|
||||
mpuRegionSize256Kb = 17, /**< 256K byte region size. */
|
||||
mpuRegionSize512Kb = 18, /**< 512K byte region size. */
|
||||
mpuRegionSize1Mb = 19, /**< 1M byte region size. */
|
||||
mpuRegionSize2Mb = 20, /**< 2M byte region size. */
|
||||
mpuRegionSize4Mb = 21, /**< 4M byte region size. */
|
||||
mpuRegionSize8Mb = 22, /**< 8M byte region size. */
|
||||
mpuRegionSize16Mb = 23, /**< 16M byte region size. */
|
||||
mpuRegionSize32Mb = 24, /**< 32M byte region size. */
|
||||
mpuRegionSize64Mb = 25, /**< 64M byte region size. */
|
||||
mpuRegionSize128Mb = 26, /**< 128M byte region size. */
|
||||
mpuRegionSize256Mb = 27, /**< 256M byte region size. */
|
||||
mpuRegionSize512Mb = 28, /**< 512M byte region size. */
|
||||
mpuRegionSize1Gb = 29, /**< 1G byte region size. */
|
||||
mpuRegionSize2Gb = 30, /**< 2G byte region size. */
|
||||
mpuRegionSize4Gb = 31 /**< 4G byte region size. */
|
||||
} MPU_RegionSize_TypeDef;
|
||||
|
||||
/**
|
||||
* MPU region access permission attributes.
|
||||
*/
|
||||
typedef enum
|
||||
{
|
||||
mpuRegionNoAccess = 0, /**< No access what so ever. */
|
||||
mpuRegionApPRw = 1, /**< Priviledged state R/W only. */
|
||||
mpuRegionApPRwURo = 2, /**< Priviledged state R/W, User state R only. */
|
||||
mpuRegionApFullAccess = 3, /**< R/W in Priviledged and User state. */
|
||||
mpuRegionApPRo = 5, /**< Priviledged R only. */
|
||||
mpuRegionApPRo_URo = 6 /**< R only in Priviledged and User state. */
|
||||
} MPU_RegionAp_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** MPU Region init structure. */
|
||||
typedef struct
|
||||
{
|
||||
bool regionEnable; /**< MPU region enable. */
|
||||
uint8_t regionNo; /**< MPU region number. */
|
||||
uint32_t baseAddress; /**< Region baseaddress. */
|
||||
MPU_RegionSize_TypeDef size; /**< Memory region size. */
|
||||
MPU_RegionAp_TypeDef accessPermission; /**< Memory access permissions. */
|
||||
bool disableExec; /**< Disable execution. */
|
||||
bool shareable; /**< Memory shareable attribute. */
|
||||
bool cacheable; /**< Memory cacheable attribute. */
|
||||
bool bufferable; /**< Memory bufferable attribute. */
|
||||
uint8_t srd; /**< Memory subregion disable bits. */
|
||||
uint8_t tex; /**< Memory type extension attributes. */
|
||||
} MPU_RegionInit_TypeDef;
|
||||
|
||||
/** Default configuration of MPU region init structure for flash memory. */
|
||||
#define MPU_INIT_FLASH_DEFAULT \
|
||||
{ \
|
||||
true, /* Enable MPU region. */ \
|
||||
0, /* MPU Region number. */ \
|
||||
FLASH_MEM_BASE, /* Flash base address. */ \
|
||||
mpuRegionSize1Mb, /* Size - Set to max. for EFM32. */ \
|
||||
mpuRegionApFullAccess, /* Access permissions. */ \
|
||||
false, /* Execution allowed. */ \
|
||||
false, /* Not shareable. */ \
|
||||
true, /* Cacheable. */ \
|
||||
false, /* Not bufferable. */ \
|
||||
0, /* No subregions. */ \
|
||||
0 /* No TEX attributes. */ \
|
||||
}
|
||||
|
||||
|
||||
/** Default configuration of MPU region init structure for sram memory. */
|
||||
#define MPU_INIT_SRAM_DEFAULT \
|
||||
{ \
|
||||
true, /* Enable MPU region. */ \
|
||||
1, /* MPU Region number. */ \
|
||||
RAM_MEM_BASE, /* SRAM base address. */ \
|
||||
mpuRegionSize128Kb, /* Size - Set to max. for EFM32. */ \
|
||||
mpuRegionApFullAccess, /* Access permissions. */ \
|
||||
false, /* Execution allowed. */ \
|
||||
true, /* Shareable. */ \
|
||||
true, /* Cacheable. */ \
|
||||
false, /* Not bufferable. */ \
|
||||
0, /* No subregions. */ \
|
||||
0 /* No TEX attributes. */ \
|
||||
}
|
||||
|
||||
|
||||
/** Default configuration of MPU region init structure for onchip peripherals.*/
|
||||
#define MPU_INIT_PERIPHERAL_DEFAULT \
|
||||
{ \
|
||||
true, /* Enable MPU region. */ \
|
||||
0, /* MPU Region number. */ \
|
||||
0, /* Region base address. */ \
|
||||
mpuRegionSize32b, /* Size - Set to minimum */ \
|
||||
mpuRegionApFullAccess, /* Access permissions. */ \
|
||||
true, /* Execution not allowed. */ \
|
||||
true, /* Shareable. */ \
|
||||
false, /* Not cacheable. */ \
|
||||
true, /* Bufferable. */ \
|
||||
0, /* No subregions. */ \
|
||||
0 /* No TEX attributes. */ \
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
|
||||
void MPU_ConfigureRegion(const MPU_RegionInit_TypeDef *init);
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable the MPU
|
||||
* @details
|
||||
* Disable MPU and MPU fault exceptions.
|
||||
******************************************************************************/
|
||||
static __INLINE void MPU_Disable(void)
|
||||
{
|
||||
SCB->SHCSR &= ~SCB_SHCSR_MEMFAULTENA_Msk; /* Disable fault exceptions */
|
||||
MPU->CTRL &= ~MPU_CTRL_ENABLE_Msk; /* Disable the MPU */
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable the MPU
|
||||
* @details
|
||||
* Enable MPU and MPU fault exceptions.
|
||||
* @param[in] flags
|
||||
* Use a logical OR of @ref MPU_CTRL_PRIVDEFENA and
|
||||
* @ref MPU_CTRL_HFNMIENA as needed.
|
||||
******************************************************************************/
|
||||
static __INLINE void MPU_Enable(uint32_t flags)
|
||||
{
|
||||
EFM_ASSERT(!(flags & ~(MPU_CTRL_PRIVDEFENA_Msk |
|
||||
MPU_CTRL_HFNMIENA_Msk |
|
||||
MPU_CTRL_ENABLE_Msk)));
|
||||
|
||||
MPU->CTRL = flags | MPU_CTRL_ENABLE_Msk; /* Enable the MPU */
|
||||
SCB->SHCSR |= SCB_SHCSR_MEMFAULTENA_Msk; /* Enable fault exceptions */
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup MPU) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* defined(__MPU_PRESENT) && (EBI_COUNT == 1) */
|
||||
|
||||
#endif /* __EFM32_MPU_H */
|
|
@ -0,0 +1,367 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Flash controller module (MSC) peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_MSC_H
|
||||
#define __EFM32_MSC_H
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
#include "efm32.h"
|
||||
#include "efm32_bitband.h"
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup MSC
|
||||
* @brief Flash controller (MSC) peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
************************* DEFINES *****************************************
|
||||
******************************************************************************/
|
||||
|
||||
/**
|
||||
* @brief
|
||||
* The timeout used while waiting for the flash to become ready after
|
||||
* a write. This number indicates the number of iterations to perform before
|
||||
* issuing a timeout.
|
||||
* @note
|
||||
* This timeout is set very large (in the order of 100x longer than
|
||||
* necessary). This is to avoid any corner cases.
|
||||
*
|
||||
*/
|
||||
#define MSC_PROGRAM_TIMEOUT 10000000ul
|
||||
|
||||
/*******************************************************************************
|
||||
************************* TYPEDEFS ****************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Return codes for writing/erasing the flash */
|
||||
typedef enum
|
||||
{
|
||||
mscReturnOk = 0, /**< Flash write/erase successful. */
|
||||
mscReturnInvalidAddr = -1, /**< Invalid address. Write to an address that is not flash. */
|
||||
mscReturnLocked = -2, /**< Flash address is locked. */
|
||||
mscReturnTimeOut = -3, /**< Timeout while writing to flash. */
|
||||
mscReturnUnaligned = -4 /**< Unaligned access to flash. */
|
||||
} msc_Return_TypeDef;
|
||||
|
||||
|
||||
#if defined (_EFM32_GIANT_FAMILY)
|
||||
/** Strategy for prioritized bus access */
|
||||
typedef enum {
|
||||
mscBusStrategyCPU = MSC_READCTRL_BUSSTRATEGY_CPU, /**< Prioritize CPU bus accesses */
|
||||
mscBusStrategyDMA = MSC_READCTRL_BUSSTRATEGY_DMA, /**< Prioritize DMA bus accesses */
|
||||
mscBusStrategyDMAEM2 = MSC_READCTRL_BUSSTRATEGY_DMAEM2, /**< Prioritize DMAEM2 for bus accesses */
|
||||
mscBusStrategyNone = MSC_READCTRL_BUSSTRATEGY_NONE /**< No unit has bus priority */
|
||||
} mscBusStrategy_Typedef;
|
||||
#endif
|
||||
|
||||
/*******************************************************************************
|
||||
************************* PROTOTYPES **************************************
|
||||
******************************************************************************/
|
||||
|
||||
void MSC_Deinit(void);
|
||||
void MSC_Init(void);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending MSC interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending MSC intterupt source to clear. Use a bitwise logic OR combination
|
||||
* of valid interrupt flags for the MSC module (MSC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void MSC_IntClear(uint32_t flags)
|
||||
{
|
||||
MSC->IFC = flags;
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more MSC interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* MSC interrupt sources to disable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the MSC module (MSC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void MSC_IntDisable(uint32_t flags)
|
||||
{
|
||||
MSC->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more MSC interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using MSC_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] flags
|
||||
* MSC interrupt sources to enable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the MSC module (MSC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void MSC_IntEnable(uint32_t flags)
|
||||
{
|
||||
MSC->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending MSV interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @return
|
||||
* MSC interrupt sources pending. A bitwise logic OR combination of valid
|
||||
* interrupt flags for the MSC module (MSC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t MSC_IntGet(void)
|
||||
{
|
||||
return(MSC->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending MSC interrupts from SW.
|
||||
*
|
||||
* @param[in] flags
|
||||
* MSC interrupt sources to set to pending. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the MSC module (MSC_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void MSC_IntSet(uint32_t flags)
|
||||
{
|
||||
MSC->IFS = flags;
|
||||
}
|
||||
|
||||
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Starts measuring cache hit ratio.
|
||||
* @details
|
||||
* This function starts the performance counters. It is defined inline to
|
||||
* minimize the impact of this code on the measurement itself.
|
||||
******************************************************************************/
|
||||
static __INLINE void MSC_StartCacheMeasurement(void)
|
||||
{
|
||||
/* Clear CMOF and CHOF to catch these later */
|
||||
MSC->IFC = MSC_IF_CHOF | MSC_IF_CMOF;
|
||||
|
||||
/* Start performance counters */
|
||||
MSC->CMD = MSC_CMD_STARTPC;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Stops measuring the hit rate.
|
||||
* @note
|
||||
* This function is defined inline to minimize the impact of this
|
||||
* code on the measurement itself.
|
||||
* This code only works for relatively short sections of code. If you wish
|
||||
* to measure longer sections of code you need to implement a IRQ Handler for
|
||||
* The CHOF and CMOF overflow interrupts. Theses overflows needs to be
|
||||
* counted and included in the total.
|
||||
* The functions can then be implemented as follows:
|
||||
* @verbatim
|
||||
* volatile uint32_t hitOverflows
|
||||
* volatile uint32_t missOverflows
|
||||
*
|
||||
* void MSC_IRQHandler(void)
|
||||
* {
|
||||
* uint32_t flags;
|
||||
* flags = MSC->IF;
|
||||
* if (flags & MSC_IF_CHOF)
|
||||
* {
|
||||
* MSC->IFC = MSC_IF_CHOF;
|
||||
* hitOverflows++;
|
||||
* }
|
||||
* if (flags & MSC_IF_CMOF)
|
||||
* {
|
||||
* MSC->IFC = MSC_IF_CMOF;
|
||||
* missOverflows++;
|
||||
* }
|
||||
* }
|
||||
*
|
||||
* void startPerformanceCounters(void)
|
||||
* {
|
||||
* hitOverflows = 0;
|
||||
* missOverflows = 0;
|
||||
*
|
||||
* MSC_IntEnable(MSC_IF_CHOF | MSC_IF_CMOF);
|
||||
* NVIC_EnableIRQ(MSC_IRQn);
|
||||
*
|
||||
* MSC_StartCacheMeasurement();
|
||||
* }
|
||||
* @endverbatim
|
||||
* @return
|
||||
* Returns -1 if there has been no cache accesses.
|
||||
* Returns -2 if there has been an overflow in the performance counters.
|
||||
* If not, it will return the percentage of hits versus misses.
|
||||
******************************************************************************/
|
||||
static __INLINE int32_t MSC_GetCacheMeasurement(void)
|
||||
{
|
||||
int32_t total;
|
||||
/* Stop the counter before computing the hit-rate */
|
||||
MSC->CMD = MSC_CMD_STOPPC;
|
||||
|
||||
/* Check for overflows in performance counters */
|
||||
if (MSC->IF & (MSC_IF_CHOF | MSC_IF_CMOF))
|
||||
return -2;
|
||||
|
||||
/* Because the hits and misses are volatile, we need to split this up into
|
||||
* two statements to avoid a compiler warning regarding the order of volatile
|
||||
* accesses. */
|
||||
total = MSC->CACHEHITS;
|
||||
total += MSC->CACHEMISSES;
|
||||
|
||||
/* To avoid a division by zero. */
|
||||
if (total == 0)
|
||||
return -1;
|
||||
|
||||
return (MSC->CACHEHITS * 100) / total;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Flush the contents of the instruction cache.
|
||||
******************************************************************************/
|
||||
static __INLINE void MSC_FlushCache(void)
|
||||
{
|
||||
MSC->CMD = MSC_CMD_INVCACHE;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable or disable instruction cache functionality
|
||||
* @param[in] enable
|
||||
* Enable instruction cache. Default is on.
|
||||
******************************************************************************/
|
||||
static __INLINE void MSC_EnableCache(bool enable)
|
||||
{
|
||||
BITBAND_Peripheral(&(MSC->READCTRL), _MSC_READCTRL_IFCDIS_SHIFT, ~enable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable or disable instruction cache functionality in IRQs
|
||||
* @param[in] enable
|
||||
* Enable instruction cache. Default is on.
|
||||
******************************************************************************/
|
||||
static __INLINE void MSC_EnableCacheIRQs(bool enable)
|
||||
{
|
||||
BITBAND_Peripheral(&(MSC->READCTRL), _MSC_READCTRL_ICCDIS_SHIFT, ~enable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable or disable instruction cache flushing when writing to flash
|
||||
* @param[in] enable
|
||||
* Enable automatic cache flushing. Default is on.
|
||||
******************************************************************************/
|
||||
static __INLINE void MSC_EnableAutoCacheFlush(bool enable)
|
||||
{
|
||||
BITBAND_Peripheral(&(MSC->READCTRL), _MSC_READCTRL_AIDIS_SHIFT, ~enable);
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure which unit should get priority on system bus.
|
||||
* @param[in] mode
|
||||
* Unit to prioritize bus accesses for.
|
||||
******************************************************************************/
|
||||
static __INLINE void MSC_BusStrategy(mscBusStrategy_Typedef mode)
|
||||
{
|
||||
MSC->READCTRL = (MSC->READCTRL & ~(_MSC_READCTRL_BUSSTRATEGY_MASK))|mode;
|
||||
}
|
||||
#endif
|
||||
|
||||
#ifdef __CC_ARM /* MDK-ARM compiler */
|
||||
msc_Return_TypeDef MSC_WriteWord(uint32_t *address, void const *data, int numBytes);
|
||||
msc_Return_TypeDef MSC_ErasePage(uint32_t *startAddress);
|
||||
#if defined (_EFM32_GIANT_FAMILY)
|
||||
msc_Return_TypeDef MSC_MassErase(void);
|
||||
#endif
|
||||
#endif /* __CC_ARM */
|
||||
|
||||
#ifdef __ICCARM__ /* IAR compiler */
|
||||
__ramfunc msc_Return_TypeDef MSC_WriteWord(uint32_t *address, void const *data, int numBytes);
|
||||
__ramfunc msc_Return_TypeDef MSC_ErasePage(uint32_t *startAddress);
|
||||
#if defined (_EFM32_GIANT_FAMILY)
|
||||
__ramfunc msc_Return_TypeDef MSC_MassErase(void);
|
||||
#endif
|
||||
#endif /* __ICCARM__ */
|
||||
|
||||
#ifdef __GNUC__ /* GCC based compilers */
|
||||
#ifdef __CROSSWORKS_ARM /* Rowley Crossworks */
|
||||
msc_Return_TypeDef MSC_WriteWord(uint32_t *address, void const *data, int numBytes) __attribute__ ((section(".fast")));
|
||||
msc_Return_TypeDef MSC_ErasePage(uint32_t *startAddress) __attribute__ ((section(".fast")));
|
||||
#if defined (_EFM32_GIANT_FAMILY)
|
||||
msc_Return_TypeDef MSC_MassErase(void) __attribute__ ((section(".fast")));
|
||||
#endif
|
||||
#else /* Sourcery G++ */
|
||||
msc_Return_TypeDef MSC_WriteWord(uint32_t *address, void const *data, int numBytes) __attribute__ ((section(".ram")));
|
||||
msc_Return_TypeDef MSC_ErasePage(uint32_t *startAddress) __attribute__ ((section(".ram")));
|
||||
#if defined (_EFM32_GIANT_FAMILY)
|
||||
msc_Return_TypeDef MSC_MassErase(void) __attribute__ ((section(".ram")));
|
||||
#endif
|
||||
|
||||
#endif /* __GNUC__ */
|
||||
#endif /* __CROSSWORKS_ARM */
|
||||
|
||||
/** @} (end addtogroup MSC) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_MSC_H */
|
|
@ -0,0 +1,538 @@
|
|||
/**************************************************************************//**
|
||||
* @file
|
||||
* @brief Operational Amplifier (OPAMP) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2011 Energy Micro AS, http://www.energymicro.com</b>
|
||||
******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
*****************************************************************************/
|
||||
#ifndef __EFM32_OPAMP_H
|
||||
#define __EFM32_OPAMP_H
|
||||
|
||||
#include "efm32.h"
|
||||
#if defined(OPAMP_PRESENT) && (OPAMP_COUNT == 1)
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
#include "efm32_dac.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup OPAMP
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/** Validation of DAC OPA number for assert statements. */
|
||||
#define DAC_OPA_VALID(opa) ((opa) <= OPA2)
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** OPAMP selector values. */
|
||||
typedef enum
|
||||
{
|
||||
OPA0 = 0, /**< Select OPA0. */
|
||||
OPA1 = 1, /**< Select OPA1. */
|
||||
OPA2 = 2 /**< Select OPA2. */
|
||||
} OPAMP_TypeDef;
|
||||
|
||||
/** OPAMP negative terminal input selection values. */
|
||||
typedef enum
|
||||
{
|
||||
opaNegSelDisable = DAC_OPA0MUX_NEGSEL_DISABLE, /**< Input disabled. */
|
||||
opaNegSelUnityGain = DAC_OPA0MUX_NEGSEL_UG, /**< Unity gain feedback path. */
|
||||
opaNegSelResTap = DAC_OPA0MUX_NEGSEL_OPATAP, /**< Feedback resistor ladder tap. */
|
||||
opaNegSelNegPad = DAC_OPA0MUX_NEGSEL_NEGPAD /**< Negative pad as input. */
|
||||
} OPAMP_NegSel_TypeDef;
|
||||
|
||||
/** OPAMP positive terminal input selection values. */
|
||||
typedef enum
|
||||
{
|
||||
opaPosSelDisable = DAC_OPA0MUX_POSSEL_DISABLE, /**< Input disabled. */
|
||||
opaPosSelDac = DAC_OPA0MUX_POSSEL_DAC, /**< DAC as input (not OPA2). */
|
||||
opaPosSelPosPad = DAC_OPA0MUX_POSSEL_POSPAD, /**< Positive pad as input. */
|
||||
opaPosSelOpaIn = DAC_OPA0MUX_POSSEL_OPA0INP, /**< Input from OPAx. */
|
||||
opaPosSelResTapOpa0 = DAC_OPA0MUX_POSSEL_OPATAP /**< Feedback resistor ladder tap from OPA0. */
|
||||
} OPAMP_PosSel_TypeDef;
|
||||
|
||||
/** OPAMP output terminal selection values. */
|
||||
typedef enum
|
||||
{
|
||||
opaOutModeDisable = DAC_OPA0MUX_OUTMODE_DISABLE, /**< OPA output disabled. */
|
||||
opaOutModeMain = DAC_OPA0MUX_OUTMODE_MAIN, /**< Main output to pin enabled. */
|
||||
opaOutModeAlt = DAC_OPA0MUX_OUTMODE_ALT, /**< Alternate output(s) enabled (not OPA2). */
|
||||
opaOutModeAll = DAC_OPA0MUX_OUTMODE_ALL /**< Both main and alternate enabled (not OPA2). */
|
||||
} OPAMP_OutMode_TypeDef;
|
||||
|
||||
/** OPAMP gain values. */
|
||||
typedef enum
|
||||
{
|
||||
opaResSelDefault = DAC_OPA0MUX_RESSEL_DEFAULT, /**< Default value when resistor ladder is unused. */
|
||||
opaResSelR2eq0_33R1 = DAC_OPA0MUX_RESSEL_RES0, /**< R2 = 0.33 * R1 */
|
||||
opaResSelR2eqR1 = DAC_OPA0MUX_RESSEL_RES1, /**< R2 = R1 */
|
||||
opaResSelR1eq1_67R1 = DAC_OPA0MUX_RESSEL_RES2, /**< R2 = 1.67 R1 */
|
||||
opaResSelR2eq2R1 = DAC_OPA0MUX_RESSEL_RES3, /**< R2 = 2 * R1 */
|
||||
opaResSelR2eq3R1 = DAC_OPA0MUX_RESSEL_RES4, /**< R2 = 3 * R1 */
|
||||
opaResSelR2eq4_33R1 = DAC_OPA0MUX_RESSEL_RES5, /**< R2 = 4.33 * R1 */
|
||||
opaResSelR2eq7R1 = DAC_OPA0MUX_RESSEL_RES6, /**< R2 = 7 * R1 */
|
||||
opaResSelR2eq15R1 = DAC_OPA0MUX_RESSEL_RES7 /**< R2 = 15 * R1 */
|
||||
} OPAMP_ResSel_TypeDef;
|
||||
|
||||
/** OPAMP resistor ladder input selector values. */
|
||||
typedef enum
|
||||
{
|
||||
opaResInMuxDisable = DAC_OPA0MUX_RESINMUX_DISABLE, /**< Resistor ladder disabled. */
|
||||
opaResInMuxOpaIn = DAC_OPA0MUX_RESINMUX_OPA0INP, /**< Input from OPAx. */
|
||||
opaResInMuxNegPad = DAC_OPA0MUX_RESINMUX_NEGPAD, /**< Input from negative pad. */
|
||||
opaResInMuxPosPad = DAC_OPA0MUX_RESINMUX_POSPAD, /**< Input from positive pad. */
|
||||
opaResInMuxVss = DAC_OPA0MUX_RESINMUX_VSS /**< Input connected to Vss. */
|
||||
} OPAMP_ResInMux_TypeDef;
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** OPAMP init structure. */
|
||||
typedef struct
|
||||
{
|
||||
OPAMP_NegSel_TypeDef negSel; /**< Select input source for negative terminal. */
|
||||
OPAMP_PosSel_TypeDef posSel; /**< Select input source for positive terminal. */
|
||||
OPAMP_OutMode_TypeDef outMode; /**< Output terminal connection. */
|
||||
OPAMP_ResSel_TypeDef resSel; /**< Select R2/R1 resistor ratio. */
|
||||
OPAMP_ResInMux_TypeDef resInMux; /**< Select input source for resistor ladder. */
|
||||
uint32_t outPen; /**< Select alternate output terminal connections. */
|
||||
uint32_t bias; /**< Set OPAMP bias current. */
|
||||
bool halfBias; /**< Divide OPAMP bias current by 2. */
|
||||
bool lpfPosPadDisable; /**< Disable low pass filter on positive pad. */
|
||||
bool lpfNegPadDisable; /**< Disable low pass filter on negative pad. */
|
||||
bool nextOut; /**< Enable NEXTOUT signal source. */
|
||||
bool npEn; /**< Enable positive pad. */
|
||||
bool ppEn; /**< Enable negative pad. */
|
||||
bool shortInputs; /**< Short OPAMP input terminals. */
|
||||
bool hcmDisable; /**< Disable input rail-to-rail capability. */
|
||||
bool defaultOffset; /**< Use factory calibrated opamp offset value. */
|
||||
uint32_t offset; /**< Opamp offset value when @ref defaultOffset is false.*/
|
||||
} OPAMP_Init_TypeDef;
|
||||
|
||||
/** Configuration of OPA0/1 in unity gain voltage follower mode. */
|
||||
#define OPA_INIT_UNITY_GAIN \
|
||||
{ \
|
||||
opaNegSelUnityGain, /* Unity gain. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeMain, /* Main output enabled. */ \
|
||||
opaResSelDefault, /* Resistor ladder is not used. */ \
|
||||
opaResInMuxDisable, /* Resistor ladder disabled. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
false, /* No nextout output enabled. */ \
|
||||
false, /* Neg pad disabled. */ \
|
||||
true, /* Pos pad enabled, used as signal input. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA2 in unity gain voltage follower mode. */
|
||||
#define OPA_INIT_UNITY_GAIN_OPA2 \
|
||||
{ \
|
||||
opaNegSelUnityGain, /* Unity gain. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeMain, /* Main output enabled. */ \
|
||||
opaResSelDefault, /* Resistor ladder is not used. */ \
|
||||
opaResInMuxDisable, /* Resistor ladder disabled. */ \
|
||||
DAC_OPA0MUX_OUTPEN_OUT0, /* Alternate output 0 enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
false, /* No nextout output enabled. */ \
|
||||
false, /* Neg pad disabled. */ \
|
||||
true, /* Pos pad enabled, used as signal input. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA0/1 in non-inverting amplifier mode. */
|
||||
#define OPA_INIT_NON_INVERTING \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeMain, /* Main output enabled. */ \
|
||||
opaResSelR2eq0_33R1, /* R2 = 1/3 R1 */ \
|
||||
opaResInMuxNegPad, /* Resistor ladder input from neg pad. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
false, /* No nextout output enabled. */ \
|
||||
true, /* Neg pad enabled, used as signal ground. */ \
|
||||
true, /* Pos pad enabled, used as signal input. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA2 in non-inverting amplifier mode. */
|
||||
#define OPA_INIT_NON_INVERTING_OPA2 \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeMain, /* Main output enabled. */ \
|
||||
opaResSelR2eq0_33R1, /* R2 = 1/3 R1 */ \
|
||||
opaResInMuxNegPad, /* Resistor ladder input from neg pad. */ \
|
||||
DAC_OPA0MUX_OUTPEN_OUT0, /* Alternate output 0 enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
false, /* No nextout output enabled. */ \
|
||||
true, /* Neg pad enabled, used as signal ground. */ \
|
||||
true, /* Pos pad enabled, used as signal input. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA0/1 in inverting amplifier mode. */
|
||||
#define OPA_INIT_INVERTING \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeMain, /* Main output enabled. */ \
|
||||
opaResSelR2eqR1, /* R2 = R1 */ \
|
||||
opaResInMuxNegPad, /* Resistor ladder input from neg pad. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
false, /* No nextout output enabled. */ \
|
||||
true, /* Neg pad enabled, used as signal input. */ \
|
||||
true, /* Pos pad enabled, used as signal ground. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA2 in inverting amplifier mode. */
|
||||
#define OPA_INIT_INVERTING_OPA2 \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeMain, /* Main output enabled. */ \
|
||||
opaResSelR2eqR1, /* R2 = R1 */ \
|
||||
opaResInMuxNegPad, /* Resistor ladder input from neg pad. */ \
|
||||
DAC_OPA0MUX_OUTPEN_OUT0, /* Alternate output 0 enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
false, /* No nextout output enabled. */ \
|
||||
true, /* Neg pad enabled, used as signal input. */ \
|
||||
true, /* Pos pad enabled, used as signal ground. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA0 in cascaded non-inverting amplifier mode. */
|
||||
#define OPA_INIT_CASCADED_NON_INVERTING_OPA0 \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeAll, /* Both main and alternate outputs. */ \
|
||||
opaResSelR2eq0_33R1, /* R2 = 1/3 R1 */ \
|
||||
opaResInMuxNegPad, /* Resistor ladder input from neg pad. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
true, /* Pass output to next stage (OPA1). */ \
|
||||
true, /* Neg pad enabled, used as signal ground. */ \
|
||||
true, /* Pos pad enabled, used as signal input. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA1 in cascaded non-inverting amplifier mode. */
|
||||
#define OPA_INIT_CASCADED_NON_INVERTING_OPA1 \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelOpaIn, /* Pos input from OPA0 output. */ \
|
||||
opaOutModeAll, /* Both main and alternate outputs. */ \
|
||||
opaResSelR2eq0_33R1, /* R2 = 1/3 R1 */ \
|
||||
opaResInMuxNegPad, /* Resistor ladder input from neg pad. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
true, /* Pass output to next stage (OPA2). */ \
|
||||
true, /* Neg pad enabled, used as signal ground. */ \
|
||||
false, /* Pos pad disabled. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA2 in cascaded non-inverting amplifier mode. */
|
||||
#define OPA_INIT_CASCADED_NON_INVERTING_OPA2 \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelOpaIn, /* Pos input from OPA1 output. */ \
|
||||
opaOutModeMain, /* Main output enabled. */ \
|
||||
opaResSelR2eq0_33R1, /* R2 = 1/3 R1 */ \
|
||||
opaResInMuxNegPad, /* Resistor ladder input from neg pad. */ \
|
||||
DAC_OPA0MUX_OUTPEN_OUT0, /* Alternate output 0 enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
false, /* No nextout output enabled. */ \
|
||||
true, /* Neg pad enabled, used as signal ground. */ \
|
||||
false, /* Pos pad disabled. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA0 in cascaded inverting amplifier mode. */
|
||||
#define OPA_INIT_CASCADED_INVERTING_OPA0 \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeAll, /* Both main and alternate outputs. */ \
|
||||
opaResSelR2eqR1, /* R2 = R1 */ \
|
||||
opaResInMuxNegPad, /* Resistor ladder input from neg pad. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
true, /* Pass output to next stage (OPA1). */ \
|
||||
true, /* Neg pad enabled, used as signal input. */ \
|
||||
true, /* Pos pad enabled, used as signal ground. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA1 in cascaded inverting amplifier mode. */
|
||||
#define OPA_INIT_CASCADED_INVERTING_OPA1 \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeAll, /* Both main and alternate outputs. */ \
|
||||
opaResSelR2eqR1, /* R2 = R1 */ \
|
||||
opaResInMuxOpaIn, /* Resistor ladder input from OPA0. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
true, /* Pass output to next stage (OPA2). */ \
|
||||
false, /* Neg pad disabled. */ \
|
||||
true, /* Pos pad enabled, used as signal ground. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA2 in cascaded inverting amplifier mode. */
|
||||
#define OPA_INIT_CASCADED_INVERTING_OPA2 \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeMain, /* Main output enabled. */ \
|
||||
opaResSelR2eqR1, /* R2 = R1 */ \
|
||||
opaResInMuxOpaIn, /* Resistor ladder input from OPA1. */ \
|
||||
DAC_OPA0MUX_OUTPEN_OUT0, /* Alternate output 0 enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
false, /* No nextout output enabled. */ \
|
||||
false, /* Neg pad disabled. */ \
|
||||
true, /* Pos pad enabled, used as signal ground. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA0 in two-opamp differential driver mode. */
|
||||
#define OPA_INIT_DIFF_DRIVER_OPA0 \
|
||||
{ \
|
||||
opaNegSelUnityGain, /* Unity gain. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeAll, /* Both main and alternate outputs. */ \
|
||||
opaResSelDefault, /* Resistor ladder is not used. */ \
|
||||
opaResInMuxDisable, /* Resistor ladder disabled. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
true, /* Pass output to next stage (OPA1). */ \
|
||||
false, /* Neg pad disabled. */ \
|
||||
true, /* Pos pad enabled, used as signal input. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA1 in two-opamp differential driver mode. */
|
||||
#define OPA_INIT_DIFF_DRIVER_OPA1 \
|
||||
{ \
|
||||
opaNegSelResTap, /* Neg input from resistor ladder tap. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeMain, /* Main output enabled. */ \
|
||||
opaResSelR2eqR1, /* R2 = R1 */ \
|
||||
opaResInMuxOpaIn, /* Resistor ladder input from OPA0. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
false, /* No nextout output enabled. */ \
|
||||
false, /* Neg pad disabled. */ \
|
||||
true, /* Pos pad enabled, used as signal ground. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA0 in three-opamp differential receiver mode. */
|
||||
#define OPA_INIT_DIFF_RECEIVER_OPA0 \
|
||||
{ \
|
||||
opaNegSelUnityGain, /* Unity gain. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeAll, /* Both main and alternate outputs. */ \
|
||||
opaResSelR2eqR1, /* R2 = R1 */ \
|
||||
opaResInMuxNegPad, /* Resistor ladder input from neg pad. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
true, /* Pass output to next stage (OPA2). */ \
|
||||
true, /* Neg pad enabled, used as signal ground. */ \
|
||||
true, /* Pos pad enabled, used as signal input. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA1 in three-opamp differential receiver mode. */
|
||||
#define OPA_INIT_DIFF_RECEIVER_OPA1 \
|
||||
{ \
|
||||
opaNegSelUnityGain, /* Unity gain. */ \
|
||||
opaPosSelPosPad, /* Pos input from pad. */ \
|
||||
opaOutModeAll, /* Both main and alternate outputs. */ \
|
||||
opaResSelDefault, /* Resistor ladder is not used. */ \
|
||||
opaResInMuxDisable, /* Disable resistor ladder. */ \
|
||||
0, /* No alternate outputs enabled. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
true, /* Pass output to next stage (OPA2). */ \
|
||||
false, /* Neg pad disabled. */ \
|
||||
true, /* Pos pad enabled, used as signal input. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/** Configuration of OPA2 in three-opamp differential receiver mode. */
|
||||
#define OPA_INIT_DIFF_RECEIVER_OPA2 \
|
||||
{ \
|
||||
opaNegSelResTap, /* Input from resistor ladder tap. */ \
|
||||
opaPosSelResTapOpa0, /* Input from OPA0 resistor ladder tap. */ \
|
||||
opaOutModeMain, /* Main output enabled. */ \
|
||||
opaResSelR2eqR1, /* R2 = R1 */ \
|
||||
opaResInMuxOpaIn, /* Resistor ladder input from OPA1. */ \
|
||||
DAC_OPA0MUX_OUTPEN_OUT0, /* Enable alternate output 0. */ \
|
||||
_DAC_BIASPROG_BIASPROG_DEFAULT, /* Default bias setting. */ \
|
||||
_DAC_BIASPROG_HALFBIAS_DEFAULT, /* Default half-bias setting. */ \
|
||||
false, /* No low pass filter on pos pad. */ \
|
||||
false, /* No low pass filter on neg pad. */ \
|
||||
false, /* No nextout output enabled. */ \
|
||||
false, /* Neg pad disabled. */ \
|
||||
false, /* Pos pad disabled. */ \
|
||||
false, /* No shorting of inputs. */ \
|
||||
false, /* Rail-to-rail input enabled. */ \
|
||||
true, /* Use factory calibrated opamp offset. */ \
|
||||
0 /* Opamp offset value (not used). */ \
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void OPAMP_Disable(DAC_TypeDef *dac, OPAMP_TypeDef opa);
|
||||
void OPAMP_Enable(DAC_TypeDef *dac, OPAMP_TypeDef opa, const OPAMP_Init_TypeDef *init);
|
||||
|
||||
/** @} (end addtogroup OPAMP) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* defined( OPAMP_PRESENT ) && ( OPAMP_COUNT == 1 ) */
|
||||
#endif /* __EFM32_DAC_H */
|
|
@ -0,0 +1,454 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Pulse Counter (PCNT) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_PCNT_H
|
||||
#define __EFM32_PCNT_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup PCNT
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Mode selection. */
|
||||
typedef enum
|
||||
{
|
||||
/** Disable pulse counter. */
|
||||
pcntModeDisable = _PCNT_CTRL_MODE_DISABLE,
|
||||
|
||||
/** Single input LFACLK oversampling mode (available in EM0-EM2). */
|
||||
pcntModeOvsSingle = _PCNT_CTRL_MODE_OVSSINGLE,
|
||||
|
||||
/** Externally clocked single input counter mode (available in EM0-EM3). */
|
||||
pcntModeExtSingle = _PCNT_CTRL_MODE_EXTCLKSINGLE,
|
||||
|
||||
/** Externally clocked quadrature decoder mode (available in EM0-EM3). */
|
||||
pcntModeExtQuad = _PCNT_CTRL_MODE_EXTCLKQUAD
|
||||
} PCNT_Mode_TypeDef;
|
||||
|
||||
|
||||
#if (defined (_EFM32_TINY_FAMILY) || defined (_EFM32_GIANT_FAMILY))
|
||||
/** Counter event selection.
|
||||
* Note: unshifted values are being used for enumeration because multiple
|
||||
* configuration structure members use this type definition. */
|
||||
typedef enum
|
||||
{
|
||||
/** Counts up on up-count and down on down-count events. */
|
||||
pcntCntEventBoth = _PCNT_CTRL_CNTEV_BOTH,
|
||||
|
||||
/** Only counts up on up-count events. */
|
||||
pcntCntEventUp = _PCNT_CTRL_CNTEV_UP,
|
||||
|
||||
/** Only counts down on down-count events. */
|
||||
pcntCntEventDown = _PCNT_CTRL_CNTEV_DOWN,
|
||||
|
||||
/** Never counts. */
|
||||
pcntCntEventNone = _PCNT_CTRL_CNTEV_NONE
|
||||
} PCNT_CntEvent_TypeDef;
|
||||
|
||||
|
||||
/** PRS sources for @p s0PRS and @p s1PRS. */
|
||||
typedef enum
|
||||
{
|
||||
pcntPRSCh0 = 0, /**< PRS channel 0. */
|
||||
pcntPRSCh1 = 1, /**< PRS channel 1. */
|
||||
pcntPRSCh2 = 2, /**< PRS channel 2. */
|
||||
pcntPRSCh3 = 3, /**< PRS channel 3. */
|
||||
pcntPRSCh4 = 4, /**< PRS channel 4. */
|
||||
pcntPRSCh5 = 5, /**< PRS channel 5. */
|
||||
pcntPRSCh6 = 6, /**< PRS channel 6. */
|
||||
pcntPRSCh7 = 7 /**< PRS channel 7. */
|
||||
} PCNT_PRSSel_TypeDef;
|
||||
|
||||
|
||||
/** PRS inputs of PCNT. */
|
||||
typedef enum
|
||||
{
|
||||
pcntPRSInputS0 = 0, /** PRS input 0. */
|
||||
pcntPRSInputS1 = 1 /** PRS input 1. */
|
||||
} PCNT_PRSInput_TypeDef;
|
||||
#endif
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Init structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Mode to operate in. */
|
||||
PCNT_Mode_TypeDef mode;
|
||||
|
||||
/** Initial counter value (refer to reference manual for max value allowed).
|
||||
* Only used for #pcntModeOvsSingle (and possibly #pcntModeDisable) modes.
|
||||
* If using #pcntModeExtSingle or #pcntModeExtQuad modes, the counter
|
||||
* value is reset to HW reset value. */
|
||||
uint32_t counter;
|
||||
|
||||
/** Initial top value (refer to reference manual for max value allowed).
|
||||
* Only used for #pcntModeOvsSingle (and possibly #pcntModeDisable) modes.
|
||||
* If using #pcntModeExtSingle or #pcntModeExtQuad modes, the top
|
||||
* value is reset to HW reset value. */
|
||||
uint32_t top;
|
||||
|
||||
/** Polarity of incoming edge.
|
||||
* @li #pcntModeExtSingle mode - if false, positive edges are counted,
|
||||
* otherwise negative edges.
|
||||
* @li #pcntModeExtQuad mode - if true, counting direction is inverted. */
|
||||
bool negEdge;
|
||||
|
||||
/** Counting direction, only applicable for #pcntModeOvsSingle and
|
||||
* #pcntModeExtSingle modes. */
|
||||
bool countDown;
|
||||
|
||||
/** Enable filter, only available in #pcntModeOvsSingle mode. */
|
||||
bool filter;
|
||||
|
||||
#if (defined (_EFM32_TINY_FAMILY) || defined (_EFM32_GIANT_FAMILY))
|
||||
/** Set to true to enable hysteresis. When its enabled, the PCNT will always
|
||||
* overflow and underflow to TOP/2. */
|
||||
bool hyst;
|
||||
|
||||
/** Set to true to enable S1 to determine the direction of counting in
|
||||
* OVSSINGLE or EXTCLKSINGLE modes.
|
||||
* When S1 is high, the count direction is given by CNTDIR, and when S1 is
|
||||
* low, the count direction is the opposite. */
|
||||
bool s1CntDir;
|
||||
|
||||
/** Selects whether the regular counter responds to up-count events,
|
||||
* down-count events, both or none. */
|
||||
PCNT_CntEvent_TypeDef cntEvent;
|
||||
|
||||
/** Selects whether the auxiliary counter responds to up-count events,
|
||||
* down-count events, both or none. */
|
||||
PCNT_CntEvent_TypeDef auxCntEvent;
|
||||
|
||||
/** Select PRS channel as input to S0IN in PCNTx_INPUT register. */
|
||||
PCNT_PRSSel_TypeDef s0PRS;
|
||||
|
||||
/** Select PRS channel as input to S1IN in PCNTx_INPUT register. */
|
||||
PCNT_PRSSel_TypeDef s1PRS;
|
||||
#endif
|
||||
} PCNT_Init_TypeDef;
|
||||
|
||||
/** Default config for PCNT init structure. */
|
||||
#if defined (_EFM32_GECKO_FAMILY)
|
||||
#define PCNT_INIT_DEFAULT \
|
||||
{ pcntModeDisable, /* Disabled by default. */ \
|
||||
_PCNT_CNT_RESETVALUE, /* Default counter HW reset value. */ \
|
||||
_PCNT_TOP_RESETVALUE, /* Default counter HW reset value. */ \
|
||||
false, /* Use positive edge. */ \
|
||||
false, /* Up-counting. */ \
|
||||
false /* Filter disabled. */ \
|
||||
}
|
||||
#elif (defined (_EFM32_TINY_FAMILY) || defined (_EFM32_GIANT_FAMILY))
|
||||
#define PCNT_INIT_DEFAULT \
|
||||
{ pcntModeDisable, /* Disabled by default. */ \
|
||||
_PCNT_CNT_RESETVALUE, /* Default counter HW reset value. */ \
|
||||
_PCNT_TOP_RESETVALUE, /* Default counter HW reset value. */ \
|
||||
false, /* Use positive edge. */ \
|
||||
false, /* Up-counting. */ \
|
||||
false, /* Filter disabled. */ \
|
||||
false, /* Hysteresis disabled. */ \
|
||||
true, /* Counter direction is given by CNTDIR. */ \
|
||||
pcntCntEventUp, /* Regular counter counts up on upcount events. */ \
|
||||
pcntCntEventNone, /* Auxiliary counter doesn't respond to events. */ \
|
||||
pcntPRSCh0, /* PRS channel 0 selected as S0IN. */ \
|
||||
pcntPRSCh0 /* PRS channel 0 selected as S1IN. */ \
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pulse counter value.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Current pulse counter value.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t PCNT_CounterGet(PCNT_TypeDef *pcnt)
|
||||
{
|
||||
return pcnt->CNT;
|
||||
}
|
||||
|
||||
|
||||
#if (defined (_EFM32_TINY_FAMILY) || defined (_EFM32_GIANT_FAMILY))
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get auxiliary counter value.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Current auxiliary counter value.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t PCNT_AuxCounterGet(PCNT_TypeDef *pcnt)
|
||||
{
|
||||
return pcnt->AUXCNT;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
void PCNT_CounterReset(PCNT_TypeDef *pcnt);
|
||||
void PCNT_CounterTopSet(PCNT_TypeDef *pcnt, uint32_t count, uint32_t top);
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set counter value.
|
||||
*
|
||||
* @details
|
||||
* The pulse counter is disabled while changing counter value, and reenabled
|
||||
* (if originally enabled) when counter value has been set.
|
||||
*
|
||||
* @note
|
||||
* This function will stall until synchronization to low frequency domain is
|
||||
* completed. For that reason, it should normally not be used when using
|
||||
* an external clock to clock the PCNT module, since stall time may be
|
||||
* undefined in that case. The counter should normally only be set when
|
||||
* operating in (or about to enable) #pcntModeOvsSingle mode.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] count
|
||||
* Value to set in counter register.
|
||||
******************************************************************************/
|
||||
static __INLINE void PCNT_CounterSet(PCNT_TypeDef *pcnt, uint32_t count)
|
||||
{
|
||||
PCNT_CounterTopSet(pcnt, count, pcnt->TOP);
|
||||
}
|
||||
|
||||
|
||||
void PCNT_Enable(PCNT_TypeDef *pcnt, PCNT_Mode_TypeDef mode);
|
||||
void PCNT_FreezeEnable(PCNT_TypeDef *pcnt, bool enable);
|
||||
void PCNT_Init(PCNT_TypeDef *pcnt, const PCNT_Init_TypeDef *init);
|
||||
|
||||
#if (defined (_EFM32_TINY_FAMILY) || defined (_EFM32_GIANT_FAMILY))
|
||||
void PCNT_PRSInputEnable(PCNT_TypeDef *pcnt,
|
||||
PCNT_PRSInput_TypeDef prsInput,
|
||||
bool enable);
|
||||
#endif
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending PCNT interrupts.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending PCNT interrupt source to clear. Use a bitwise logic OR combination
|
||||
* of valid interrupt flags for the PCNT module (PCNT_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void PCNT_IntClear(PCNT_TypeDef *pcnt, uint32_t flags)
|
||||
{
|
||||
pcnt->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more PCNT interrupts.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* PCNT interrupt sources to disable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the PCNT module (PCNT_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void PCNT_IntDisable(PCNT_TypeDef *pcnt, uint32_t flags)
|
||||
{
|
||||
pcnt->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more PCNT interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using PCNT_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* PCNT interrupt sources to enable. Use a bitwise logic OR combination of
|
||||
* valid interrupt flags for the PCNT module (PCNT_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void PCNT_IntEnable(PCNT_TypeDef *pcnt, uint32_t flags)
|
||||
{
|
||||
pcnt->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending PCNT interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* PCNT interrupt sources pending. A bitwise logic OR combination of valid
|
||||
* interrupt flags for the PCNT module (PCNT_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t PCNT_IntGet(PCNT_TypeDef *pcnt)
|
||||
{
|
||||
return pcnt->IF;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get enabled and pending PCNT interrupt flags.
|
||||
*
|
||||
* @details
|
||||
* Useful for handling more interrupt sources in the same interrupt handler.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Pending and enabled PCNT interrupt sources.
|
||||
* The return value is the bitwise AND combination of
|
||||
* - the OR combination of enabled interrupt sources in PCNT_IEN_nnn
|
||||
* register (PCNT_IEN_nnn) and
|
||||
* - the OR combination of valid interrupt flags of the PCNT module
|
||||
* (PCNT_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t PCNT_IntGetEnabled(PCNT_TypeDef *pcnt)
|
||||
{
|
||||
uint32_t tmp = 0U;
|
||||
|
||||
|
||||
/* Store pcnt->IEN in temporary variable in order to define explicit order
|
||||
* of volatile accesses. */
|
||||
tmp = pcnt->IEN;
|
||||
|
||||
/* Bitwise AND of pending and enabled interrupts */
|
||||
return pcnt->IF & tmp;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending PCNT interrupts from SW.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* PCNT interrupt sources to set to pending. Use a bitwise logic OR combination
|
||||
* of valid interrupt flags for the PCNT module (PCNT_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void PCNT_IntSet(PCNT_TypeDef *pcnt, uint32_t flags)
|
||||
{
|
||||
pcnt->IFS = flags;
|
||||
}
|
||||
|
||||
void PCNT_Reset(PCNT_TypeDef *pcnt);
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pulse counter top buffer value.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Current pulse counter top buffer value.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t PCNT_TopBufferGet(PCNT_TypeDef *pcnt)
|
||||
{
|
||||
return pcnt->TOPB;
|
||||
}
|
||||
|
||||
void PCNT_TopBufferSet(PCNT_TypeDef *pcnt, uint32_t val);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pulse counter top value.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Current pulse counter top value.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t PCNT_TopGet(PCNT_TypeDef *pcnt)
|
||||
{
|
||||
return pcnt->TOP;
|
||||
}
|
||||
|
||||
void PCNT_TopSet(PCNT_TypeDef *pcnt, uint32_t val);
|
||||
|
||||
|
||||
/** @} (end addtogroup PCNT) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_PCNT_H */
|
|
@ -0,0 +1,123 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Peripheral Reflex System (PRS) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_PRS_H
|
||||
#define __EFM32_PRS_H
|
||||
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup PRS
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Edge detection type. */
|
||||
typedef enum
|
||||
{
|
||||
prsEdgeOff = PRS_CH_CTRL_EDSEL_OFF, /**< Leave signal as is. */
|
||||
prsEdgePos = PRS_CH_CTRL_EDSEL_POSEDGE, /**< Generate pules on positive edge. */
|
||||
prsEdgeNeg = PRS_CH_CTRL_EDSEL_NEGEDGE, /**< Generate pules on negative edge. */
|
||||
prsEdgeBoth = PRS_CH_CTRL_EDSEL_BOTHEDGES /**< Generate pules on both edges. */
|
||||
} PRS_Edge_TypeDef;
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set level control bit for one or more channels.
|
||||
*
|
||||
* @details
|
||||
* The level value for a channel is XORed with both the pulse possible issued
|
||||
* by PRS_PulseTrigger() and the PRS input signal selected for the channel(s).
|
||||
*
|
||||
* @param[in] level
|
||||
* Level to use for channels indicated by @p mask. Use logical OR combination
|
||||
* of PRS_SWLEVEL_CHnLEVEL defines for channels to set high level, otherwise 0.
|
||||
*
|
||||
* @param[in] mask
|
||||
* Mask indicating which channels to set level for. Use logical OR combination
|
||||
* of PRS_SWLEVEL_CHnLEVEL defines.
|
||||
******************************************************************************/
|
||||
static __INLINE void PRS_LevelSet(uint32_t level, uint32_t mask)
|
||||
{
|
||||
PRS->SWLEVEL = (PRS->SWLEVEL & ~mask) | (level & mask);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Trigger a high pulse (one HFPERCLK) for one or more channels.
|
||||
*
|
||||
* @details
|
||||
* Setting a bit for a channel causes the bit in the register to remain high
|
||||
* for one HFPERCLK cycle. The pulse is XORed with both the corresponding bit
|
||||
* in PRS SWLEVEL register and the PRS input signal selected for the
|
||||
* channel(s).
|
||||
*
|
||||
* @param[in] channels
|
||||
* Logical ORed combination of channels to trigger a pulse for. Use
|
||||
* PRS_SWPULSE_CHnPULSE defines.
|
||||
******************************************************************************/
|
||||
static __INLINE void PRS_PulseTrigger(uint32_t channels)
|
||||
{
|
||||
PRS->SWPULSE = channels & _PRS_SWPULSE_MASK;
|
||||
}
|
||||
|
||||
void PRS_SourceSignalSet(unsigned int ch,
|
||||
uint32_t source,
|
||||
uint32_t signal,
|
||||
PRS_Edge_TypeDef edge);
|
||||
|
||||
#if ((defined _EFM32_TINY_FAMILY) || (defined _EFM32_GIANT_FAMILY))
|
||||
void PRS_SourceAsyncSignalSet(unsigned int ch,
|
||||
uint32_t source,
|
||||
uint32_t signal);
|
||||
#endif
|
||||
|
||||
/** @} (end addtogroup PRS) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_PRS_H */
|
|
@ -0,0 +1,63 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Reset Management Unit (RMU) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_RMU_H
|
||||
#define __EFM32_RMU_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup RMU
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void RMU_LockupResetDisable(bool disable);
|
||||
void RMU_ResetCauseClear(void);
|
||||
uint32_t RMU_ResetCauseGet(void);
|
||||
|
||||
/** @} (end addtogroup RMU) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_RMU_H */
|
|
@ -0,0 +1,182 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Real Time Counter (RTC) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_RTC_H
|
||||
#define __EFM32_RTC_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup RTC
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** RTC initialization structure. */
|
||||
typedef struct
|
||||
{
|
||||
bool enable; /**< Start counting when init completed. */
|
||||
bool debugRun; /**< Counter shall keep running during debug halt. */
|
||||
bool comp0Top; /**< Use compare register 0 as max count value. */
|
||||
} RTC_Init_TypeDef;
|
||||
|
||||
/** Suggested default config for RTC init structure. */
|
||||
#define RTC_INIT_DEFAULT \
|
||||
{ true, /* Start counting when init done */ \
|
||||
false, /* Disable updating during debug halt */ \
|
||||
true /* Restart counting from 0 when reaching COMP0 */ \
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
uint32_t RTC_CompareGet(unsigned int comp);
|
||||
void RTC_CompareSet(unsigned int comp, uint32_t value);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get RTC counter value.
|
||||
*
|
||||
* @return
|
||||
* Current RTC counter value.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t RTC_CounterGet(void)
|
||||
{
|
||||
return(RTC->CNT);
|
||||
}
|
||||
|
||||
void RTC_CounterReset(void);
|
||||
void RTC_Enable(bool enable);
|
||||
void RTC_FreezeEnable(bool enable);
|
||||
void RTC_Init(const RTC_Init_TypeDef *init);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending RTC interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* RTC interrupt sources to clear. Use a set of interrupt flags OR-ed
|
||||
* together to clear multiple interrupt sources for the RTC module
|
||||
* (RTC_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void RTC_IntClear(uint32_t flags)
|
||||
{
|
||||
RTC->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more RTC interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* RTC interrupt sources to disable. Use a set of interrupt flags OR-ed
|
||||
* together to disable multiple interrupt sources for the RTC module
|
||||
* (RTC_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void RTC_IntDisable(uint32_t flags)
|
||||
{
|
||||
RTC->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more RTC interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using RTC_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] flags
|
||||
* RTC interrupt sources to enable. Use a set of interrupt flags OR-ed
|
||||
* together to set multiple interrupt sources for the RTC module
|
||||
* (RTC_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void RTC_IntEnable(uint32_t flags)
|
||||
{
|
||||
RTC->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending RTC interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @return
|
||||
* Pending RTC interrupt sources. Returns a set of interrupt flags OR-ed
|
||||
* together for multiple interrupt sources in the RTC module (RTC_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t RTC_IntGet(void)
|
||||
{
|
||||
return(RTC->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending RTC interrupts from SW.
|
||||
*
|
||||
* @param[in] flags
|
||||
* RTC interrupt sources to set to pending. Use a set of interrupt flags
|
||||
* OR-ed together to set multiple interrupt sources for the RTC module
|
||||
* (RTC_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void RTC_IntSet(uint32_t flags)
|
||||
{
|
||||
RTC->IFS = flags;
|
||||
}
|
||||
|
||||
void RTC_Reset(void);
|
||||
|
||||
/** @} (end addtogroup RTC) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_RTC_H */
|
|
@ -0,0 +1,74 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief System API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_SYSTEM_H
|
||||
#define __EFM32_SYSTEM_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup SYSTEM
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Chip revision details */
|
||||
typedef struct
|
||||
{
|
||||
uint8_t major; /**< Major revision number */
|
||||
uint8_t minor; /**< Minor revision number */
|
||||
} SYSTEM_ChipRevision_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void SYSTEM_ChipRevisionGet(SYSTEM_ChipRevision_TypeDef *rev);
|
||||
uint32_t SYSTEM_GetCalibrationValue(volatile uint32_t *regAddress);
|
||||
|
||||
/** @} (end addtogroup SYSTEM) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_SYSTEM_H */
|
|
@ -0,0 +1,642 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Timer/counter (TIMER) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_TIMER_H
|
||||
#define __EFM32_TIMER_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup TIMER
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Timer compare/capture mode. */
|
||||
typedef enum
|
||||
{
|
||||
timerCCModeOff = _TIMER_CC_CTRL_MODE_OFF, /**< Channel turned off. */
|
||||
timerCCModeCapture = _TIMER_CC_CTRL_MODE_INPUTCAPTURE, /**< Input capture. */
|
||||
timerCCModeCompare = _TIMER_CC_CTRL_MODE_OUTPUTCOMPARE, /**< Output compare. */
|
||||
timerCCModePWM = _TIMER_CC_CTRL_MODE_PWM /**< Pulse-Width modulation. */
|
||||
} TIMER_CCMode_TypeDef;
|
||||
|
||||
|
||||
/** Clock select. */
|
||||
typedef enum
|
||||
{
|
||||
/** Prescaled HFPER clock. */
|
||||
timerClkSelHFPerClk = _TIMER_CTRL_CLKSEL_PRESCHFPERCLK,
|
||||
|
||||
/** Prescaled HFPER clock. */
|
||||
timerClkSelCC1 = _TIMER_CTRL_CLKSEL_CC1,
|
||||
|
||||
/**
|
||||
* Cascaded, clocked by underflow (down-counting) or overflow (up-counting)
|
||||
* by lower numbered timer.
|
||||
*/
|
||||
timerClkSelCascade = _TIMER_CTRL_CLKSEL_TIMEROUF
|
||||
} TIMER_ClkSel_TypeDef;
|
||||
|
||||
|
||||
/** Input capture edge select. */
|
||||
typedef enum
|
||||
{
|
||||
/** Rising edges detected. */
|
||||
timerEdgeRising = _TIMER_CC_CTRL_ICEDGE_RISING,
|
||||
|
||||
/** Falling edges detected. */
|
||||
timerEdgeFalling = _TIMER_CC_CTRL_ICEDGE_FALLING,
|
||||
|
||||
/** Both edges detected. */
|
||||
timerEdgeBoth = _TIMER_CC_CTRL_ICEDGE_BOTH,
|
||||
|
||||
/** No edge detection, leave signal as is. */
|
||||
timerEdgeNone = _TIMER_CC_CTRL_ICEDGE_NONE
|
||||
} TIMER_Edge_TypeDef;
|
||||
|
||||
|
||||
/** Input capture event control. */
|
||||
typedef enum
|
||||
{
|
||||
/** PRS output pulse, interrupt flag and DMA request set on every capture. */
|
||||
timerEventEveryEdge = _TIMER_CC_CTRL_ICEVCTRL_EVERYEDGE,
|
||||
/** PRS output pulse, interrupt flag and DMA request set on every second capture. */
|
||||
timerEventEvery2ndEdge = _TIMER_CC_CTRL_ICEVCTRL_EVERYSECONDEDGE,
|
||||
/**
|
||||
* PRS output pulse, interrupt flag and DMA request set on rising edge (if
|
||||
* input capture edge = BOTH).
|
||||
*/
|
||||
timerEventRising = _TIMER_CC_CTRL_ICEVCTRL_RISING,
|
||||
/**
|
||||
* PRS output pulse, interrupt flag and DMA request set on falling edge (if
|
||||
* input capture edge = BOTH).
|
||||
*/
|
||||
timerEventFalling = _TIMER_CC_CTRL_ICEVCTRL_FALLING
|
||||
} TIMER_Event_TypeDef;
|
||||
|
||||
|
||||
/** Input edge action. */
|
||||
typedef enum
|
||||
{
|
||||
/** No action taken. */
|
||||
timerInputActionNone = _TIMER_CTRL_FALLA_NONE,
|
||||
|
||||
/** Start counter without reload. */
|
||||
timerInputActionStart = _TIMER_CTRL_FALLA_START,
|
||||
|
||||
/** Stop counter without reload. */
|
||||
timerInputActionStop = _TIMER_CTRL_FALLA_STOP,
|
||||
|
||||
/** Reload and start counter. */
|
||||
timerInputActionReloadStart = _TIMER_CTRL_FALLA_RELOADSTART
|
||||
} TIMER_InputAction_TypeDef;
|
||||
|
||||
|
||||
/** Timer mode. */
|
||||
typedef enum
|
||||
{
|
||||
timerModeUp = _TIMER_CTRL_MODE_UP, /**< Up-counting. */
|
||||
timerModeDown = _TIMER_CTRL_MODE_DOWN, /**< Down-counting. */
|
||||
timerModeUpDown = _TIMER_CTRL_MODE_UPDOWN, /**< Up/down-counting. */
|
||||
timerModeQDec = _TIMER_CTRL_MODE_QDEC /**< Quadrature decoder. */
|
||||
} TIMER_Mode_TypeDef;
|
||||
|
||||
|
||||
/** Compare/capture output action. */
|
||||
typedef enum
|
||||
{
|
||||
/** No action. */
|
||||
timerOutputActionNone = _TIMER_CC_CTRL_CUFOA_NONE,
|
||||
|
||||
/** Toggle on event. */
|
||||
timerOutputActionToggle = _TIMER_CC_CTRL_CUFOA_TOGGLE,
|
||||
|
||||
/** Clear on event. */
|
||||
timerOutputActionClear = _TIMER_CC_CTRL_CUFOA_CLEAR,
|
||||
|
||||
/** Set on event. */
|
||||
timerOutputActionSet = _TIMER_CC_CTRL_CUFOA_SET
|
||||
} TIMER_OutputAction_TypeDef;
|
||||
|
||||
|
||||
/** Prescaler. */
|
||||
typedef enum
|
||||
{
|
||||
timerPrescale1 = _TIMER_CTRL_PRESC_DIV1, /**< Divide by 1. */
|
||||
timerPrescale2 = _TIMER_CTRL_PRESC_DIV2, /**< Divide by 2. */
|
||||
timerPrescale4 = _TIMER_CTRL_PRESC_DIV4, /**< Divide by 4. */
|
||||
timerPrescale8 = _TIMER_CTRL_PRESC_DIV8, /**< Divide by 8. */
|
||||
timerPrescale16 = _TIMER_CTRL_PRESC_DIV16, /**< Divide by 16. */
|
||||
timerPrescale32 = _TIMER_CTRL_PRESC_DIV32, /**< Divide by 32. */
|
||||
timerPrescale64 = _TIMER_CTRL_PRESC_DIV64, /**< Divide by 64. */
|
||||
timerPrescale128 = _TIMER_CTRL_PRESC_DIV128, /**< Divide by 128. */
|
||||
timerPrescale256 = _TIMER_CTRL_PRESC_DIV256, /**< Divide by 256. */
|
||||
timerPrescale512 = _TIMER_CTRL_PRESC_DIV512, /**< Divide by 512. */
|
||||
timerPrescale1024 = _TIMER_CTRL_PRESC_DIV1024 /**< Divide by 1024. */
|
||||
} TIMER_Prescale_TypeDef;
|
||||
|
||||
|
||||
/** Peripheral Reflex System signal. */
|
||||
typedef enum
|
||||
{
|
||||
timerPRSSELCh0 = _ADC_SINGLECTRL_PRSSEL_PRSCH0, /**< PRS channel 0. */
|
||||
timerPRSSELCh1 = _ADC_SINGLECTRL_PRSSEL_PRSCH1, /**< PRS channel 1. */
|
||||
timerPRSSELCh2 = _ADC_SINGLECTRL_PRSSEL_PRSCH2, /**< PRS channel 2. */
|
||||
timerPRSSELCh3 = _ADC_SINGLECTRL_PRSSEL_PRSCH3, /**< PRS channel 3. */
|
||||
timerPRSSELCh4 = _ADC_SINGLECTRL_PRSSEL_PRSCH4, /**< PRS channel 4. */
|
||||
timerPRSSELCh5 = _ADC_SINGLECTRL_PRSSEL_PRSCH5, /**< PRS channel 5. */
|
||||
timerPRSSELCh6 = _ADC_SINGLECTRL_PRSSEL_PRSCH6, /**< PRS channel 6. */
|
||||
timerPRSSELCh7 = _ADC_SINGLECTRL_PRSSEL_PRSCH7 /**< PRS channel 7. */
|
||||
} TIMER_PRSSEL_TypeDef;
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** TIMER initialization structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Start counting when init completed. */
|
||||
bool enable;
|
||||
|
||||
/** Counter shall keep running during debug halt. */
|
||||
bool debugRun;
|
||||
|
||||
/** Prescaling factor, if HFPER clock used. */
|
||||
TIMER_Prescale_TypeDef prescale;
|
||||
|
||||
/** Clock selection. */
|
||||
TIMER_ClkSel_TypeDef clkSel;
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
/** 2x Count mode, counter increments/decrements by 2, meant for PWN mode. */
|
||||
bool count2x;
|
||||
|
||||
/** ATI (Always Track Inputs) makes CCPOL always track
|
||||
* the polarity of the inputs. */
|
||||
bool ati;
|
||||
#endif
|
||||
|
||||
/** Action on falling input edge. */
|
||||
TIMER_InputAction_TypeDef fallAction;
|
||||
|
||||
/** Action on rising input edge. */
|
||||
TIMER_InputAction_TypeDef riseAction;
|
||||
|
||||
/** Counting mode. */
|
||||
TIMER_Mode_TypeDef mode;
|
||||
|
||||
/** DMA request clear on active. */
|
||||
bool dmaClrAct;
|
||||
|
||||
/** Select X2 or X4 quadrature decode mode (if used). */
|
||||
bool quadModeX4;
|
||||
|
||||
/** Determines if only counting up or down once. */
|
||||
bool oneShot;
|
||||
|
||||
/** Timer start/stop/reload by other timers. */
|
||||
bool sync;
|
||||
} TIMER_Init_TypeDef;
|
||||
|
||||
/** Default config for TIMER init structure. */
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
#define TIMER_INIT_DEFAULT \
|
||||
{ true, /* Enable timer when init complete. */ \
|
||||
false, /* Stop counter during debug halt. */ \
|
||||
timerPrescale1, /* No prescaling. */ \
|
||||
timerClkSelHFPerClk, /* Select HFPER clock. */ \
|
||||
false, /* Not 2x count mode. */ \
|
||||
false, /* No ATI. */ \
|
||||
timerInputActionNone, /* No action on falling input edge. */ \
|
||||
timerInputActionNone, /* No action on rising input edge. */ \
|
||||
timerModeUp, /* Up-counting. */ \
|
||||
false, /* Do not clear DMA requests when DMA channel is active. */ \
|
||||
false, /* Select X2 quadrature decode mode (if used). */ \
|
||||
false, /* Disable one shot. */ \
|
||||
false /* Not started/stopped/reloaded by other timers. */ \
|
||||
}
|
||||
#else
|
||||
#define TIMER_INIT_DEFAULT \
|
||||
{ true, /* Enable timer when init complete. */ \
|
||||
false, /* Stop counter during debug halt. */ \
|
||||
timerPrescale1, /* No prescaling. */ \
|
||||
timerClkSelHFPerClk, /* Select HFPER clock. */ \
|
||||
timerInputActionNone, /* No action on falling input edge. */ \
|
||||
timerInputActionNone, /* No action on rising input edge. */ \
|
||||
timerModeUp, /* Up-counting. */ \
|
||||
false, /* Do not clear DMA requests when DMA channel is active. */ \
|
||||
false, /* Select X2 quadrature decode mode (if used). */ \
|
||||
false, /* Disable one shot. */ \
|
||||
false /* Not started/stopped/reloaded by other timers. */ \
|
||||
}
|
||||
#endif
|
||||
|
||||
/** TIMER compare/capture initialization structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Input capture event control. */
|
||||
TIMER_Event_TypeDef eventCtrl;
|
||||
|
||||
/** Input capture edge select. */
|
||||
TIMER_Edge_TypeDef edge;
|
||||
|
||||
/**
|
||||
* Peripheral reflex system trigger selection. Only applicable if @p prsInput
|
||||
* is enabled.
|
||||
*/
|
||||
TIMER_PRSSEL_TypeDef prsSel;
|
||||
|
||||
/** Counter underflow output action. */
|
||||
TIMER_OutputAction_TypeDef cufoa;
|
||||
|
||||
/** Counter overflow output action. */
|
||||
TIMER_OutputAction_TypeDef cofoa;
|
||||
|
||||
/** Counter match output action. */
|
||||
TIMER_OutputAction_TypeDef cmoa;
|
||||
|
||||
/** Compare/capture channel mode. */
|
||||
TIMER_CCMode_TypeDef mode;
|
||||
|
||||
/** Enable digital filter. */
|
||||
bool filter;
|
||||
|
||||
/** Select TIMERnCCx (false) or PRS input (true). */
|
||||
bool prsInput;
|
||||
|
||||
/**
|
||||
* Compare output initial state. Only used in Output Compare and PWM mode.
|
||||
* When true, the compare/PWM output is set high when the counter is
|
||||
* disabled. When counting resumes, this value will represent the initial
|
||||
* value for the compare/PWM output. If the bit is cleared, the output
|
||||
* will be cleared when the counter is disabled.
|
||||
*/
|
||||
bool coist;
|
||||
|
||||
/** Invert output from compare/capture channel. */
|
||||
bool outInvert;
|
||||
} TIMER_InitCC_TypeDef;
|
||||
|
||||
/** Default config for TIMER compare/capture init structure. */
|
||||
#define TIMER_INITCC_DEFAULT \
|
||||
{ timerEventEveryEdge, /* Event on every capture. */ \
|
||||
timerEdgeRising, /* Input capture edge on rising edge. */ \
|
||||
timerPRSSELCh0, /* Not used by default, select PRS channel 0. */ \
|
||||
timerOutputActionNone, /* No action on underflow. */ \
|
||||
timerOutputActionNone, /* No action on overflow. */ \
|
||||
timerOutputActionNone, /* No action on match. */ \
|
||||
timerCCModeOff, /* Disable compare/capture channel. */ \
|
||||
false, /* Disable filter. */ \
|
||||
false, /* Select TIMERnCCx input. */ \
|
||||
false, /* Clear output when countre disabled. */ \
|
||||
false /* Do not invert output. */ \
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get capture value for compare/capture channel when operating in capture
|
||||
* mode.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] ch
|
||||
* Compare/capture channel to access.
|
||||
*
|
||||
* @return
|
||||
* Current capture value.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t TIMER_CaptureGet(TIMER_TypeDef *timer, unsigned int ch)
|
||||
{
|
||||
return(timer->CC[ch].CCV);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set compare value buffer for compare/capture channel when operating in
|
||||
* compare or PWM mode.
|
||||
*
|
||||
* @details
|
||||
* The compare value buffer holds the value which will be written to
|
||||
* TIMERn_CCx_CCV on an update event if the buffer has been updated since
|
||||
* the last event.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] ch
|
||||
* Compare/capture channel to access.
|
||||
*
|
||||
* @param[in] val
|
||||
* Value to set in compare value buffer register.
|
||||
******************************************************************************/
|
||||
static __INLINE void TIMER_CompareBufSet(TIMER_TypeDef *timer,
|
||||
unsigned int ch,
|
||||
uint32_t val)
|
||||
{
|
||||
timer->CC[ch].CCVB = val;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set compare value for compare/capture channel when operating in compare
|
||||
* or PWM mode.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] ch
|
||||
* Compare/capture channel to access.
|
||||
*
|
||||
* @param[in] val
|
||||
* Value to set in compare value register.
|
||||
******************************************************************************/
|
||||
static __INLINE void TIMER_CompareSet(TIMER_TypeDef *timer,
|
||||
unsigned int ch,
|
||||
uint32_t val)
|
||||
{
|
||||
timer->CC[ch].CCV = val;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get TIMER counter value.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Current TIMER counter value.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t TIMER_CounterGet(TIMER_TypeDef *timer)
|
||||
{
|
||||
return(timer->CNT);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set TIMER counter value.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] val
|
||||
* Value to set counter to.
|
||||
******************************************************************************/
|
||||
static __INLINE void TIMER_CounterSet(TIMER_TypeDef *timer, uint32_t val)
|
||||
{
|
||||
timer->CNT = val;
|
||||
}
|
||||
|
||||
|
||||
void TIMER_Enable(TIMER_TypeDef *rtc, bool enable);
|
||||
void TIMER_Init(TIMER_TypeDef *timer, const TIMER_Init_TypeDef *init);
|
||||
void TIMER_InitCC(TIMER_TypeDef *timer,
|
||||
unsigned int ch,
|
||||
const TIMER_InitCC_TypeDef *init);
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending TIMER interrupts.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending TIMER interrupt source(s) to clear. Use one or more valid
|
||||
* interrupt flags for the TIMER module (TIMER_IF_nnn) OR'ed together.
|
||||
******************************************************************************/
|
||||
static __INLINE void TIMER_IntClear(TIMER_TypeDef *timer, uint32_t flags)
|
||||
{
|
||||
timer->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more TIMER interrupts.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* TIMER interrupt source(s) to disable. Use one or more valid
|
||||
* interrupt flags for the TIMER module (TIMER_IF_nnn) OR'ed together.
|
||||
******************************************************************************/
|
||||
static __INLINE void TIMER_IntDisable(TIMER_TypeDef *timer, uint32_t flags)
|
||||
{
|
||||
timer->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more TIMER interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using TIMER_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* TIMER interrupt source(s) to enable. Use one or more valid
|
||||
* interrupt flags for the TIMER module (TIMER_IF_nnn) OR'ed together.
|
||||
******************************************************************************/
|
||||
static __INLINE void TIMER_IntEnable(TIMER_TypeDef *timer, uint32_t flags)
|
||||
{
|
||||
timer->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending TIMER interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* TIMER interrupt source(s) pending. Returns one or more valid
|
||||
* interrupt flags for the TIMER module (TIMER_IF_nnn) OR'ed together.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t TIMER_IntGet(TIMER_TypeDef *timer)
|
||||
{
|
||||
return(timer->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get enabled and pending TIMER interrupt flags.
|
||||
* Useful for handling more interrupt sources in the same interrupt handler.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @note
|
||||
* Interrupt flags are not cleared by the use of this function.
|
||||
*
|
||||
* @return
|
||||
* Pending and enabled TIMER interrupt sources.
|
||||
* The return value is the bitwise AND combination of
|
||||
* - the OR combination of enabled interrupt sources in TIMERx_IEN_nnn
|
||||
* register (TIMERx_IEN_nnn) and
|
||||
* - the OR combination of valid interrupt flags of the TIMER module
|
||||
* (TIMERx_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t TIMER_IntGetEnabled(TIMER_TypeDef *timer)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
/* Store TIMER->IEN in temporary variable in order to define explicit order
|
||||
* of volatile accesses. */
|
||||
tmp = timer->IEN;
|
||||
|
||||
/* Bitwise AND of pending and enabled interrupts */
|
||||
return timer->IF & tmp;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending TIMER interrupts from SW.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* TIMER interrupt source(s) to set to pending. Use one or more valid
|
||||
* interrupt flags for the TIMER module (TIMER_IF_nnn) OR'ed together.
|
||||
******************************************************************************/
|
||||
static __INLINE void TIMER_IntSet(TIMER_TypeDef *timer, uint32_t flags)
|
||||
{
|
||||
timer->IFS = flags;
|
||||
}
|
||||
|
||||
#ifdef TIMER_DTLOCK_LOCKKEY_LOCK
|
||||
void TIMER_Lock(TIMER_TypeDef *timer);
|
||||
#endif
|
||||
|
||||
void TIMER_Reset(TIMER_TypeDef *timer);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set top value buffer for timer.
|
||||
*
|
||||
* @details
|
||||
* When the top value buffer register is updated, the value is loaded into
|
||||
* the top value register at the next wrap around. This feature is useful
|
||||
* in order to update the top value safely when the timer is running.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] val
|
||||
* Value to set in top value buffer register.
|
||||
******************************************************************************/
|
||||
static __INLINE void TIMER_TopBufSet(TIMER_TypeDef *timer, uint32_t val)
|
||||
{
|
||||
timer->TOPB = val;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get top value setting for timer.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Current top value.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t TIMER_TopGet(TIMER_TypeDef *timer)
|
||||
{
|
||||
return(timer->TOP);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set top value for timer.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] val
|
||||
* Value to set in top value register.
|
||||
******************************************************************************/
|
||||
static __INLINE void TIMER_TopSet(TIMER_TypeDef *timer, uint32_t val)
|
||||
{
|
||||
timer->TOP = val;
|
||||
}
|
||||
|
||||
#ifdef TIMER_DTLOCK_LOCKKEY_UNLOCK
|
||||
void TIMER_Unlock(TIMER_TypeDef *timer);
|
||||
#endif
|
||||
|
||||
|
||||
/** @} (end addtogroup TIMER) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_TIMER_H */
|
|
@ -0,0 +1,645 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Universal synchronous/asynchronous receiver/transmitter (USART/UART)
|
||||
* peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_USART_H
|
||||
#define __EFM32_USART_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup USART
|
||||
* @brief Universal Synchronous/Asynchronous Receiver/Transmitter (USART) peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Databit selection. */
|
||||
typedef enum
|
||||
{
|
||||
usartDatabits4 = USART_FRAME_DATABITS_FOUR, /**< 4 databits (not available for UART). */
|
||||
usartDatabits5 = USART_FRAME_DATABITS_FIVE, /**< 5 databits (not available for UART). */
|
||||
usartDatabits6 = USART_FRAME_DATABITS_SIX, /**< 6 databits (not available for UART). */
|
||||
usartDatabits7 = USART_FRAME_DATABITS_SEVEN, /**< 7 databits (not available for UART). */
|
||||
usartDatabits8 = USART_FRAME_DATABITS_EIGHT, /**< 8 databits. */
|
||||
usartDatabits9 = USART_FRAME_DATABITS_NINE, /**< 9 databits. */
|
||||
usartDatabits10 = USART_FRAME_DATABITS_TEN, /**< 10 databits (not available for UART). */
|
||||
usartDatabits11 = USART_FRAME_DATABITS_ELEVEN, /**< 11 databits (not available for UART). */
|
||||
usartDatabits12 = USART_FRAME_DATABITS_TWELVE, /**< 12 databits (not available for UART). */
|
||||
usartDatabits13 = USART_FRAME_DATABITS_THIRTEEN, /**< 13 databits (not available for UART). */
|
||||
usartDatabits14 = USART_FRAME_DATABITS_FOURTEEN, /**< 14 databits (not available for UART). */
|
||||
usartDatabits15 = USART_FRAME_DATABITS_FIFTEEN, /**< 15 databits (not available for UART). */
|
||||
usartDatabits16 = USART_FRAME_DATABITS_SIXTEEN /**< 16 databits (not available for UART). */
|
||||
} USART_Databits_TypeDef;
|
||||
|
||||
|
||||
/** Enable selection. */
|
||||
typedef enum
|
||||
{
|
||||
/** Disable both receiver and transmitter. */
|
||||
usartDisable = 0x0,
|
||||
|
||||
/** Enable receiver only, transmitter disabled. */
|
||||
usartEnableRx = USART_CMD_RXEN,
|
||||
|
||||
/** Enable transmitter only, receiver disabled. */
|
||||
usartEnableTx = USART_CMD_TXEN,
|
||||
|
||||
/** Enable both receiver and transmitter. */
|
||||
usartEnable = (USART_CMD_RXEN | USART_CMD_TXEN)
|
||||
} USART_Enable_TypeDef;
|
||||
|
||||
|
||||
/** Oversampling selection, used for asynchronous operation. */
|
||||
typedef enum
|
||||
{
|
||||
usartOVS16 = USART_CTRL_OVS_X16, /**< 16x oversampling (normal). */
|
||||
usartOVS8 = USART_CTRL_OVS_X8, /**< 8x oversampling. */
|
||||
usartOVS6 = USART_CTRL_OVS_X6, /**< 6x oversampling. */
|
||||
usartOVS4 = USART_CTRL_OVS_X4 /**< 4x oversampling. */
|
||||
} USART_OVS_TypeDef;
|
||||
|
||||
|
||||
/** Parity selection, mainly used for asynchronous operation. */
|
||||
typedef enum
|
||||
{
|
||||
usartNoParity = USART_FRAME_PARITY_NONE, /**< No parity. */
|
||||
usartEvenParity = USART_FRAME_PARITY_EVEN, /**< Even parity. */
|
||||
usartOddParity = USART_FRAME_PARITY_ODD /**< Odd parity. */
|
||||
} USART_Parity_TypeDef;
|
||||
|
||||
|
||||
/** Stopbits selection, used for asynchronous operation. */
|
||||
typedef enum
|
||||
{
|
||||
usartStopbits0p5 = USART_FRAME_STOPBITS_HALF, /**< 0.5 stopbits. */
|
||||
usartStopbits1 = USART_FRAME_STOPBITS_ONE, /**< 1 stopbits. */
|
||||
usartStopbits1p5 = USART_FRAME_STOPBITS_ONEANDAHALF, /**< 1.5 stopbits. */
|
||||
usartStopbits2 = USART_FRAME_STOPBITS_TWO /**< 2 stopbits. */
|
||||
} USART_Stopbits_TypeDef;
|
||||
|
||||
|
||||
/** Clock polarity/phase mode. */
|
||||
typedef enum
|
||||
{
|
||||
/** Clock idle low, sample on rising edge. */
|
||||
usartClockMode0 = USART_CTRL_CLKPOL_IDLELOW | USART_CTRL_CLKPHA_SAMPLELEADING,
|
||||
|
||||
/** Clock idle low, sample on falling edge. */
|
||||
usartClockMode1 = USART_CTRL_CLKPOL_IDLELOW | USART_CTRL_CLKPHA_SAMPLETRAILING,
|
||||
|
||||
/** Clock idle high, sample on falling edge. */
|
||||
usartClockMode2 = USART_CTRL_CLKPOL_IDLEHIGH | USART_CTRL_CLKPHA_SAMPLELEADING,
|
||||
|
||||
/** Clock idle high, sample on rising edge. */
|
||||
usartClockMode3 = USART_CTRL_CLKPOL_IDLEHIGH | USART_CTRL_CLKPHA_SAMPLETRAILING
|
||||
} USART_ClockMode_TypeDef;
|
||||
|
||||
|
||||
/** Pulse width selection for IrDA mode. */
|
||||
typedef enum
|
||||
{
|
||||
/** IrDA pulse width is 1/16 for OVS=0 and 1/8 for OVS=1 */
|
||||
usartIrDAPwONE = USART_IRCTRL_IRPW_ONE,
|
||||
|
||||
/** IrDA pulse width is 2/16 for OVS=0 and 2/8 for OVS=1 */
|
||||
usartIrDAPwTWO = USART_IRCTRL_IRPW_TWO,
|
||||
|
||||
/** IrDA pulse width is 3/16 for OVS=0 and 3/8 for OVS=1 */
|
||||
usartIrDAPwTHREE = USART_IRCTRL_IRPW_THREE,
|
||||
|
||||
/** IrDA pulse width is 4/16 for OVS=0 and 4/8 for OVS=1 */
|
||||
usartIrDAPwFOUR = USART_IRCTRL_IRPW_FOUR
|
||||
} USART_IrDAPw_Typedef;
|
||||
|
||||
|
||||
/** PRS channel selection for IrDA mode. */
|
||||
typedef enum
|
||||
{
|
||||
usartIrDAPrsCh0 = USART_IRCTRL_IRPRSSEL_PRSCH0, /**< PRS channel 0 */
|
||||
usartIrDAPrsCh1 = USART_IRCTRL_IRPRSSEL_PRSCH1, /**< PRS channel 1 */
|
||||
usartIrDAPrsCh2 = USART_IRCTRL_IRPRSSEL_PRSCH2, /**< PRS channel 2 */
|
||||
usartIrDAPrsCh3 = USART_IRCTRL_IRPRSSEL_PRSCH3, /**< PRS channel 3 */
|
||||
usartIrDAPrsCh4 = USART_IRCTRL_IRPRSSEL_PRSCH4, /**< PRS channel 4 */
|
||||
usartIrDAPrsCh5 = USART_IRCTRL_IRPRSSEL_PRSCH5, /**< PRS channel 5 */
|
||||
usartIrDAPrsCh6 = USART_IRCTRL_IRPRSSEL_PRSCH6, /**< PRS channel 6 */
|
||||
usartIrDAPrsCh7 = USART_IRCTRL_IRPRSSEL_PRSCH7 /**< PRS channel 7 */
|
||||
} USART_IrDAPrsSel_Typedef;
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
/** I2S format selection. */
|
||||
typedef enum
|
||||
{
|
||||
usartI2sFormatW32D32 = USART_I2SCTRL_FORMAT_W32D32, /**< 32-bit word, 32-bit data */
|
||||
usartI2sFormatW32D24M = USART_I2SCTRL_FORMAT_W32D24M, /**< 32-bit word, 32-bit data with 8 lsb masked */
|
||||
usartI2sFormatW32D24 = USART_I2SCTRL_FORMAT_W32D24, /**< 32-bit word, 24-bit data */
|
||||
usartI2sFormatW32D16 = USART_I2SCTRL_FORMAT_W32D16, /**< 32-bit word, 16-bit data */
|
||||
usartI2sFormatW32D8 = USART_I2SCTRL_FORMAT_W32D8, /**< 32-bit word, 8-bit data */
|
||||
usartI2sFormatW16D16 = USART_I2SCTRL_FORMAT_W16D16, /**< 16-bit word, 16-bit data */
|
||||
usartI2sFormatW16D8 = USART_I2SCTRL_FORMAT_W16D8, /**< 16-bit word, 8-bit data */
|
||||
usartI2sFormatW8D8 = USART_I2SCTRL_FORMAT_W8D8 /**< 8-bit word, 8-bit data */
|
||||
} USART_I2sFormat_TypeDef;
|
||||
|
||||
/** I2S frame data justify. */
|
||||
typedef enum
|
||||
{
|
||||
usartI2sJustifyLeft = USART_I2SCTRL_JUSTIFY_LEFT, /**< Data is left-justified within the frame */
|
||||
usartI2sJustifyRight = USART_I2SCTRL_JUSTIFY_RIGHT /**< Data is right-justified within the frame */
|
||||
} USART_I2sJustify_TypeDef;
|
||||
|
||||
/** USART Rx input PRS selection. */
|
||||
typedef enum
|
||||
{
|
||||
usartPrsRxCh0 = USART_INPUT_RXPRSSEL_PRSCH0, /**< PRSCH0 selected as USART_INPUT */
|
||||
usartPrsRxCh1 = USART_INPUT_RXPRSSEL_PRSCH1, /**< PRSCH1 selected as USART_INPUT */
|
||||
usartPrsRxCh2 = USART_INPUT_RXPRSSEL_PRSCH2, /**< PRSCH2 selected as USART_INPUT */
|
||||
usartPrsRxCh3 = USART_INPUT_RXPRSSEL_PRSCH3, /**< PRSCH3 selected as USART_INPUT */
|
||||
usartPrsRxCh4 = USART_INPUT_RXPRSSEL_PRSCH4, /**< PRSCH4 selected as USART_INPUT */
|
||||
usartPrsRxCh5 = USART_INPUT_RXPRSSEL_PRSCH5, /**< PRSCH5 selected as USART_INPUT */
|
||||
usartPrsRxCh6 = USART_INPUT_RXPRSSEL_PRSCH6, /**< PRSCH6 selected as USART_INPUT */
|
||||
|
||||
#if defined(_EFM32_TINY_FAMILY)
|
||||
usartPrsRxCh7 = USART_INPUT_RXPRSSEL_PRSCH7 /**< PRSCH7 selected as USART_INPUT */
|
||||
|
||||
#elif defined(_EFM32_GIANT_FAMILY)
|
||||
usartPrsRxCh7 = USART_INPUT_RXPRSSEL_PRSCH7, /**< PRSCH7 selected as USART_INPUT */
|
||||
usartPrsRxCh8 = USART_INPUT_RXPRSSEL_PRSCH8, /**< PRSCH8 selected as USART_INPUT */
|
||||
usartPrsRxCh9 = USART_INPUT_RXPRSSEL_PRSCH9, /**< PRSCH9 selected as USART_INPUT */
|
||||
usartPrsRxCh10 = USART_INPUT_RXPRSSEL_PRSCH10, /**< PRSCH10 selected as USART_INPUT */
|
||||
usartPrsRxCh11 = USART_INPUT_RXPRSSEL_PRSCH11 /**< PRSCH11 selected as USART_INPUT */
|
||||
#else
|
||||
#error Unknown EFM32 family.
|
||||
#endif
|
||||
} USART_PrsRxCh_TypeDef;
|
||||
#endif
|
||||
|
||||
#if defined (_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/** USART PRS Transmit Trigger Channels */
|
||||
typedef enum
|
||||
{
|
||||
usartPrsTriggerCh0 = USART_TRIGCTRL_TSEL_PRSCH0, /**< PRSCH0 selected as USART Trigger */
|
||||
usartPrsTriggerCh1 = USART_TRIGCTRL_TSEL_PRSCH1, /**< PRSCH0 selected as USART Trigger */
|
||||
usartPrsTriggerCh2 = USART_TRIGCTRL_TSEL_PRSCH2, /**< PRSCH0 selected as USART Trigger */
|
||||
usartPrsTriggerCh3 = USART_TRIGCTRL_TSEL_PRSCH3, /**< PRSCH0 selected as USART Trigger */
|
||||
usartPrsTriggerCh4 = USART_TRIGCTRL_TSEL_PRSCH4, /**< PRSCH0 selected as USART Trigger */
|
||||
usartPrsTriggerCh5 = USART_TRIGCTRL_TSEL_PRSCH5, /**< PRSCH0 selected as USART Trigger */
|
||||
usartPrsTriggerCh6 = USART_TRIGCTRL_TSEL_PRSCH6, /**< PRSCH0 selected as USART Trigger */
|
||||
usartPrsTriggerCh7 = USART_TRIGCTRL_TSEL_PRSCH7, /**< PRSCH0 selected as USART Trigger */
|
||||
} USART_PrsTriggerCh_TypeDef;
|
||||
#endif
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Asynchronous mode init structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Specifies whether TX and/or RX shall be enabled when init completed. */
|
||||
USART_Enable_TypeDef enable;
|
||||
|
||||
/**
|
||||
* USART/UART reference clock assumed when configuring baudrate setup. Set
|
||||
* it to 0 if currently configurated reference clock shall be used.
|
||||
*/
|
||||
uint32_t refFreq;
|
||||
|
||||
/** Desired baudrate. */
|
||||
uint32_t baudrate;
|
||||
|
||||
/** Oversampling used. */
|
||||
USART_OVS_TypeDef oversampling;
|
||||
|
||||
/** Number of databits in frame. Notice that UART modules only support 8 or
|
||||
* 9 databits. */
|
||||
USART_Databits_TypeDef databits;
|
||||
|
||||
/** Parity mode to use. */
|
||||
USART_Parity_TypeDef parity;
|
||||
|
||||
/** Number of stopbits to use. */
|
||||
USART_Stopbits_TypeDef stopbits;
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
/** Majority Vote Disable for 16x, 8x and 6x oversampling modes. */
|
||||
bool mvdis;
|
||||
|
||||
/** Enable USART Rx via PRS. */
|
||||
bool prsRxEnable;
|
||||
|
||||
/** Select PRS channel for USART Rx. (Only valid if prsRxEnable is true). */
|
||||
USART_PrsRxCh_TypeDef prsRxCh;
|
||||
#endif
|
||||
} USART_InitAsync_TypeDef;
|
||||
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/** USART PRS trigger enable */
|
||||
typedef struct
|
||||
{
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/** Enable AUTOTX */
|
||||
bool autoTxTriggerEnable;
|
||||
#endif
|
||||
/** Trigger receive via PRS channel */
|
||||
bool rxTriggerEnable;
|
||||
/** Trigger transmit via PRS channel */
|
||||
bool txTriggerEnable;
|
||||
/** PRS channel to be used to trigger auto transmission */
|
||||
USART_PrsTriggerCh_TypeDef prsTriggerChannel;
|
||||
} USART_PrsTriggerInit_TypeDef;
|
||||
#endif
|
||||
|
||||
/** Default config for USART async init structure. */
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
#define USART_INITASYNC_DEFAULT \
|
||||
{ usartEnable, /* Enable RX/TX when init completed. */ \
|
||||
0, /* Use current configured reference clock for configuring baudrate. */ \
|
||||
115200, /* 115200 bits/s. */ \
|
||||
usartOVS16, /* 16x oversampling. */ \
|
||||
usartDatabits8, /* 8 databits. */ \
|
||||
usartNoParity, /* No parity. */ \
|
||||
usartStopbits1, /* 1 stopbit. */ \
|
||||
false, /* Do not disable majority vote. */ \
|
||||
false, /* Not USART PRS input mode. */ \
|
||||
usartPrsRxCh0 /* PRS channel 0. */ \
|
||||
}
|
||||
#else
|
||||
#define USART_INITASYNC_DEFAULT \
|
||||
{ usartEnable, /* Enable RX/TX when init completed. */ \
|
||||
0, /* Use current configured reference clock for configuring baudrate. */ \
|
||||
115200, /* 115200 bits/s. */ \
|
||||
usartOVS16, /* 16x oversampling. */ \
|
||||
usartDatabits8, /* 8 databits. */ \
|
||||
usartNoParity, /* No parity. */ \
|
||||
usartStopbits1 /* 1 stopbit. */ \
|
||||
}
|
||||
#endif
|
||||
|
||||
/** Synchronous mode init structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Specifies whether TX and/or RX shall be enabled when init completed. */
|
||||
USART_Enable_TypeDef enable;
|
||||
|
||||
/**
|
||||
* USART/UART reference clock assumed when configuring baudrate setup. Set
|
||||
* it to 0 if currently configurated reference clock shall be used.
|
||||
*/
|
||||
uint32_t refFreq;
|
||||
|
||||
/** Desired baudrate. */
|
||||
uint32_t baudrate;
|
||||
|
||||
/** Number of databits in frame. */
|
||||
USART_Databits_TypeDef databits;
|
||||
|
||||
/** Select if to operate in master or slave mode. */
|
||||
bool master;
|
||||
|
||||
/** Select if to send most or least significant bit first. */
|
||||
bool msbf;
|
||||
|
||||
/** Clock polarity/phase mode. */
|
||||
USART_ClockMode_TypeDef clockMode;
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
/** Enable USART Rx via PRS. */
|
||||
bool prsRxEnable;
|
||||
|
||||
/** Select PRS channel for USART Rx. (Only valid if prsRxEnable is true). */
|
||||
USART_PrsRxCh_TypeDef prsRxCh;
|
||||
|
||||
/** Enable AUTOTX mode. Transmits as long as RX is not full.
|
||||
* If TX is empty, underflows are generated. */
|
||||
bool autoTx;
|
||||
#endif
|
||||
} USART_InitSync_TypeDef;
|
||||
|
||||
/** Default config for USART sync init structure. */
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
#define USART_INITSYNC_DEFAULT \
|
||||
{ usartEnable, /* Enable RX/TX when init completed. */ \
|
||||
0, /* Use current configured reference clock for configuring baudrate. */ \
|
||||
1000000, /* 1 Mbits/s. */ \
|
||||
usartDatabits8, /* 8 databits. */ \
|
||||
true, /* Master mode. */ \
|
||||
false, /* Send least significant bit first. */ \
|
||||
usartClockMode0, /* Clock idle low, sample on rising edge. */ \
|
||||
false, /* Not USART PRS input mode. */ \
|
||||
usartPrsRxCh0, /* PRS channel 0. */ \
|
||||
false /* No AUTOTX mode. */ \
|
||||
}
|
||||
#else
|
||||
#define USART_INITSYNC_DEFAULT \
|
||||
{ usartEnable, /* Enable RX/TX when init completed. */ \
|
||||
0, /* Use current configured reference clock for configuring baudrate. */ \
|
||||
1000000, /* 1 Mbits/s. */ \
|
||||
usartDatabits8, /* 8 databits. */ \
|
||||
true, /* Master mode. */ \
|
||||
false, /* Send least significant bit first. */ \
|
||||
usartClockMode0 /* Clock idle low, sample on rising edge. */ \
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/** IrDA mode init structure. Inherited from asynchronous mode init structure */
|
||||
typedef struct
|
||||
{
|
||||
/** General Async initialization structure. */
|
||||
USART_InitAsync_TypeDef async;
|
||||
|
||||
/** Set to invert Rx signal before IrDA demodulator. */
|
||||
bool irRxInv;
|
||||
|
||||
/** Set to enable filter on IrDA demodulator. */
|
||||
bool irFilt;
|
||||
|
||||
/** Configure the pulse width generated by the IrDA modulator as a fraction
|
||||
* of the configured USART bit period. */
|
||||
USART_IrDAPw_Typedef irPw;
|
||||
|
||||
/** Enable the PRS channel selected by irPrsSel as input to IrDA module
|
||||
* instead of TX. */
|
||||
bool irPrsEn;
|
||||
|
||||
/** A PRS can be used as input to the pulse modulator instead of TX.
|
||||
* This value selects the channel to use. */
|
||||
USART_IrDAPrsSel_Typedef irPrsSel;
|
||||
} USART_InitIrDA_TypeDef;
|
||||
|
||||
|
||||
/** Default config for IrDA mode init structure. */
|
||||
#define USART_INITIRDA_DEFAULT \
|
||||
{ \
|
||||
{ usartEnable, /* Enable RX/TX when init completed. */ \
|
||||
0, /* Use current configured reference clock for configuring baudrate. */ \
|
||||
115200, /* 115200 bits/s. */ \
|
||||
usartOVS16, /* 16x oversampling. */ \
|
||||
usartDatabits8, /* 8 databits. */ \
|
||||
usartEvenParity, /* Even parity. */ \
|
||||
usartStopbits1 /* 1 stopbit. */ \
|
||||
}, \
|
||||
false, /* Rx invert disabled. */ \
|
||||
false, /* Filtering disabled. */ \
|
||||
usartIrDAPwTHREE, /* Pulse width is set to ONE. */ \
|
||||
false, /* Routing to PRS is disabled. */ \
|
||||
usartIrDAPrsCh0 /* PRS channel 0. */ \
|
||||
}
|
||||
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
/** I2S mode init structure. Inherited from synchronous mode init structure */
|
||||
typedef struct
|
||||
{
|
||||
/** General Sync initialization structure. */
|
||||
USART_InitSync_TypeDef sync;
|
||||
|
||||
/** I2S mode. */
|
||||
USART_I2sFormat_TypeDef format;
|
||||
|
||||
/** Delay on I2S data. Set to add a one-cycle delay between a transition
|
||||
* on the word-clock and the start of the I2S word.
|
||||
* Should be set for standard I2S format. */
|
||||
bool delay;
|
||||
|
||||
/** Separate DMA Request For Left/Right Data. */
|
||||
bool dmaSplit;
|
||||
|
||||
/** Justification of I2S data within the frame */
|
||||
USART_I2sJustify_TypeDef justify;
|
||||
|
||||
/** Stero or Mono, set to true for mono. */
|
||||
bool mono;
|
||||
} USART_InitI2s_TypeDef;
|
||||
|
||||
|
||||
/** Default config for I2S mode init structure. */
|
||||
#define USART_INITI2S_DEFAULT \
|
||||
{ \
|
||||
{ usartEnableTx, /* Enable TX when init completed. */ \
|
||||
0, /* Use current configured reference clock for configuring baudrate. */ \
|
||||
1000000, /* Baudrate 1M bits/s. */ \
|
||||
usartDatabits16, /* 16 databits. */ \
|
||||
true, /* Operate as I2S master. */ \
|
||||
true, /* Most significant bit first. */ \
|
||||
usartClockMode0, /* Clock idle low, sample on rising edge. */ \
|
||||
false, /* Don't enable USARTRx via PRS. */ \
|
||||
usartPrsRxCh0, /* PRS channel selection (dummy). */ \
|
||||
false /* Disable AUTOTX mode. */ \
|
||||
}, \
|
||||
usartI2sFormatW16D16, /* 16-bit word, 16-bit data */ \
|
||||
true, /* Delay on I2S data. */ \
|
||||
false, /* No DMA split. */ \
|
||||
usartI2sJustifyLeft, /* Data is left-justified within the frame */ \
|
||||
false /* Stereo mode. */ \
|
||||
}
|
||||
#endif
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void USART_BaudrateAsyncSet(USART_TypeDef *usart,
|
||||
uint32_t refFreq,
|
||||
uint32_t baudrate,
|
||||
USART_OVS_TypeDef ovs);
|
||||
uint32_t USART_BaudrateCalc(uint32_t refFreq,
|
||||
uint32_t clkdiv,
|
||||
bool syncmode,
|
||||
USART_OVS_TypeDef ovs);
|
||||
uint32_t USART_BaudrateGet(USART_TypeDef *usart);
|
||||
void USART_BaudrateSyncSet(USART_TypeDef *usart,
|
||||
uint32_t refFreq,
|
||||
uint32_t baudrate);
|
||||
void USART_Enable(USART_TypeDef *usart, USART_Enable_TypeDef enable);
|
||||
|
||||
void USART_InitAsync(USART_TypeDef *usart, const USART_InitAsync_TypeDef *init);
|
||||
void USART_InitSync(USART_TypeDef *usart, const USART_InitSync_TypeDef *init);
|
||||
void USART_InitIrDA(const USART_InitIrDA_TypeDef *init);
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
void USART_InitI2s(USART_TypeDef *usart, USART_InitI2s_TypeDef *init);
|
||||
void USART_InitPrsTrigger(USART_TypeDef *usart, const USART_PrsTriggerInit_TypeDef *init);
|
||||
#endif
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending USART interrupts.
|
||||
*
|
||||
* @param[in] usart
|
||||
* Pointer to USART/UART peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* Pending USART/UART interrupt source(s) to clear. Use one or more valid
|
||||
* interrupt flags for the USART module (USART_IF_nnn) OR'ed together.
|
||||
******************************************************************************/
|
||||
static __INLINE void USART_IntClear(USART_TypeDef *usart, uint32_t flags)
|
||||
{
|
||||
usart->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more USART interrupts.
|
||||
*
|
||||
* @param[in] usart
|
||||
* Pointer to USART/UART peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* USART/UART interrupt source(s) to disable. Use one or more valid
|
||||
* interrupt flags for the USART module (USART_IF_nnn) OR'ed together.
|
||||
******************************************************************************/
|
||||
static __INLINE void USART_IntDisable(USART_TypeDef *usart, uint32_t flags)
|
||||
{
|
||||
usart->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more USART interrupts.
|
||||
*
|
||||
* @note
|
||||
* Depending on the use, a pending interrupt may already be set prior to
|
||||
* enabling the interrupt. Consider using USART_IntClear() prior to enabling
|
||||
* if such a pending interrupt should be ignored.
|
||||
*
|
||||
* @param[in] usart
|
||||
* Pointer to USART/UART peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* USART/UART interrupt source(s) to enable. Use one or more valid
|
||||
* interrupt flags for the USART module (USART_IF_nnn) OR'ed together.
|
||||
******************************************************************************/
|
||||
static __INLINE void USART_IntEnable(USART_TypeDef *usart, uint32_t flags)
|
||||
{
|
||||
usart->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending USART interrupt flags.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @param[in] usart
|
||||
* Pointer to USART/UART peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* USART/UART interrupt source(s) pending. Returns one or more valid
|
||||
* interrupt flags for the USART module (USART_IF_nnn) OR'ed together.
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t USART_IntGet(USART_TypeDef *usart)
|
||||
{
|
||||
return usart->IF;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get enabled and pending USART interrupt flags.
|
||||
* Useful for handling more interrupt sources in the same interrupt handler.
|
||||
*
|
||||
* @param[in] usart
|
||||
* Pointer to USART/UART peripheral register block.
|
||||
*
|
||||
* @note
|
||||
* Interrupt flags are not cleared by the use of this function.
|
||||
*
|
||||
* @return
|
||||
* Pending and enabled USART interrupt sources.
|
||||
* The return value is the bitwise AND combination of
|
||||
* - the OR combination of enabled interrupt sources in USARTx_IEN_nnn
|
||||
* register (USARTx_IEN_nnn) and
|
||||
* - the OR combination of valid interrupt flags of the USART module
|
||||
* (USARTx_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t USART_IntGetEnabled(USART_TypeDef *usart)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
/* Store USARTx->IEN in temporary variable in order to define explicit order
|
||||
* of volatile accesses. */
|
||||
tmp = usart->IEN;
|
||||
|
||||
/* Bitwise AND of pending and enabled interrupts */
|
||||
return usart->IF & tmp;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending USART interrupts from SW.
|
||||
*
|
||||
* @param[in] usart
|
||||
* Pointer to USART/UART peripheral register block.
|
||||
*
|
||||
* @param[in] flags
|
||||
* USART/UART interrupt source(s) to set to pending. Use one or more valid
|
||||
* interrupt flags for the USART module (USART_IF_nnn) OR'ed together.
|
||||
******************************************************************************/
|
||||
static __INLINE void USART_IntSet(USART_TypeDef *usart, uint32_t flags)
|
||||
{
|
||||
usart->IFS = flags;
|
||||
}
|
||||
|
||||
void USART_Reset(USART_TypeDef *usart);
|
||||
uint8_t USART_Rx(USART_TypeDef *usart);
|
||||
uint16_t USART_RxDouble(USART_TypeDef *usart);
|
||||
uint32_t USART_RxDoubleExt(USART_TypeDef *usart);
|
||||
uint16_t USART_RxExt(USART_TypeDef *usart);
|
||||
void USART_Tx(USART_TypeDef *usart, uint8_t data);
|
||||
void USART_TxDouble(USART_TypeDef *usart, uint16_t data);
|
||||
void USART_TxDoubleExt(USART_TypeDef *usart, uint32_t data);
|
||||
void USART_TxExt(USART_TypeDef *usart, uint16_t data);
|
||||
|
||||
|
||||
/** @} (end addtogroup USART) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_USART_H */
|
|
@ -0,0 +1,352 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Voltage Comparator (VCMP) peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_VCMP_H
|
||||
#define __EFM32_VCMP_H
|
||||
#include "efm32.h"
|
||||
|
||||
#include <stdint.h>
|
||||
#include <stdbool.h>
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup VCMP
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Warm-up Time in High Frequency Peripheral Clock cycles */
|
||||
typedef enum
|
||||
{
|
||||
/** 4 cycles */
|
||||
vcmpWarmTime4Cycles = _VCMP_CTRL_WARMTIME_4CYCLES,
|
||||
/** 8 cycles */
|
||||
vcmpWarmTime8Cycles = _VCMP_CTRL_WARMTIME_8CYCLES,
|
||||
/** 16 cycles */
|
||||
vcmpWarmTime16Cycles = _VCMP_CTRL_WARMTIME_16CYCLES,
|
||||
/** 32 cycles */
|
||||
vcmpWarmTime32Cycles = _VCMP_CTRL_WARMTIME_32CYCLES,
|
||||
/** 64 cycles */
|
||||
vcmpWarmTime64Cycles = _VCMP_CTRL_WARMTIME_64CYCLES,
|
||||
/** 128 cycles */
|
||||
vcmpWarmTime128Cycles = _VCMP_CTRL_WARMTIME_128CYCLES,
|
||||
/** 256 cycles */
|
||||
vcmpWarmTime256Cycles = _VCMP_CTRL_WARMTIME_256CYCLES,
|
||||
/** 512 cycles */
|
||||
vcmpWarmTime512Cycles = _VCMP_CTRL_WARMTIME_512CYCLES
|
||||
} VCMP_WarmTime_TypeDef;
|
||||
|
||||
/** Hyseresis configuration */
|
||||
typedef enum
|
||||
{
|
||||
/** Normal operation, no hysteresis */
|
||||
vcmpHystNone,
|
||||
/** Digital output will not toggle until positive edge is at least
|
||||
* 20mV above or below negative input voltage */
|
||||
vcmpHyst20mV
|
||||
} VCMP_Hysteresis_TypeDef;
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** VCMP Initialization structure */
|
||||
typedef struct
|
||||
{
|
||||
/** If set to true, will reduce by half the bias current */
|
||||
bool halfBias;
|
||||
/** BIAS current configuration, depends on halfBias setting,
|
||||
* above, see reference manual */
|
||||
int biasProg;
|
||||
/** Enable interrupt for falling edge */
|
||||
bool irqFalling;
|
||||
/** Enable interrupt for rising edge */
|
||||
bool irqRising;
|
||||
/** Warm-up time in clock cycles */
|
||||
VCMP_WarmTime_TypeDef warmup;
|
||||
/** Hysteresis configuration */
|
||||
VCMP_Hysteresis_TypeDef hyst;
|
||||
/** Output value when comparator is inactive, should be 0 or 1 */
|
||||
int inactive;
|
||||
/** Enable low power mode for VDD and bandgap reference */
|
||||
bool lowPowerRef;
|
||||
/** Trigger level, according to formula
|
||||
* VDD Trigger Level = 1.667V + 0.034V x triggerLevel */
|
||||
int triggerLevel;
|
||||
/** Enable VCMP after configuration */
|
||||
bool enable;
|
||||
} VCMP_Init_TypeDef;
|
||||
|
||||
/** Default VCMP initialization structure */
|
||||
#define VCMP_INIT_DEFAULT \
|
||||
{ true, /** Half Bias enabled */ \
|
||||
0x7, /** Bias curernt 0.7 uA when half bias enabled */ \
|
||||
false, /** Falling edge sense not enabled */ \
|
||||
false, /** Rising edge sense not enabled */ \
|
||||
vcmpWarmTime4Cycles, /** 4 clock cycles warm-up time */ \
|
||||
vcmpHystNone, /** No hysteresis */ \
|
||||
0, /** 0 in digital ouput when inactive */ \
|
||||
true, /** Do not use low power reference */ \
|
||||
39, /** Trigger level just below 3V */ \
|
||||
true, /** Enable after init */ \
|
||||
}
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
void VCMP_Init(const VCMP_Init_TypeDef *vcmpInit);
|
||||
void VCMP_LowPowerRefSet(bool enable);
|
||||
void VCMP_TriggerSet(int level);
|
||||
|
||||
static __INLINE void VCMP_Enable(void);
|
||||
static __INLINE void VCMP_Disable(void);
|
||||
static __INLINE uint32_t VCMP_VoltageToLevel(float v);
|
||||
static __INLINE bool VCMP_VDDLower(void);
|
||||
static __INLINE bool VCMP_VDDHigher(void);
|
||||
static __INLINE bool VCMP_Ready(void);
|
||||
static __INLINE void VCMP_IntClear(uint32_t flags);
|
||||
static __INLINE void VCMP_IntSet(uint32_t flags);
|
||||
static __INLINE void VCMP_IntDisable(uint32_t flags);
|
||||
static __INLINE void VCMP_IntEnable(uint32_t flags);
|
||||
static __INLINE uint32_t VCMP_IntGet(void);
|
||||
static __INLINE uint32_t VCMP_IntGetEnabled(void);
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable Voltage Comparator
|
||||
******************************************************************************/
|
||||
static __INLINE void VCMP_Enable(void)
|
||||
{
|
||||
VCMP->CTRL |= VCMP_CTRL_EN;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable Voltage Comparator
|
||||
******************************************************************************/
|
||||
static __INLINE void VCMP_Disable(void)
|
||||
{
|
||||
VCMP->CTRL &= ~(VCMP_CTRL_EN);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Calculate voltage to trigger level
|
||||
*
|
||||
* @note
|
||||
* You need soft float support for this function to be working
|
||||
*
|
||||
* @param[in] v
|
||||
* Voltage Level for trigger
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t VCMP_VoltageToLevel(float v)
|
||||
{
|
||||
return (uint32_t)((v - (float)1.667) / (float)0.034);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Returns true, if Voltage Comparator indicated VDD < trigger level, else
|
||||
* false
|
||||
******************************************************************************/
|
||||
static __INLINE bool VCMP_VDDLower(void)
|
||||
{
|
||||
if (VCMP->STATUS & VCMP_STATUS_VCMPOUT)
|
||||
{
|
||||
return false;
|
||||
}
|
||||
else
|
||||
{
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Returns true, if Voltage Comparator indicated VDD > trigger level, else
|
||||
* false
|
||||
******************************************************************************/
|
||||
static __INLINE bool VCMP_VDDHigher(void)
|
||||
{
|
||||
if (VCMP->STATUS & VCMP_STATUS_VCMPOUT)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* VCMP output is ready
|
||||
******************************************************************************/
|
||||
static __INLINE bool VCMP_Ready(void)
|
||||
{
|
||||
if (VCMP->STATUS & VCMP_STATUS_VCMPACT)
|
||||
{
|
||||
return true;
|
||||
}
|
||||
else
|
||||
{
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear one or more pending VCMP interrupts.
|
||||
*
|
||||
* @param[in] flags
|
||||
* VCMP interrupt sources to clear. Use a set of interrupt flags OR-ed
|
||||
* together to clear multiple interrupt sources for the VCMP module
|
||||
* (VCMP_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void VCMP_IntClear(uint32_t flags)
|
||||
{
|
||||
VCMP->IFC = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set one or more pending VCMP interrupts from SW.
|
||||
*
|
||||
* @param[in] flags
|
||||
* VCMP interrupt sources to set to pending. Use a set of interrupt flags
|
||||
* OR-ed together to set multiple interrupt sources for the VCMP module
|
||||
* (VCMP_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void VCMP_IntSet(uint32_t flags)
|
||||
{
|
||||
VCMP->IFS = flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable one or more VCMP interrupts
|
||||
*
|
||||
* @param[in] flags
|
||||
* VCMP interrupt sources to enable. Use a set of interrupt flags OR-ed
|
||||
* together to set multiple interrupt sources for the VCMP module
|
||||
* (VCMP_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void VCMP_IntDisable(uint32_t flags)
|
||||
{
|
||||
VCMP->IEN &= ~(flags);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable one or more VCMP interrupts
|
||||
*
|
||||
* @param[in] flags
|
||||
* VCMP interrupt sources to enable. Use a set of interrupt flags OR-ed
|
||||
* together to set multiple interrupt sources for the VCMP module
|
||||
* (VCMP_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE void VCMP_IntEnable(uint32_t flags)
|
||||
{
|
||||
VCMP->IEN |= flags;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get pending VCMP interrupt flags
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function
|
||||
*
|
||||
* @return
|
||||
* Pending VCMP interrupt sources. Returns a set of interrupt flags OR-ed
|
||||
* together for multiple interrupt sources in the VCMP module (VCMP_IFS_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t VCMP_IntGet(void)
|
||||
{
|
||||
return(VCMP->IF);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get enabled and pending VCMP interrupt flags.
|
||||
*
|
||||
* @details
|
||||
* Useful for handling more interrupt sources in the same interrupt handler.
|
||||
*
|
||||
* @note
|
||||
* The event bits are not cleared by the use of this function.
|
||||
*
|
||||
* @return
|
||||
* Pending and enabled VCMP interrupt sources.
|
||||
* The return value is the bitwise AND combination of
|
||||
* - the OR combination of enabled interrupt sources in VCMP_IEN_nnn
|
||||
* register (VCMP_IEN_nnn) and
|
||||
* - the OR combination of valid interrupt flags of the VCMP module
|
||||
* (VCMP_IF_nnn).
|
||||
******************************************************************************/
|
||||
static __INLINE uint32_t VCMP_IntGetEnabled(void)
|
||||
{
|
||||
uint32_t tmp = 0U;
|
||||
|
||||
/* Store VCMP->IEN in temporary variable in order to define explicit order
|
||||
* of volatile accesses. */
|
||||
tmp = VCMP->IEN;
|
||||
|
||||
/* Bitwise AND of pending and enabled interrupts */
|
||||
return VCMP->IF & tmp;
|
||||
}
|
||||
|
||||
/** @} (end addtogroup VCMP) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_VCMP_H */
|
|
@ -0,0 +1,146 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Watchdog (WDOG) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#ifndef __EFM32_WDOG_H
|
||||
#define __EFM32_WDOG_H
|
||||
|
||||
#include <stdbool.h>
|
||||
#include "efm32.h"
|
||||
|
||||
#ifdef __cplusplus
|
||||
extern "C" {
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup WDOG
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Watchdog clock selection. */
|
||||
typedef enum
|
||||
{
|
||||
wdogClkSelULFRCO = _WDOG_CTRL_CLKSEL_ULFRCO, /**< Ultra low frequency (1 kHz) clock */
|
||||
wdogClkSelLFRCO = _WDOG_CTRL_CLKSEL_LFRCO, /**< Low frequency RC oscillator */
|
||||
wdogClkSelLFXO = _WDOG_CTRL_CLKSEL_LFXO /**< Low frequency crystal oscillator */
|
||||
} WDOG_ClkSel_TypeDef;
|
||||
|
||||
/** Watchdog period selection. */
|
||||
typedef enum
|
||||
{
|
||||
wdogPeriod_9 = 0x0, /**< 9 clock periods */
|
||||
wdogPeriod_17 = 0x1, /**< 17 clock periods */
|
||||
wdogPeriod_33 = 0x2, /**< 33 clock periods */
|
||||
wdogPeriod_65 = 0x3, /**< 65 clock periods */
|
||||
wdogPeriod_129 = 0x4, /**< 129 clock periods */
|
||||
wdogPeriod_257 = 0x5, /**< 257 clock periods */
|
||||
wdogPeriod_513 = 0x6, /**< 513 clock periods */
|
||||
wdogPeriod_1k = 0x7, /**< 1025 clock periods */
|
||||
wdogPeriod_2k = 0x8, /**< 2049 clock periods */
|
||||
wdogPeriod_4k = 0x9, /**< 4097 clock periods */
|
||||
wdogPeriod_8k = 0xA, /**< 8193 clock periods */
|
||||
wdogPeriod_16k = 0xB, /**< 16385 clock periods */
|
||||
wdogPeriod_32k = 0xC, /**< 32769 clock periods */
|
||||
wdogPeriod_64k = 0xD, /**< 65537 clock periods */
|
||||
wdogPeriod_128k = 0xE, /**< 131073 clock periods */
|
||||
wdogPeriod_256k = 0xF /**< 262145 clock periods */
|
||||
} WDOG_PeriodSel_TypeDef;
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** Watchdog initialization structure. */
|
||||
typedef struct
|
||||
{
|
||||
/** Enable watchdog when init completed. */
|
||||
bool enable;
|
||||
|
||||
/** Counter shall keep running during debug halt. */
|
||||
bool debugRun;
|
||||
|
||||
/** Counter shall keep running when in EM2. */
|
||||
bool em2Run;
|
||||
|
||||
/** Counter shall keep running when in EM3. */
|
||||
bool em3Run;
|
||||
|
||||
/** Block EMU from entering EM4. */
|
||||
bool em4Block;
|
||||
|
||||
/** Block SW from disabling LFRCO/LFXO oscillators. */
|
||||
bool swoscBlock;
|
||||
|
||||
/** Block SW from modifying the configuration (a reset is needed to reconfigure). */
|
||||
bool lock;
|
||||
|
||||
/** Clock source to use for watchdog. */
|
||||
WDOG_ClkSel_TypeDef clkSel;
|
||||
|
||||
/** Watchdog timeout period. */
|
||||
WDOG_PeriodSel_TypeDef perSel;
|
||||
} WDOG_Init_TypeDef;
|
||||
|
||||
/** Suggested default config for WDOG init structure. */
|
||||
#define WDOG_INIT_DEFAULT \
|
||||
{ true, /* Start watchdog when init done */ \
|
||||
false, /* WDOG not counting during debug halt */ \
|
||||
false, /* WDOG not counting when in EM2 */ \
|
||||
false, /* WDOG not counting when in EM3 */ \
|
||||
false, /* EM4 can be entered */ \
|
||||
false, /* Do not block disabling LFRCO/LFXO in CMU */ \
|
||||
false, /* Do not lock WDOG configuration (if locked, reset needed to unlock) */ \
|
||||
wdogClkSelULFRCO, /* Select 1kHZ WDOG oscillator */ \
|
||||
wdogPeriod_256k /* Set longest possible timeout period */ \
|
||||
}
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** PROTOTYPES **********************************
|
||||
******************************************************************************/
|
||||
|
||||
void WDOG_Enable(bool enable);
|
||||
void WDOG_Feed(void);
|
||||
void WDOG_Init(const WDOG_Init_TypeDef *init);
|
||||
void WDOG_Lock(void);
|
||||
|
||||
/** @} (end addtogroup WDOG) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
#endif /* __EFM32_WDOG_H */
|
|
@ -0,0 +1,294 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Analog Comparator (ACMP) peripheral module library implementation
|
||||
* for EFM32 devices.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#include <stdbool.h>
|
||||
#include "efm32_acmp.h"
|
||||
#include "efm32_bitband.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup ACMP
|
||||
* @brief Analog comparator (ACMP) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
|
||||
/** Validation of ACMP register block pointer reference
|
||||
* for assert statements. */
|
||||
#if (ACMP_COUNT == 1)
|
||||
#define ACMP_REF_VALID(ref) ((ref) == ACMP0)
|
||||
#elif (ACMP_COUNT == 2)
|
||||
#define ACMP_REF_VALID(ref) (((ref) == ACMP0) || ((ref) == ACMP1))
|
||||
#else
|
||||
#error Undefined number of analog comparators (ACMP).
|
||||
#endif
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Sets up the ACMP for use in capacative sense applications.
|
||||
*
|
||||
* @details
|
||||
* This function sets up the ACMP for use in capacacitve sense applications.
|
||||
* To use the capacative sense functionality in the ACMP you need to use
|
||||
* the PRS output of the ACMP module to count the number of oscillations
|
||||
* in the capacative sense circuit (possibly using a TIMER).
|
||||
*
|
||||
* @note
|
||||
* A basic example of capacative sensing can be found in the STK BSP
|
||||
* (capsense demo).
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to ACMP peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to initialization structure used to configure ACMP for capacative
|
||||
* sensing operation.
|
||||
******************************************************************************/
|
||||
void ACMP_CapsenseInit(ACMP_TypeDef *acmp, const ACMP_CapsenseInit_TypeDef *init)
|
||||
{
|
||||
/* Make sure the module exists on the selected chip */
|
||||
EFM_ASSERT(ACMP_REF_VALID(acmp));
|
||||
|
||||
/* Make sure that vddLevel is within bounds */
|
||||
EFM_ASSERT(init->vddLevel < 64);
|
||||
|
||||
/* Make sure biasprog is within bounds */
|
||||
EFM_ASSERT(init->biasProg < 16);
|
||||
|
||||
/* Set control register. No need to set interrupt modes */
|
||||
acmp->CTRL = (init->fullBias << _ACMP_CTRL_FULLBIAS_SHIFT)
|
||||
| (init->halfBias << _ACMP_CTRL_HALFBIAS_SHIFT)
|
||||
| (init->biasProg << _ACMP_CTRL_BIASPROG_SHIFT)
|
||||
| (init->warmTime << _ACMP_CTRL_WARMTIME_SHIFT)
|
||||
| (init->hysteresisLevel << _ACMP_CTRL_HYSTSEL_SHIFT);
|
||||
|
||||
/* Select capacative sensing mode by selecting a resistor and enabling it */
|
||||
acmp->INPUTSEL = (init->resistor << _ACMP_INPUTSEL_CSRESSEL_SHIFT)
|
||||
| ACMP_INPUTSEL_CSRESEN
|
||||
| (init->lowPowerReferenceEnabled << _ACMP_INPUTSEL_LPREF_SHIFT)
|
||||
| (init->vddLevel << _ACMP_INPUTSEL_VDDLEVEL_SHIFT)
|
||||
| ACMP_INPUTSEL_NEGSEL_CAPSENSE;
|
||||
|
||||
/* Enable ACMP if requested.
|
||||
* Note: BITBAND_Peripheral() function is used for setting/clearing single
|
||||
* bit peripheral register bitfields. */
|
||||
BITBAND_Peripheral(&(acmp->CTRL),
|
||||
(uint32_t)_ACMP_CTRL_EN_SHIFT,
|
||||
(uint32_t)init->enable);
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Sets the ACMP channel used for capacative sensing.
|
||||
*
|
||||
* @note
|
||||
* A basic example of capacative sensing can be found in the STK BSP
|
||||
* (capsense demo).
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to ACMP peripheral register block.
|
||||
*
|
||||
* @param[in] channel
|
||||
* The ACMP channel to use for capacative sensing (Possel).
|
||||
******************************************************************************/
|
||||
void ACMP_CapsenseChannelSet(ACMP_TypeDef *acmp, ACMP_Channel_TypeDef channel)
|
||||
{
|
||||
/* Make sure that only external channels are used */
|
||||
EFM_ASSERT(channel < _ACMP_INPUTSEL_NEGSEL_1V25);
|
||||
|
||||
/* Set channel as positive channel in ACMP */
|
||||
SET_BIT_FIELD(acmp->INPUTSEL, _ACMP_INPUTSEL_POSSEL_MASK, channel,
|
||||
_ACMP_INPUTSEL_POSSEL_SHIFT);
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disables the ACMP.
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to ACMP peripheral register block.
|
||||
******************************************************************************/
|
||||
void ACMP_Disable(ACMP_TypeDef *acmp)
|
||||
{
|
||||
acmp->CTRL &= ~ACMP_CTRL_EN;
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enables the ACMP.
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to ACMP peripheral register block.
|
||||
******************************************************************************/
|
||||
void ACMP_Enable(ACMP_TypeDef *acmp)
|
||||
{
|
||||
acmp->CTRL |= ACMP_CTRL_EN;
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Reset ACMP to same state as after a HW reset.
|
||||
*
|
||||
* @note
|
||||
* The ROUTE register is NOT reset by this function, in order to allow for
|
||||
* centralized setup of this feature.
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to the ACMP peripheral register block.
|
||||
******************************************************************************/
|
||||
void ACMP_Reset(ACMP_TypeDef *acmp)
|
||||
{
|
||||
/* Make sure the module exists on the selected chip */
|
||||
EFM_ASSERT(ACMP_REF_VALID(acmp));
|
||||
|
||||
acmp->CTRL = _ACMP_CTRL_RESETVALUE;
|
||||
acmp->INPUTSEL = _ACMP_INPUTSEL_RESETVALUE;
|
||||
acmp->IEN = _ACMP_IEN_RESETVALUE;
|
||||
acmp->IFC = _ACMP_IF_MASK;
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Sets up GPIO output from the ACMP.
|
||||
*
|
||||
* @note
|
||||
* GPIO must be enabled in the CMU before this function call, i.e.
|
||||
* @verbatim CMU_ClockEnable(cmuClock_GPIO, true); @endverbatim
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to the ACMP peripheral register block.
|
||||
*
|
||||
* @param location
|
||||
* The pin location to use. See the datasheet for location to pin mappings.
|
||||
*
|
||||
* @param enable
|
||||
* Enable or disable pin output.
|
||||
*
|
||||
* @param invert
|
||||
* Invert output.
|
||||
******************************************************************************/
|
||||
void ACMP_GPIOSetup(ACMP_TypeDef *acmp, uint32_t location, bool enable, bool invert)
|
||||
{
|
||||
/* Sanity checking of location */
|
||||
EFM_ASSERT(location < 4);
|
||||
|
||||
/* Set GPIO inversion */
|
||||
SET_BIT_FIELD(acmp->CTRL, _ACMP_CTRL_GPIOINV_MASK, invert,
|
||||
_ACMP_CTRL_GPIOINV_SHIFT);
|
||||
|
||||
acmp->ROUTE = (location << _ACMP_ROUTE_LOCATION_SHIFT)
|
||||
| (enable << _ACMP_ROUTE_ACMPPEN_SHIFT);
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Sets which channels should be used in ACMP comparisons.
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to the ACMP peripheral register block.
|
||||
*
|
||||
* @param negSel
|
||||
* Channel to use on the negative input to the ACMP.
|
||||
*
|
||||
* @param posSel
|
||||
* Channel to use on the positive input to the ACMP.
|
||||
******************************************************************************/
|
||||
void ACMP_ChannelSet(ACMP_TypeDef *acmp, ACMP_Channel_TypeDef negSel,
|
||||
ACMP_Channel_TypeDef posSel)
|
||||
{
|
||||
/* Make sure that only external channels are used as ACMP positive input */
|
||||
EFM_ASSERT(posSel < _ACMP_INPUTSEL_NEGSEL_1V25);
|
||||
/* Sanity checking of ACMP negative input */
|
||||
EFM_ASSERT(negSel <= _ACMP_INPUTSEL_NEGSEL_VDD);
|
||||
|
||||
acmp->INPUTSEL = (acmp->INPUTSEL & ~(_ACMP_INPUTSEL_POSSEL_MASK |
|
||||
_ACMP_INPUTSEL_NEGSEL_MASK))
|
||||
| (negSel << _ACMP_INPUTSEL_NEGSEL_SHIFT)
|
||||
| (posSel << _ACMP_INPUTSEL_POSSEL_SHIFT);
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
*
|
||||
*
|
||||
* @param[in] acmp
|
||||
* Pointer to the ACMP peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to initialization structure used to configure ACMP for capacative
|
||||
* sensing operation.
|
||||
******************************************************************************/
|
||||
void ACMP_Init(ACMP_TypeDef *acmp, const ACMP_Init_TypeDef *init)
|
||||
{
|
||||
/* Make sure the module exists on the selected chip */
|
||||
EFM_ASSERT(ACMP_REF_VALID(acmp));
|
||||
|
||||
/* Make sure biasprog is within bounds */
|
||||
EFM_ASSERT(init->biasProg < 16);
|
||||
|
||||
/* Set control register. No need to set interrupt modes */
|
||||
acmp->CTRL = (init->fullBias << _ACMP_CTRL_FULLBIAS_SHIFT)
|
||||
| (init->halfBias << _ACMP_CTRL_HALFBIAS_SHIFT)
|
||||
| (init->biasProg << _ACMP_CTRL_BIASPROG_SHIFT)
|
||||
| (init->interruptOnFallingEdge << _ACMP_CTRL_IFALL_SHIFT)
|
||||
| (init->interruptOnRisingEdge << _ACMP_CTRL_IRISE_SHIFT)
|
||||
| (init->warmTime << _ACMP_CTRL_WARMTIME_SHIFT)
|
||||
| (init->hysteresisLevel << _ACMP_CTRL_HYSTSEL_SHIFT)
|
||||
| (init->inactiveValue << _ACMP_CTRL_INACTVAL_SHIFT);
|
||||
|
||||
acmp->INPUTSEL = (init->lowPowerReferenceEnabled << _ACMP_INPUTSEL_LPREF_SHIFT)
|
||||
| (init->vddLevel << _ACMP_INPUTSEL_VDDLEVEL_SHIFT);
|
||||
|
||||
/* Enable ACMP if requested.
|
||||
* Note: BITBAND_Peripheral() function is used for setting/clearing single
|
||||
* bit peripheral register bitfields. */
|
||||
BITBAND_Peripheral(&(acmp->CTRL),
|
||||
(uint32_t)_ACMP_CTRL_EN_SHIFT,
|
||||
(uint32_t)init->enable);
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup ACMP) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,510 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Analog to Digital Converter (ADC) Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#include "efm32_adc.h"
|
||||
#include "efm32_cmu.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup ADC
|
||||
* @brief Analog to Digital Converter (ADC) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/** Validation of ADC register block pointer reference for assert statements. */
|
||||
#define ADC_REF_VALID(ref) ((ref) == ADC0)
|
||||
|
||||
/** Max ADC clock */
|
||||
#define ADC_MAX_CLOCK 13000000
|
||||
|
||||
/** Min ADC clock */
|
||||
#define ADC_MIN_CLOCK 32000
|
||||
|
||||
/** @endcond */
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
*************************** LOCAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Load SCAN calibrate register with predefined values for a certain
|
||||
* reference.
|
||||
*
|
||||
* @details
|
||||
* During production, calibration values are made and stored in the device
|
||||
* information page for known references. Notice that for external references,
|
||||
* calibration values must be determined explicitly, and this function
|
||||
* will not modify the calibration register.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @param[in] ref
|
||||
* Reference to load calibrated values for. No values are loaded for
|
||||
* external references.
|
||||
******************************************************************************/
|
||||
static void ADC_CalibrateLoadScan(ADC_TypeDef *adc, ADC_Ref_TypeDef ref)
|
||||
{
|
||||
uint32_t cal;
|
||||
|
||||
/* Load proper calibration data depending on selected reference */
|
||||
/* NOTE: We use ...SCAN... defines below, they are the same as */
|
||||
/* similar ...SINGLE... defines. */
|
||||
switch (ref)
|
||||
{
|
||||
case adcRef1V25:
|
||||
cal = adc->CAL & ~(_ADC_CAL_SCANOFFSET_MASK | _ADC_CAL_SCANGAIN_MASK);
|
||||
cal |= ((DEVINFO->ADC0CAL0 & _DEVINFO_ADC0CAL0_1V25_GAIN_MASK) >>
|
||||
_DEVINFO_ADC0CAL0_1V25_GAIN_SHIFT) << _ADC_CAL_SCANGAIN_SHIFT;
|
||||
cal |= ((DEVINFO->ADC0CAL0 & _DEVINFO_ADC0CAL0_1V25_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL0_1V25_OFFSET_SHIFT) << _ADC_CAL_SCANOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
break;
|
||||
|
||||
case adcRef2V5:
|
||||
cal = adc->CAL & ~(_ADC_CAL_SCANOFFSET_MASK | _ADC_CAL_SCANGAIN_MASK);
|
||||
cal |= ((DEVINFO->ADC0CAL0 & _DEVINFO_ADC0CAL0_2V5_GAIN_MASK) >>
|
||||
_DEVINFO_ADC0CAL0_2V5_GAIN_SHIFT) << _ADC_CAL_SCANGAIN_SHIFT;
|
||||
cal |= ((DEVINFO->ADC0CAL0 & _DEVINFO_ADC0CAL0_2V5_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL0_2V5_OFFSET_SHIFT) << _ADC_CAL_SCANOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
break;
|
||||
|
||||
case adcRefVDD:
|
||||
cal = adc->CAL & ~(_ADC_CAL_SCANOFFSET_MASK | _ADC_CAL_SCANGAIN_MASK);
|
||||
cal |= ((DEVINFO->ADC0CAL1 & _DEVINFO_ADC0CAL1_VDD_GAIN_MASK) >>
|
||||
_DEVINFO_ADC0CAL1_VDD_GAIN_SHIFT) << _ADC_CAL_SCANGAIN_SHIFT;
|
||||
cal |= ((DEVINFO->ADC0CAL1 & _DEVINFO_ADC0CAL1_VDD_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL1_VDD_OFFSET_SHIFT) << _ADC_CAL_SCANOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
break;
|
||||
|
||||
case adcRef5VDIFF:
|
||||
cal = adc->CAL & ~(_ADC_CAL_SCANOFFSET_MASK | _ADC_CAL_SCANGAIN_MASK);
|
||||
cal |= ((DEVINFO->ADC0CAL1 & _DEVINFO_ADC0CAL1_5VDIFF_GAIN_MASK) >>
|
||||
_DEVINFO_ADC0CAL1_5VDIFF_GAIN_SHIFT) << _ADC_CAL_SCANGAIN_SHIFT;
|
||||
cal |= ((DEVINFO->ADC0CAL1 & _DEVINFO_ADC0CAL1_5VDIFF_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL1_5VDIFF_OFFSET_SHIFT) << _ADC_CAL_SCANOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
break;
|
||||
|
||||
case adcRef2xVDD:
|
||||
/* Gain value not of relevance for this reference, leave as is */
|
||||
cal = adc->CAL & ~_ADC_CAL_SCANOFFSET_MASK;
|
||||
cal |= ((DEVINFO->ADC0CAL2 & _DEVINFO_ADC0CAL2_2XVDDVSS_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL2_2XVDDVSS_OFFSET_SHIFT) << _ADC_CAL_SCANOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
break;
|
||||
|
||||
/* For external references, the calibration must be determined for the */
|
||||
/* specific application and set explicitly. */
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Load SINGLE calibrate register with predefined values for a certain
|
||||
* reference.
|
||||
*
|
||||
* @details
|
||||
* During production, calibration values are made and stored in the device
|
||||
* information page for known references. Notice that for external references,
|
||||
* calibration values must be determined explicitly, and this function
|
||||
* will not modify the calibration register.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @param[in] ref
|
||||
* Reference to load calibrated values for. No values are loaded for
|
||||
* external references.
|
||||
******************************************************************************/
|
||||
static void ADC_CalibrateLoadSingle(ADC_TypeDef *adc, ADC_Ref_TypeDef ref)
|
||||
{
|
||||
uint32_t cal;
|
||||
|
||||
/* Load proper calibration data depending on selected reference */
|
||||
/* NOTE: We use ...SCAN... defines below, they are the same as */
|
||||
/* similar ...SINGLE... defines. */
|
||||
switch (ref)
|
||||
{
|
||||
case adcRef1V25:
|
||||
cal = adc->CAL & ~(_ADC_CAL_SINGLEOFFSET_MASK | _ADC_CAL_SINGLEGAIN_MASK);
|
||||
cal |= ((DEVINFO->ADC0CAL0 & _DEVINFO_ADC0CAL0_1V25_GAIN_MASK) >>
|
||||
_DEVINFO_ADC0CAL0_1V25_GAIN_SHIFT) << _ADC_CAL_SINGLEGAIN_SHIFT;
|
||||
cal |= ((DEVINFO->ADC0CAL0 & _DEVINFO_ADC0CAL0_1V25_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL0_1V25_OFFSET_SHIFT) << _ADC_CAL_SINGLEOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
break;
|
||||
|
||||
case adcRef2V5:
|
||||
cal = adc->CAL & ~(_ADC_CAL_SINGLEOFFSET_MASK | _ADC_CAL_SINGLEGAIN_MASK);
|
||||
cal |= ((DEVINFO->ADC0CAL0 & _DEVINFO_ADC0CAL0_2V5_GAIN_MASK) >>
|
||||
_DEVINFO_ADC0CAL0_2V5_GAIN_SHIFT) << _ADC_CAL_SINGLEGAIN_SHIFT;
|
||||
cal |= ((DEVINFO->ADC0CAL0 & _DEVINFO_ADC0CAL0_2V5_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL0_2V5_OFFSET_SHIFT) << _ADC_CAL_SINGLEOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
break;
|
||||
|
||||
case adcRefVDD:
|
||||
cal = adc->CAL & ~(_ADC_CAL_SINGLEOFFSET_MASK | _ADC_CAL_SINGLEGAIN_MASK);
|
||||
cal |= ((DEVINFO->ADC0CAL1 & _DEVINFO_ADC0CAL1_VDD_GAIN_MASK) >>
|
||||
_DEVINFO_ADC0CAL1_VDD_GAIN_SHIFT) << _ADC_CAL_SINGLEGAIN_SHIFT;
|
||||
cal |= ((DEVINFO->ADC0CAL1 & _DEVINFO_ADC0CAL1_VDD_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL1_VDD_OFFSET_SHIFT) << _ADC_CAL_SINGLEOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
break;
|
||||
|
||||
case adcRef5VDIFF:
|
||||
cal = adc->CAL & ~(_ADC_CAL_SINGLEOFFSET_MASK | _ADC_CAL_SINGLEGAIN_MASK);
|
||||
cal |= ((DEVINFO->ADC0CAL1 & _DEVINFO_ADC0CAL1_5VDIFF_GAIN_MASK) >>
|
||||
_DEVINFO_ADC0CAL1_5VDIFF_GAIN_SHIFT) << _ADC_CAL_SINGLEGAIN_SHIFT;
|
||||
cal |= ((DEVINFO->ADC0CAL1 & _DEVINFO_ADC0CAL1_5VDIFF_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL1_5VDIFF_OFFSET_SHIFT) << _ADC_CAL_SINGLEOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
break;
|
||||
|
||||
case adcRef2xVDD:
|
||||
/* Gain value not of relevance for this reference, leave as is */
|
||||
cal = adc->CAL & ~_ADC_CAL_SINGLEOFFSET_MASK;
|
||||
cal |= ((DEVINFO->ADC0CAL2 & _DEVINFO_ADC0CAL2_2XVDDVSS_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL2_2XVDDVSS_OFFSET_SHIFT) << _ADC_CAL_SINGLEOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
break;
|
||||
|
||||
/* For external references, the calibration must be determined for the */
|
||||
/* specific application and set explicitly. */
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize ADC.
|
||||
*
|
||||
* @details
|
||||
* Initializes common parts for both single conversion and scan sequence.
|
||||
* In addition, single and/or scan control configuration must be done, please
|
||||
* refer to ADC_InitSingle() and ADC_InitScan() respectively.
|
||||
*
|
||||
* @note
|
||||
* This function will stop any ongoing conversion.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to ADC initialization structure.
|
||||
******************************************************************************/
|
||||
void ADC_Init(ADC_TypeDef *adc, const ADC_Init_TypeDef *init)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
EFM_ASSERT(ADC_REF_VALID(adc));
|
||||
|
||||
/* Make sure conversion is not in progress */
|
||||
adc->CMD = ADC_CMD_SINGLESTOP | ADC_CMD_SCANSTOP;
|
||||
|
||||
tmp = ((uint32_t)(init->ovsRateSel) << _ADC_CTRL_OVSRSEL_SHIFT) |
|
||||
(((uint32_t)(init->timebase) << _ADC_CTRL_TIMEBASE_SHIFT) & _ADC_CTRL_TIMEBASE_MASK) |
|
||||
(((uint32_t)(init->prescale) << _ADC_CTRL_PRESC_SHIFT) & _ADC_CTRL_PRESC_MASK) |
|
||||
((uint32_t)(init->lpfMode) << _ADC_CTRL_LPFMODE_SHIFT) |
|
||||
((uint32_t)(init->warmUpMode) << _ADC_CTRL_WARMUPMODE_SHIFT);
|
||||
|
||||
if (init->tailgate)
|
||||
{
|
||||
tmp |= ADC_CTRL_TAILGATE;
|
||||
}
|
||||
|
||||
adc->CTRL = tmp;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize ADC scan sequence.
|
||||
*
|
||||
* @details
|
||||
* Please refer to ADC_StartScan() for starting scan sequence.
|
||||
*
|
||||
* When selecting an external reference, the gain and offset calibration
|
||||
* must be set explicitly (CAL register). For other references, the
|
||||
* calibration is updated with values defined during manufacturing.
|
||||
*
|
||||
* @note
|
||||
* This function will stop any ongoing scan sequence.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to ADC initialization structure.
|
||||
******************************************************************************/
|
||||
void ADC_InitScan(ADC_TypeDef *adc, const ADC_InitScan_TypeDef *init)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
EFM_ASSERT(ADC_REF_VALID(adc));
|
||||
|
||||
/* Make sure scan sequence is not in progress */
|
||||
adc->CMD = ADC_CMD_SCANSTOP;
|
||||
|
||||
/* Load proper calibration data depending on selected reference */
|
||||
ADC_CalibrateLoadScan(adc, init->reference);
|
||||
|
||||
tmp = ((uint32_t)(init->prsSel) << _ADC_SCANCTRL_PRSSEL_SHIFT) |
|
||||
((uint32_t)(init->acqTime) << _ADC_SCANCTRL_AT_SHIFT) |
|
||||
((uint32_t)(init->reference) << _ADC_SCANCTRL_REF_SHIFT) |
|
||||
init->input |
|
||||
((uint32_t)(init->resolution) << _ADC_SCANCTRL_RES_SHIFT);
|
||||
|
||||
if (init->prsEnable)
|
||||
{
|
||||
tmp |= ADC_SCANCTRL_PRSEN;
|
||||
}
|
||||
|
||||
if (init->leftAdjust)
|
||||
{
|
||||
tmp |= ADC_SCANCTRL_ADJ_LEFT;
|
||||
}
|
||||
|
||||
if (init->diff)
|
||||
{
|
||||
tmp |= ADC_SCANCTRL_DIFF;
|
||||
}
|
||||
|
||||
if (init->rep)
|
||||
{
|
||||
tmp |= ADC_SCANCTRL_REP;
|
||||
}
|
||||
|
||||
adc->SCANCTRL = tmp;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize single ADC sample conversion.
|
||||
*
|
||||
* @details
|
||||
* Please refer to ADC_StartSingle() for starting single conversion.
|
||||
*
|
||||
* When selecting an external reference, the gain and offset calibration
|
||||
* must be set explicitly (CAL register). For other references, the
|
||||
* calibration is updated with values defined during manufacturing.
|
||||
*
|
||||
* @note
|
||||
* This function will stop any ongoing single conversion.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to ADC initialization structure.
|
||||
******************************************************************************/
|
||||
void ADC_InitSingle(ADC_TypeDef *adc, const ADC_InitSingle_TypeDef *init)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
EFM_ASSERT(ADC_REF_VALID(adc));
|
||||
|
||||
/* Make sure single conversion is not in progress */
|
||||
adc->CMD = ADC_CMD_SINGLESTOP;
|
||||
|
||||
/* Load proper calibration data depending on selected reference */
|
||||
ADC_CalibrateLoadSingle(adc, init->reference);
|
||||
|
||||
tmp = ((uint32_t)(init->prsSel) << _ADC_SINGLECTRL_PRSSEL_SHIFT) |
|
||||
((uint32_t)(init->acqTime) << _ADC_SINGLECTRL_AT_SHIFT) |
|
||||
((uint32_t)(init->reference) << _ADC_SINGLECTRL_REF_SHIFT) |
|
||||
((uint32_t)(init->input) << _ADC_SINGLECTRL_INPUTSEL_SHIFT) |
|
||||
((uint32_t)(init->resolution) << _ADC_SINGLECTRL_RES_SHIFT);
|
||||
|
||||
if (init->prsEnable)
|
||||
{
|
||||
tmp |= ADC_SINGLECTRL_PRSEN;
|
||||
}
|
||||
|
||||
if (init->leftAdjust)
|
||||
{
|
||||
tmp |= ADC_SINGLECTRL_ADJ_LEFT;
|
||||
}
|
||||
|
||||
if (init->diff)
|
||||
{
|
||||
tmp |= ADC_SINGLECTRL_DIFF;
|
||||
}
|
||||
|
||||
if (init->rep)
|
||||
{
|
||||
tmp |= ADC_SINGLECTRL_REP;
|
||||
}
|
||||
|
||||
adc->SINGLECTRL = tmp;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Calculate prescaler value used to determine ADC clock.
|
||||
*
|
||||
* @details
|
||||
* The ADC clock is given by: HFPERCLK / (prescale + 1).
|
||||
*
|
||||
* @param[in] adcFreq ADC frequency wanted. The frequency will automatically
|
||||
* be adjusted to be within valid range according to reference manual.
|
||||
*
|
||||
* @param[in] hfperFreq Frequency in Hz of reference HFPER clock. Set to 0 to
|
||||
* use currently defined HFPER clock setting.
|
||||
*
|
||||
* @return
|
||||
* Prescaler value to use for ADC in order to achieve a clock value
|
||||
* <= @p adcFreq.
|
||||
******************************************************************************/
|
||||
uint8_t ADC_PrescaleCalc(uint32_t adcFreq, uint32_t hfperFreq)
|
||||
{
|
||||
uint32_t ret;
|
||||
|
||||
/* Make sure selected ADC clock is within valid range */
|
||||
if (adcFreq > ADC_MAX_CLOCK)
|
||||
{
|
||||
adcFreq = ADC_MAX_CLOCK;
|
||||
}
|
||||
else if (adcFreq < ADC_MIN_CLOCK)
|
||||
{
|
||||
adcFreq = ADC_MIN_CLOCK;
|
||||
}
|
||||
|
||||
/* Use current HFPER frequency? */
|
||||
if (!hfperFreq)
|
||||
{
|
||||
hfperFreq = CMU_ClockFreqGet(cmuClock_HFPER);
|
||||
}
|
||||
|
||||
ret = (hfperFreq + adcFreq - 1) / adcFreq;
|
||||
if (ret)
|
||||
{
|
||||
ret--;
|
||||
}
|
||||
|
||||
return (uint8_t)ret;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Reset ADC to same state as after a HW reset.
|
||||
*
|
||||
* @note
|
||||
* The ROUTE register is NOT reset by this function, in order to allow for
|
||||
* centralized setup of this feature.
|
||||
*
|
||||
* @param[in] adc
|
||||
* Pointer to ADC peripheral register block.
|
||||
******************************************************************************/
|
||||
void ADC_Reset(ADC_TypeDef *adc)
|
||||
{
|
||||
uint32_t cal;
|
||||
|
||||
/* Stop conversions, before resetting other registers. */
|
||||
adc->CMD = ADC_CMD_SINGLESTOP | ADC_CMD_SCANSTOP;
|
||||
adc->SINGLECTRL = _ADC_SINGLECTRL_RESETVALUE;
|
||||
adc->SCANCTRL = _ADC_SCANCTRL_RESETVALUE;
|
||||
adc->CTRL = _ADC_CTRL_RESETVALUE;
|
||||
adc->IEN = _ADC_IEN_RESETVALUE;
|
||||
adc->IFC = _ADC_IFC_MASK;
|
||||
adc->BIASPROG = _ADC_BIASPROG_RESETVALUE;
|
||||
|
||||
cal = adc->CAL & ~(_ADC_CAL_SINGLEOFFSET_MASK | _ADC_CAL_SINGLEGAIN_MASK);
|
||||
cal |= ((DEVINFO->ADC0CAL0 & _DEVINFO_ADC0CAL0_1V25_GAIN_MASK) >>
|
||||
_DEVINFO_ADC0CAL0_1V25_GAIN_SHIFT) << _ADC_CAL_SINGLEGAIN_SHIFT;
|
||||
cal |= ((DEVINFO->ADC0CAL0 & _DEVINFO_ADC0CAL0_1V25_OFFSET_MASK) >>
|
||||
_DEVINFO_ADC0CAL0_1V25_OFFSET_SHIFT) << _ADC_CAL_SINGLEOFFSET_SHIFT;
|
||||
adc->CAL = cal;
|
||||
|
||||
/* Do not reset route register, setting should be done independently */
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Calculate timebase value in order to get a timebase providing at least 1us.
|
||||
*
|
||||
* @param[in] hfperFreq Frequency in Hz of reference HFPER clock. Set to 0 to
|
||||
* use currently defined HFPER clock setting.
|
||||
*
|
||||
* @return
|
||||
* Timebase value to use for ADC in order to achieve at least 1 us.
|
||||
******************************************************************************/
|
||||
uint8_t ADC_TimebaseCalc(uint32_t hfperFreq)
|
||||
{
|
||||
if (!hfperFreq)
|
||||
{
|
||||
hfperFreq = CMU_ClockFreqGet(cmuClock_HFPER);
|
||||
|
||||
/* Just in case, make sure we get non-zero freq for below calculation */
|
||||
if (!hfperFreq)
|
||||
{
|
||||
hfperFreq = 1;
|
||||
}
|
||||
}
|
||||
|
||||
/* Determine number of HFPERCLK cycle >= 1us */
|
||||
hfperFreq += 999999;
|
||||
hfperFreq /= 1000000;
|
||||
|
||||
/* Return timebase value (N+1 format) */
|
||||
return (uint8_t)(hfperFreq - 1);
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup ADC) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,64 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Assert API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32_assert.h"
|
||||
|
||||
#if defined(DEBUG_EFM)
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* EFM internal assert handling.
|
||||
*
|
||||
* This function is invoked through EFM_ASSERT() macro usage only, it should
|
||||
* not be used explicitly.
|
||||
*
|
||||
* Currently this implementation only enters an indefinite loop, allowing
|
||||
* the use of a debugger to determine cause of failure. By defining
|
||||
* DEBUG_EFM_USER to the preprocessor for all files, a user defined version
|
||||
* of this function must be defined and will be invoked instead, possibly
|
||||
* providing output of assertion location.
|
||||
*
|
||||
* Please notice that this function is not used unless DEBUG_EFM is defined
|
||||
* during preprocessing of EFM_ASSERT() usage.
|
||||
*
|
||||
* @par file
|
||||
* Name of source file where assertion failed.
|
||||
*
|
||||
* @par line
|
||||
* Line number in source file where assertion failed.
|
||||
******************************************************************************/
|
||||
void assertEFM(const char *file, int line)
|
||||
{
|
||||
(void)file; /* Unused parameter */
|
||||
(void)line; /* Unused parameter */
|
||||
|
||||
while (1)
|
||||
;
|
||||
}
|
||||
|
||||
#endif /* DEBUG_EFM */
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,287 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Digital to Analog Coversion (DAC) Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32_dac.h"
|
||||
#include "efm32_cmu.h"
|
||||
#include "efm32_assert.h"
|
||||
#include "efm32_bitband.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup DAC
|
||||
* @brief Digital to Analog Coversion (DAC) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/** Validation of DAC channel for assert statements. */
|
||||
#define DAC_CH_VALID(ch) ((ch) <= 1)
|
||||
|
||||
/** Max DAC clock */
|
||||
#define DAC_MAX_CLOCK 1000000
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable/disable DAC channel.
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to DAC peripheral register block.
|
||||
*
|
||||
* @param[in] ch
|
||||
* Channel to enable/disable.
|
||||
*
|
||||
* @param[in] enable
|
||||
* true to enable DAC channel, false to disable.
|
||||
******************************************************************************/
|
||||
void DAC_Enable(DAC_TypeDef *dac, unsigned int ch, bool enable)
|
||||
{
|
||||
volatile uint32_t *reg;
|
||||
|
||||
EFM_ASSERT(DAC_REF_VALID(dac));
|
||||
EFM_ASSERT(DAC_CH_VALID(ch));
|
||||
|
||||
if (!ch)
|
||||
{
|
||||
reg = &(dac->CH0CTRL);
|
||||
}
|
||||
else
|
||||
{
|
||||
reg = &(dac->CH1CTRL);
|
||||
}
|
||||
|
||||
BITBAND_Peripheral(reg, _DAC_CH0CTRL_EN_SHIFT, (unsigned int)enable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize DAC.
|
||||
*
|
||||
* @details
|
||||
* Initializes common parts for both channels. In addition, channel control
|
||||
* configuration must be done, please refer to DAC_InitChannel().
|
||||
*
|
||||
* @note
|
||||
* This function will disable both channels prior to configuration.
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to DAC peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to DAC initialization structure.
|
||||
******************************************************************************/
|
||||
void DAC_Init(DAC_TypeDef *dac, const DAC_Init_TypeDef *init)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
EFM_ASSERT(DAC_REF_VALID(dac));
|
||||
|
||||
/* Make sure both channels are disabled. */
|
||||
BITBAND_Peripheral(&(dac->CH0CTRL), _DAC_CH0CTRL_EN_SHIFT, 0);
|
||||
BITBAND_Peripheral(&(dac->CH1CTRL), _DAC_CH0CTRL_EN_SHIFT, 0);
|
||||
|
||||
/* Load proper calibration data depending on selected reference */
|
||||
switch (init->reference)
|
||||
{
|
||||
case dacRef2V5:
|
||||
dac->CAL = DEVINFO->DAC0CAL1;
|
||||
break;
|
||||
|
||||
case dacRefVDD:
|
||||
dac->CAL = DEVINFO->DAC0CAL2;
|
||||
break;
|
||||
|
||||
default: /* 1.25V */
|
||||
dac->CAL = DEVINFO->DAC0CAL0;
|
||||
break;
|
||||
}
|
||||
|
||||
tmp = ((uint32_t)(init->refresh) << _DAC_CTRL_REFRSEL_SHIFT) |
|
||||
(((uint32_t)(init->prescale) << _DAC_CTRL_PRESC_SHIFT) & _DAC_CTRL_PRESC_MASK) |
|
||||
((uint32_t)(init->reference) << _DAC_CTRL_REFSEL_SHIFT) |
|
||||
((uint32_t)(init->outMode) << _DAC_CTRL_OUTMODE_SHIFT) |
|
||||
((uint32_t)(init->convMode) << _DAC_CTRL_CONVMODE_SHIFT);
|
||||
|
||||
if (init->ch0ResetPre)
|
||||
{
|
||||
tmp |= DAC_CTRL_CH0PRESCRST;
|
||||
}
|
||||
|
||||
if (init->outEnablePRS)
|
||||
{
|
||||
tmp |= DAC_CTRL_OUTENPRS;
|
||||
}
|
||||
|
||||
if (init->sineEnable)
|
||||
{
|
||||
tmp |= DAC_CTRL_SINEMODE;
|
||||
}
|
||||
|
||||
if (init->diff)
|
||||
{
|
||||
tmp |= DAC_CTRL_DIFF;
|
||||
}
|
||||
|
||||
dac->CTRL = tmp;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize DAC channel.
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to DAC peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to DAC initialization structure.
|
||||
*
|
||||
* @param[in] ch
|
||||
* Channel number to initialize.
|
||||
******************************************************************************/
|
||||
void DAC_InitChannel(DAC_TypeDef *dac,
|
||||
const DAC_InitChannel_TypeDef *init,
|
||||
unsigned int ch)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
EFM_ASSERT(DAC_REF_VALID(dac));
|
||||
EFM_ASSERT(DAC_CH_VALID(ch));
|
||||
|
||||
tmp = (uint32_t)(init->prsSel) << _DAC_CH0CTRL_PRSSEL_SHIFT;
|
||||
|
||||
if (init->enable)
|
||||
{
|
||||
tmp |= DAC_CH0CTRL_EN;
|
||||
}
|
||||
|
||||
if (init->prsEnable)
|
||||
{
|
||||
tmp |= DAC_CH0CTRL_PRSEN;
|
||||
}
|
||||
|
||||
if (init->refreshEnable)
|
||||
{
|
||||
tmp |= DAC_CH0CTRL_REFREN;
|
||||
}
|
||||
|
||||
if (ch)
|
||||
{
|
||||
dac->CH1CTRL = tmp;
|
||||
}
|
||||
else
|
||||
{
|
||||
dac->CH0CTRL = tmp;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Calculate prescaler value used to determine DAC clock.
|
||||
*
|
||||
* @details
|
||||
* The DAC clock is given by: HFPERCLK / (prescale ^ 2).
|
||||
*
|
||||
* @param[in] dacFreq DAC frequency wanted. The frequency will automatically
|
||||
* be adjusted to be below max allowed DAC clock.
|
||||
*
|
||||
* @param[in] hfperFreq Frequency in Hz of reference HFPER clock. Set to 0 to
|
||||
* use currently defined HFPER clock setting.
|
||||
*
|
||||
* @return
|
||||
* Prescaler value to use for DAC in order to achieve a clock value
|
||||
* <= @p dacFreq.
|
||||
******************************************************************************/
|
||||
uint8_t DAC_PrescaleCalc(uint32_t dacFreq, uint32_t hfperFreq)
|
||||
{
|
||||
uint32_t ret;
|
||||
|
||||
/* Make sure selected DAC clock is below max value */
|
||||
if (dacFreq > DAC_MAX_CLOCK)
|
||||
{
|
||||
dacFreq = DAC_MAX_CLOCK;
|
||||
}
|
||||
|
||||
/* Use current HFPER frequency? */
|
||||
if (!hfperFreq)
|
||||
{
|
||||
hfperFreq = CMU_ClockFreqGet(cmuClock_HFPER);
|
||||
}
|
||||
|
||||
/* Iterate in order to determine best prescale value. Only a few possible */
|
||||
/* values. We start with lowest prescaler value in order to get first */
|
||||
/* equal or below wanted DAC frequency value. */
|
||||
for (ret = 0; ret <= (_DAC_CTRL_PRESC_MASK >> _DAC_CTRL_PRESC_SHIFT); ret++)
|
||||
{
|
||||
if ((hfperFreq >> ret) <= dacFreq)
|
||||
break;
|
||||
}
|
||||
|
||||
return((uint8_t)ret);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Reset DAC to same state as after a HW reset.
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to ADC peripheral register block.
|
||||
******************************************************************************/
|
||||
void DAC_Reset(DAC_TypeDef *dac)
|
||||
{
|
||||
/* Disable channels, before resetting other registers. */
|
||||
dac->CH0CTRL = _DAC_CH0CTRL_RESETVALUE;
|
||||
dac->CH1CTRL = _DAC_CH1CTRL_RESETVALUE;
|
||||
dac->CTRL = _DAC_CTRL_RESETVALUE;
|
||||
dac->IEN = _DAC_IEN_RESETVALUE;
|
||||
dac->IFC = _DAC_IFC_MASK;
|
||||
dac->CAL = DEVINFO->DAC0CAL0;
|
||||
dac->BIASPROG = _DAC_BIASPROG_RESETVALUE;
|
||||
/* Do not reset route register, setting should be done independently */
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup DAC) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,109 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Debug (DBG) Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32_assert.h"
|
||||
#include "efm32_dbg.h"
|
||||
#include "efm32_cmu.h"
|
||||
#include "efm32_gpio.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup DBG
|
||||
* @brief Debug (DBG) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable Serial Wire Output (SWO) pin.
|
||||
*
|
||||
* @details
|
||||
* The SWO pin (sometimes denoted SWV, serial wire viewer) allows for
|
||||
* miscellaneous output to be passed from the Cortex-M3 debug trace module to
|
||||
* an external debug probe. By default, the debug trace module and pin output
|
||||
* may be disabled.
|
||||
*
|
||||
* Since the SWO pin is only useful when using a debugger, a suggested use
|
||||
* of this function during startup may be:
|
||||
* @verbatim
|
||||
* if (DBG_Connected())
|
||||
* {
|
||||
* DBG_SWOEnable(1);
|
||||
* }
|
||||
* @endverbatim
|
||||
* By checking if debugger is attached, some setup leading to higher energy
|
||||
* consumption when debugger is attached, can be avoided when not using
|
||||
* a debugger.
|
||||
*
|
||||
* Another alternative may be to set the debugger tool chain to configure
|
||||
* the required setup (similar to the content of this function) by some
|
||||
* sort of toolchain scripting during its attach/reset procedure. In that
|
||||
* case, the above suggested code for enabling the SWO pin is not required
|
||||
* in the application.
|
||||
*
|
||||
* @param[in] location
|
||||
* Pin location used for SWO pin on the application in use.
|
||||
******************************************************************************/
|
||||
void DBG_SWOEnable(unsigned int location)
|
||||
{
|
||||
int port;
|
||||
int pin;
|
||||
|
||||
EFM_ASSERT(location < AFCHANLOC_MAX);
|
||||
|
||||
port = AF_DBG_SWO_PORT(location);
|
||||
pin = AF_DBG_SWO_PIN(location);
|
||||
|
||||
/* Port/pin location not defined for device? */
|
||||
if ((pin < 0) || (port < 0))
|
||||
{
|
||||
EFM_ASSERT(0);
|
||||
return;
|
||||
}
|
||||
|
||||
/* Ensure auxiliary clock going to the Cortex debug trace module is enabled */
|
||||
CMU_OscillatorEnable(cmuOsc_AUXHFRCO, true, false);
|
||||
|
||||
/* Set selected pin location for SWO pin and enable it */
|
||||
GPIO_DbgLocationSet(location);
|
||||
GPIO_DbgSWOEnable(true);
|
||||
|
||||
/* Configure SWO pin for output */
|
||||
GPIO_PinModeSet((GPIO_Port_TypeDef)port, pin, gpioModePushPull, 0);
|
||||
}
|
||||
|
||||
/** @} (end addtogroup DBG) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
File diff suppressed because it is too large
Load Diff
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,499 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Energy Management Unit (EMU) Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32_emu.h"
|
||||
#include "efm32_cmu.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EMU
|
||||
* @brief Energy Management Unit (EMU) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/* Consistency check, since restoring assumes similar bitpositions in */
|
||||
/* CMU OSCENCMD and STATUS regs */
|
||||
#if (CMU_STATUS_AUXHFRCOENS != CMU_OSCENCMD_AUXHFRCOEN)
|
||||
#error Conflict in AUXHFRCOENS and AUXHFRCOEN bitpositions
|
||||
#endif
|
||||
#if (CMU_STATUS_HFXOENS != CMU_OSCENCMD_HFXOEN)
|
||||
#error Conflict in HFXOENS and HFXOEN bitpositions
|
||||
#endif
|
||||
#if (CMU_STATUS_LFRCOENS != CMU_OSCENCMD_LFRCOEN)
|
||||
#error Conflict in LFRCOENS and LFRCOEN bitpositions
|
||||
#endif
|
||||
#if (CMU_STATUS_LFXOENS != CMU_OSCENCMD_LFXOEN)
|
||||
#error Conflict in LFXOENS and LFXOEN bitpositions
|
||||
#endif
|
||||
|
||||
/*******************************************************************************
|
||||
************************** LOCAL VARIABLES ********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
/**
|
||||
* CMU configured oscillator selection and oscillator enable status. When a
|
||||
* user configures oscillators, this varaiable shall shadow the configuration.
|
||||
* It is used by the EMU module in order to be able to restore the oscillator
|
||||
* config after having been in certain energy modes (since HW may automatically
|
||||
* alter config when going into an energy mode). It is the responsibility of
|
||||
* the CMU module to keep it up-to-date (or a user if not using the CMU API
|
||||
* for oscillator control).
|
||||
*/
|
||||
static uint16_t cmuStatus;
|
||||
/** @endcond */
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
************************** LOCAL FUNCTIONS ********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Restore oscillators and core clock after having been in EM2 or EM3.
|
||||
******************************************************************************/
|
||||
static void EMU_Restore(void)
|
||||
{
|
||||
uint32_t cmuLocked;
|
||||
|
||||
/* Although we could use the CMU API for most of the below handling, we */
|
||||
/* would like this function to be as efficient as possible. */
|
||||
|
||||
/* CMU registers may be locked */
|
||||
cmuLocked = CMU->LOCK & CMU_LOCK_LOCKKEY_LOCKED;
|
||||
CMU_Unlock();
|
||||
|
||||
/* AUXHFRCO was automatically disabled (except if using debugger). */
|
||||
/* HFXO was automatically disabled. */
|
||||
/* LFRCO/LFXO were possibly disabled by SW in EM3. */
|
||||
/* Restore according to status prior to entering EM. */
|
||||
CMU->OSCENCMD = cmuStatus & (CMU_STATUS_AUXHFRCOENS |
|
||||
CMU_STATUS_HFXOENS |
|
||||
CMU_STATUS_LFRCOENS |
|
||||
CMU_STATUS_LFXOENS);
|
||||
|
||||
/* Restore oscillator used for clocking core */
|
||||
switch (cmuStatus & (CMU_STATUS_HFXOSEL | CMU_STATUS_HFRCOSEL |
|
||||
CMU_STATUS_LFXOSEL | CMU_STATUS_LFRCOSEL))
|
||||
{
|
||||
case CMU_STATUS_LFRCOSEL:
|
||||
/* Wait for LFRCO to stabilize */
|
||||
while (!(CMU->STATUS & CMU_STATUS_LFRCORDY))
|
||||
;
|
||||
CMU->CMD = CMU_CMD_HFCLKSEL_LFRCO;
|
||||
break;
|
||||
|
||||
case CMU_STATUS_LFXOSEL:
|
||||
/* Wait for LFXO to stabilize */
|
||||
while (!(CMU->STATUS & CMU_STATUS_LFXORDY))
|
||||
;
|
||||
CMU->CMD = CMU_CMD_HFCLKSEL_LFXO;
|
||||
break;
|
||||
|
||||
case CMU_STATUS_HFXOSEL:
|
||||
/* Wait for HFXO to stabilize */
|
||||
while (!(CMU->STATUS & CMU_STATUS_HFXORDY))
|
||||
;
|
||||
CMU->CMD = CMU_CMD_HFCLKSEL_HFXO;
|
||||
break;
|
||||
|
||||
default: /* CMU_STATUS_HFRCOSEL */
|
||||
/* If core clock was HFRCO core clock, it is automatically restored to */
|
||||
/* state prior to entering energy mode. No need for further action. */
|
||||
break;
|
||||
}
|
||||
|
||||
/* If HFRCO was disabled before entering Energy Mode, turn it off again */
|
||||
/* as it is automatically enabled by wake up */
|
||||
if ( ! (cmuStatus & CMU_STATUS_HFRCOENS) )
|
||||
{
|
||||
CMU->OSCENCMD = CMU_OSCENCMD_HFRCODIS;
|
||||
}
|
||||
|
||||
/* Restore CMU register locking */
|
||||
if (cmuLocked)
|
||||
{
|
||||
CMU_Lock();
|
||||
}
|
||||
}
|
||||
|
||||
/** @endcond */
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enter energy mode 2 (EM2).
|
||||
*
|
||||
* @details
|
||||
* When entering EM2, the high frequency clocks are disabled, ie HFXO, HFRCO
|
||||
* and AUXHFRCO (for AUXHFRCO, see exception note below). When re-entering
|
||||
* EM0, HFRCO is re-enabled and the core will be clocked by the configured
|
||||
* HFRCO band. This ensures a quick wakeup from EM2.
|
||||
*
|
||||
* However, prior to entering EM2, the core may have been using another
|
||||
* oscillator than HFRCO. The @p restore parameter gives the user the option
|
||||
* to restore all HF oscillators according to state prior to entering EM2,
|
||||
* as well as the clock used to clock the core. This restore procedure is
|
||||
* handled by SW. However, since handled by SW, it will not be restored
|
||||
* before completing the interrupt function(s) waking up the core!
|
||||
*
|
||||
* @note
|
||||
* If restoring core clock to use the HFXO oscillator, which has been
|
||||
* disabled during EM2 mode, this function will stall until the oscillator
|
||||
* has stabilized. Stalling time can be reduced by adding interrupt
|
||||
* support detecting stable oscillator, and an asynchronous switch to the
|
||||
* original oscillator. See CMU documentation. Such a feature is however
|
||||
* outside the scope of the implementation in this function.
|
||||
* @par
|
||||
* If HFXO is re-enabled by this function, and NOT used to clock the core,
|
||||
* this function will not wait for HFXO to stabilize. This must be considered
|
||||
* by the application if trying to use features relying on that oscillator
|
||||
* upon return.
|
||||
* @par
|
||||
* If a debugger is attached, the AUXHFRCO will not be disabled if enabled
|
||||
* upon entering EM2. It will thus remain enabled when returning to EM0
|
||||
* regardless of the @p restore parameter.
|
||||
*
|
||||
* @param[in] restore
|
||||
* @li true - restore oscillators and clocks, see function details.
|
||||
* @li false - do not restore oscillators and clocks, see function details.
|
||||
* @par
|
||||
* The @p restore option should only be used if all clock control is done
|
||||
* via the CMU API.
|
||||
******************************************************************************/
|
||||
void EMU_EnterEM2(bool restore)
|
||||
{
|
||||
/* Auto-update CMU status just in case before entering energy mode. */
|
||||
/* This variable is normally kept up-to-date by the CMU API. */
|
||||
cmuStatus = (uint16_t)(CMU->STATUS);
|
||||
|
||||
/* Enter Cortex-M3 deep sleep mode */
|
||||
SCB->SCR |= SCB_SCR_SLEEPDEEP_Msk;
|
||||
__WFI();
|
||||
|
||||
/* Restore oscillators/clocks if specified */
|
||||
if (restore)
|
||||
{
|
||||
EMU_Restore();
|
||||
}
|
||||
/* If not restoring, and original clock was not HFRCO, we have to */
|
||||
/* update CMSIS core clock variable since core clock has changed */
|
||||
/* to using HFRCO. */
|
||||
else if (!(cmuStatus & CMU_STATUS_HFRCOSEL))
|
||||
{
|
||||
SystemCoreClockUpdate();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enter energy mode 3 (EM3).
|
||||
*
|
||||
* @details
|
||||
* When entering EM3, the high frequency clocks are disabled by HW, ie HFXO,
|
||||
* HFRCO and AUXHFRCO (for AUXHFRCO, see exception note below). In addition,
|
||||
* the low frequency clocks, ie LFXO and LFRCO are disabled by SW. When
|
||||
* re-entering EM0, HFRCO is re-enabled and the core will be clocked by the
|
||||
* configured HFRCO band. This ensures a quick wakeup from EM3.
|
||||
*
|
||||
* However, prior to entering EM3, the core may have been using another
|
||||
* oscillator than HFRCO. The @p restore parameter gives the user the option
|
||||
* to restore all HF/LF oscillators according to state prior to entering EM3,
|
||||
* as well as the clock used to clock the core. This restore procedure is
|
||||
* handled by SW. However, since handled by SW, it will not be restored
|
||||
* before completing the interrupt function(s) waking up the core!
|
||||
*
|
||||
* @note
|
||||
* If restoring core clock to use an oscillator other than HFRCO, this
|
||||
* function will stall until the oscillator has stabilized. Stalling time
|
||||
* can be reduced by adding interrupt support detecting stable oscillator,
|
||||
* and an asynchronous switch to the original oscillator. See CMU
|
||||
* documentation. Such a feature is however outside the scope of the
|
||||
* implementation in this function.
|
||||
* @par
|
||||
* If HFXO/LFXO/LFRCO are re-enabled by this function, and NOT used to clock
|
||||
* the core, this function will not wait for those oscillators to stabilize.
|
||||
* This must be considered by the application if trying to use features
|
||||
* relying on those oscillators upon return.
|
||||
* @par
|
||||
* If a debugger is attached, the AUXHFRCO will not be disabled if enabled
|
||||
* upon entering EM3. It will thus remain enabled when returning to EM0
|
||||
* regardless of the @p restore parameter.
|
||||
*
|
||||
* @param[in] restore
|
||||
* @li true - restore oscillators and clocks, see function details.
|
||||
* @li false - do not restore oscillators and clocks, see function details.
|
||||
* @par
|
||||
* The @p restore option should only be used if all clock control is done
|
||||
* via the CMU API.
|
||||
******************************************************************************/
|
||||
void EMU_EnterEM3(bool restore)
|
||||
{
|
||||
uint32_t cmuLocked;
|
||||
|
||||
/* Auto-update CMU status just in case before entering energy mode. */
|
||||
/* This variable is normally kept up-to-date by the CMU API. */
|
||||
cmuStatus = (uint16_t)(CMU->STATUS);
|
||||
|
||||
/* CMU registers may be locked */
|
||||
cmuLocked = CMU->LOCK & CMU_LOCK_LOCKKEY_LOCKED;
|
||||
CMU_Unlock();
|
||||
|
||||
/* Disable LF oscillators */
|
||||
CMU->OSCENCMD = CMU_OSCENCMD_LFXODIS | CMU_OSCENCMD_LFRCODIS;
|
||||
|
||||
/* Restore CMU register locking */
|
||||
if (cmuLocked)
|
||||
{
|
||||
CMU_Lock();
|
||||
}
|
||||
|
||||
/* Enter Cortex-M3 deep sleep mode */
|
||||
SCB->SCR |= SCB_SCR_SLEEPDEEP_Msk;
|
||||
__WFI();
|
||||
|
||||
/* Restore oscillators/clocks if specified */
|
||||
if (restore)
|
||||
{
|
||||
EMU_Restore();
|
||||
}
|
||||
/* If not restoring, and original clock was not HFRCO, we have to */
|
||||
/* update CMSIS core clock variable since core clock has changed */
|
||||
/* to using HFRCO. */
|
||||
else if (!(cmuStatus & CMU_STATUS_HFRCOSEL))
|
||||
{
|
||||
SystemCoreClockUpdate();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enter energy mode 4 (EM4).
|
||||
*
|
||||
* @note
|
||||
* Only a power on reset or external reset pin can wake the device from EM4.
|
||||
******************************************************************************/
|
||||
void EMU_EnterEM4(void)
|
||||
{
|
||||
int i;
|
||||
|
||||
/* Make sure register write lock is disabled */
|
||||
EMU->LOCK = EMU_LOCK_LOCKKEY_UNLOCK;
|
||||
|
||||
for (i = 0; i < 4; i++)
|
||||
{
|
||||
EMU->CTRL = (2 << _EMU_CTRL_EM4CTRL_SHIFT);
|
||||
EMU->CTRL = (3 << _EMU_CTRL_EM4CTRL_SHIFT);
|
||||
}
|
||||
EMU->CTRL = (2 << _EMU_CTRL_EM4CTRL_SHIFT);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Power down memory block.
|
||||
*
|
||||
* @param[in] blocks
|
||||
* Specifies a logical OR of bits indicating memory blocks to power down.
|
||||
* Bit 0 selects block 1, bit 1 selects block 2, etc. Memory block 0 cannot
|
||||
* be disabled. Please refer to the EFM32 reference manual for available
|
||||
* memory blocks for a device.
|
||||
*
|
||||
* @note
|
||||
* Only a reset can make the specified memory block(s) available for use
|
||||
* after having been powered down. Function will be void for devices not
|
||||
* supporting this feature.
|
||||
******************************************************************************/
|
||||
void EMU_MemPwrDown(uint32_t blocks)
|
||||
{
|
||||
#if defined(_EMU_MEMCTRL_RESETVALUE)
|
||||
EFM_ASSERT(blocks <= _EMU_MEMCTRL_MASK);
|
||||
|
||||
EMU->MEMCTRL = blocks;
|
||||
#else
|
||||
(void)blocks;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Update EMU module with CMU oscillator selection/enable status.
|
||||
*
|
||||
* @details
|
||||
* When entering EM2 and EM3, the HW may change the core clock oscillator
|
||||
* used, as well as disabling some oscillators. The user may optionally select
|
||||
* to restore the oscillators after waking up from EM2 and EM3 through the
|
||||
* SW API.
|
||||
*
|
||||
* However, in order to support this in a safe way, the EMU module must
|
||||
* be kept up-to-date on the actual selected configuration. The CMU
|
||||
* module must keep the EMU module up-to-date.
|
||||
*
|
||||
* This function is mainly intended for internal use by the CMU module,
|
||||
* but if the applications changes oscillator configurations without
|
||||
* using the CMU API, this function can be used to keep the EMU module
|
||||
* up-to-date.
|
||||
******************************************************************************/
|
||||
void EMU_UpdateOscConfig(void)
|
||||
{
|
||||
/* Fetch current configuration */
|
||||
cmuStatus = (uint16_t)(CMU->STATUS);
|
||||
}
|
||||
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Update EMU module with Energy Mode 4 configuration
|
||||
*
|
||||
* @param[in] em4init
|
||||
* Energy Mode 4 configuration structure
|
||||
******************************************************************************/
|
||||
void EMU_EM4Init(EMU_EM4Init_TypeDef *em4init)
|
||||
{
|
||||
uint32_t em4conf = EMU->EM4CONF;
|
||||
|
||||
/* Clear fields that will be reconfigured */
|
||||
em4conf &= ~(
|
||||
_EMU_EM4CONF_LOCKCONF_MASK|
|
||||
_EMU_EM4CONF_OSC_MASK|
|
||||
_EMU_EM4CONF_BURTCWU_MASK|
|
||||
_EMU_EM4CONF_VREGEN_MASK);
|
||||
|
||||
/* Configure new settings */
|
||||
em4conf |= (
|
||||
(em4init->lockConfig << _EMU_EM4CONF_LOCKCONF_SHIFT)|
|
||||
(em4init->osc)|
|
||||
(em4init->buRtcWakeup << _EMU_EM4CONF_BURTCWU_SHIFT)|
|
||||
(em4init->vreg << _EMU_EM4CONF_VREGEN_SHIFT));
|
||||
|
||||
/* Apply configuration. Note that lock can be set after this stage. */
|
||||
EMU->EM4CONF = em4conf;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure BackUp Power Domain settings
|
||||
*
|
||||
* @note
|
||||
* stig note to self: Touches RMU->CTRL BUPD?
|
||||
*
|
||||
* @param[in] bupdInit
|
||||
* Backup power domain initialization structure
|
||||
******************************************************************************/
|
||||
void EMU_BUPDInit(EMU_BUPDInit_TypeDef *bupdInit)
|
||||
{
|
||||
uint32_t reg;
|
||||
|
||||
EFM_ASSERT(bupdInit->inactiveThresRange < 4);
|
||||
EFM_ASSERT(bupdInit->inactiveThreshold < 4);
|
||||
EFM_ASSERT(bupdInit->activeThresRange < 4);
|
||||
EFM_ASSERT(bupdInit->activeThreshold < 4);
|
||||
|
||||
/* Set power connection configuration */
|
||||
reg = EMU->PWRCONF & ~(
|
||||
_EMU_PWRCONF_PWRRES_MASK|
|
||||
_EMU_PWRCONF_VOUTSTRONG_MASK|
|
||||
_EMU_PWRCONF_VOUTMED_MASK|
|
||||
_EMU_PWRCONF_VOUTWEAK_MASK);
|
||||
|
||||
reg |= (bupdInit->resistor|
|
||||
(bupdInit->voutStrong << _EMU_PWRCONF_VOUTSTRONG_SHIFT)|
|
||||
(bupdInit->voutMed << _EMU_PWRCONF_VOUTMED_SHIFT)|
|
||||
(bupdInit->voutWeak << _EMU_PWRCONF_VOUTWEAK_SHIFT));
|
||||
|
||||
EMU->PWRCONF = reg;
|
||||
|
||||
/* Set backup domain inactive mode configuration */
|
||||
reg = EMU->BUINACT & ~(
|
||||
_EMU_BUINACT_PWRCON_MASK|
|
||||
_EMU_BUINACT_BUENRANGE_MASK|
|
||||
_EMU_BUINACT_BUENTHRES_MASK);
|
||||
|
||||
reg |= (bupdInit->inactivePower|
|
||||
(bupdInit->inactiveThresRange << _EMU_BUINACT_BUENRANGE_SHIFT)|
|
||||
(bupdInit->inactiveThreshold << _EMU_BUINACT_BUENTHRES_SHIFT));
|
||||
|
||||
EMU->BUINACT = reg;
|
||||
|
||||
/* Set backup domain active mode configuration */
|
||||
reg = EMU->BUACT & ~(
|
||||
_EMU_BUACT_PWRCON_MASK|
|
||||
_EMU_BUACT_BUEXRANGE_MASK|
|
||||
_EMU_BUACT_BUEXTHRES_MASK);
|
||||
|
||||
reg |= (bupdInit->activePower|
|
||||
(bupdInit->activeThresRange << _EMU_BUACT_BUEXRANGE_SHIFT)|
|
||||
(bupdInit->activeThreshold << _EMU_BUACT_BUEXTHRES_SHIFT));
|
||||
|
||||
EMU->BUACT = reg;
|
||||
|
||||
/* Set power control configuration */
|
||||
reg = EMU->BUCTRL & ~(
|
||||
_EMU_BUCTRL_PROBE_MASK|
|
||||
_EMU_BUCTRL_BODCAL_MASK|
|
||||
_EMU_BUCTRL_STATEN_MASK|
|
||||
_EMU_BUCTRL_EN_MASK);
|
||||
|
||||
/* Note use of ->enable to both enable BUPD, use BU_VIN pin input and
|
||||
release reset */
|
||||
reg |= (bupdInit->probe|
|
||||
(bupdInit->bodCal << _EMU_BUCTRL_BODCAL_SHIFT)|
|
||||
(bupdInit->statusPinEnable << _EMU_BUCTRL_STATEN_SHIFT)|
|
||||
(bupdInit->enable << _EMU_BUCTRL_EN_SHIFT));
|
||||
|
||||
/* Enable configuration */
|
||||
EMU->BUCTRL = reg;
|
||||
|
||||
/* If enable is true, enable BU_VIN input power pin, if not disable it */
|
||||
EMU_BUPinEnable(bupdInit->enable);
|
||||
|
||||
/* If enable is true, release BU reset, if not keep reset asserted */
|
||||
BITBAND_Peripheral(&(RMU->CTRL), _RMU_CTRL_BURSTEN_SHIFT, !bupdInit->enable);
|
||||
}
|
||||
|
||||
#endif
|
||||
|
||||
|
||||
/** @} (end addtogroup EMU) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,487 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief General Purpose IO (GPIO) peripheral API for EFM32
|
||||
* devices.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32_gpio.h"
|
||||
#include "efm32_bitband.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup GPIO
|
||||
* @brief General Purpose Input/Output (GPIO) API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/** Validation of pin typically usable in assert statements. */
|
||||
#define GPIO_DRIVEMODE_VALID(mode) ((mode) <= 3)
|
||||
|
||||
/** Validation of pin typically usable in assert statements. */
|
||||
#define GPIO_PIN_VALID(pin) ((pin) < 16)
|
||||
|
||||
/** Validation of port typically usable in assert statements. */
|
||||
#define GPIO_PORT_VALID(port) ((port) <= gpioPortF)
|
||||
|
||||
/** @endcond */
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Sets the pin location of the debug pins (Serial Wire interface).
|
||||
*
|
||||
* @note
|
||||
* Changing the pins used for debugging uncontrolled, may result in a lockout.
|
||||
*
|
||||
* @param[in] location
|
||||
* The debug pin location to use (0-3).
|
||||
******************************************************************************/
|
||||
void GPIO_DbgLocationSet(unsigned int location)
|
||||
{
|
||||
EFM_ASSERT(location < AFCHANLOC_MAX);
|
||||
|
||||
GPIO->ROUTE = (GPIO->ROUTE & ~_GPIO_ROUTE_SWLOCATION_MASK) |
|
||||
(location << _GPIO_ROUTE_SWLOCATION_SHIFT);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Sets the drive mode for a GPIO port.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] mode
|
||||
* Drive mode to use for port.
|
||||
******************************************************************************/
|
||||
void GPIO_DriveModeSet(GPIO_Port_TypeDef port, GPIO_DriveMode_TypeDef mode)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port) && GPIO_DRIVEMODE_VALID(mode));
|
||||
|
||||
GPIO->P[port].CTRL = (GPIO->P[port].CTRL & ~(_GPIO_P_CTRL_DRIVEMODE_MASK))
|
||||
| (mode << _GPIO_P_CTRL_DRIVEMODE_SHIFT);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure GPIO interrupt.
|
||||
*
|
||||
* @details
|
||||
* If reconfiguring a GPIO interrupt that is already enabled, it is generally
|
||||
* recommended to disable it first, see GPIO_Disable().
|
||||
*
|
||||
* The actual GPIO interrupt handler must be in place before enabling the
|
||||
* interrupt.
|
||||
*
|
||||
* Notice that any pending interrupt for the selected pin is cleared by this
|
||||
* function.
|
||||
*
|
||||
* @note
|
||||
* A certain pin number can only be associated with one port. Ie, if GPIO
|
||||
* interrupt 1 is assigned to port A/pin 1, then it is not possibly to use
|
||||
* pin 1 from any other ports for interrupts. Please refer to the reference
|
||||
* manual.
|
||||
*
|
||||
* @param[in] port
|
||||
* The port to associate with @p pin.
|
||||
*
|
||||
* @param[in] pin
|
||||
* The GPIO interrupt number (= port pin).
|
||||
*
|
||||
* @param[in] risingEdge
|
||||
* Set to true if interrupts shall be enabled on rising edge, otherwise false.
|
||||
*
|
||||
* @param[in] fallingEdge
|
||||
* Set to true if interrupts shall be enabled on falling edge, otherwise false.
|
||||
*
|
||||
* @param[in] enable
|
||||
* Set to true if interrupt shall be enabled after configuration completed,
|
||||
* false to leave disabled. See GPIO_IntDisable() and GPIO_IntEnable().
|
||||
******************************************************************************/
|
||||
void GPIO_IntConfig(GPIO_Port_TypeDef port,
|
||||
unsigned int pin,
|
||||
bool risingEdge,
|
||||
bool fallingEdge,
|
||||
bool enable)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port) && GPIO_PIN_VALID(pin));
|
||||
|
||||
/* There are two registers controlling the interrupt configuration:
|
||||
* The EXTIPSELL register controls pins 0-7 and EXTIPSELH controls
|
||||
* pins 8-15. */
|
||||
if (pin < 8)
|
||||
{
|
||||
GPIO->EXTIPSELL = (GPIO->EXTIPSELL & ~(0xF << (4 * pin))) |
|
||||
(port << (4 * pin));
|
||||
}
|
||||
else
|
||||
{
|
||||
tmp = pin - 8;
|
||||
GPIO->EXTIPSELH = (GPIO->EXTIPSELH & ~(0xF << (4 * tmp))) |
|
||||
(port << (4 * tmp));
|
||||
}
|
||||
|
||||
/* Enable/disable rising edge */
|
||||
BITBAND_Peripheral(&(GPIO->EXTIRISE), pin, (unsigned int)risingEdge);
|
||||
|
||||
/* Enable/disable falling edge */
|
||||
BITBAND_Peripheral(&(GPIO->EXTIFALL), pin, (unsigned int)fallingEdge);
|
||||
|
||||
/* Clear any pending interrupt */
|
||||
GPIO->IFC = 1 << pin;
|
||||
|
||||
/* Finally enable/disable interrupt */
|
||||
BITBAND_Peripheral(&(GPIO->IEN), pin, (unsigned int)enable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Read the pad value for a single pin in a GPIO port.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] pin
|
||||
* The pin number to read.
|
||||
*
|
||||
* @return
|
||||
* The pin value, 0 or 1.
|
||||
******************************************************************************/
|
||||
unsigned int GPIO_PinInGet(GPIO_Port_TypeDef port, unsigned int pin)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port) && GPIO_PIN_VALID(pin));
|
||||
|
||||
return((unsigned int)((GPIO->P[port].DIN >> pin) & 0x1));
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set the mode for a GPIO pin.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] pin
|
||||
* The pin number in the port.
|
||||
*
|
||||
* @param[in] mode
|
||||
* The desired pin mode.
|
||||
*
|
||||
* @param[in] out
|
||||
* Value to set for pin in DOUT register. The DOUT setting is important for
|
||||
* even some input mode configurations, determining pull-up/down direction.
|
||||
* Notice that this parameter is not used if disabling a pin, leaving the
|
||||
* corresponding DOUT bit unchanged.
|
||||
******************************************************************************/
|
||||
void GPIO_PinModeSet(GPIO_Port_TypeDef port,
|
||||
unsigned int pin,
|
||||
GPIO_Mode_TypeDef mode,
|
||||
unsigned int out)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port) && GPIO_PIN_VALID(pin));
|
||||
|
||||
/* If disabling pin, do not modify DOUT in order to reduce chance for */
|
||||
/* glitch/spike (may not be sufficient precaution in all use cases) */
|
||||
if (mode != gpioModeDisabled)
|
||||
{
|
||||
if (out)
|
||||
{
|
||||
GPIO->P[port].DOUTSET = 1 << pin;
|
||||
}
|
||||
else
|
||||
{
|
||||
GPIO->P[port].DOUTCLR = 1 << pin;
|
||||
}
|
||||
}
|
||||
|
||||
/* There are two registers controlling the pins for each port. The MODEL
|
||||
* register controls pins 0-7 and MODEH controls pins 8-15. */
|
||||
if (pin < 8)
|
||||
{
|
||||
GPIO->P[port].MODEL = (GPIO->P[port].MODEL & ~(0xF << (pin * 4))) |
|
||||
(mode << (pin * 4));
|
||||
}
|
||||
else
|
||||
{
|
||||
GPIO->P[port].MODEH = (GPIO->P[port].MODEH & ~(0xF << ((pin - 8) * 4))) |
|
||||
(mode << ((pin - 8) * 4));
|
||||
}
|
||||
|
||||
if (mode == gpioModeDisabled)
|
||||
{
|
||||
if (out)
|
||||
{
|
||||
GPIO->P[port].DOUTSET = 1 << pin;
|
||||
}
|
||||
else
|
||||
{
|
||||
GPIO->P[port].DOUTCLR = 1 << pin;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set a single pin in GPIO data out port register to 0.
|
||||
*
|
||||
* @note
|
||||
* In order for the setting to take effect on the output pad, the pin must
|
||||
* have been configured properly. If not, it will take effect whenever the
|
||||
* pin has been properly configured.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] pin
|
||||
* The pin to set.
|
||||
******************************************************************************/
|
||||
void GPIO_PinOutClear(GPIO_Port_TypeDef port, unsigned int pin)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port) && GPIO_PIN_VALID(pin));
|
||||
|
||||
GPIO->P[port].DOUTCLR = 1 << pin;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get current setting for a pin in a GPIO port data out register.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] pin
|
||||
* The pin to get setting for.
|
||||
*
|
||||
* @return
|
||||
* The DOUT setting for the requested pin, 0 or 1.
|
||||
******************************************************************************/
|
||||
unsigned int GPIO_PinOutGet(GPIO_Port_TypeDef port, unsigned int pin)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port) && GPIO_PIN_VALID(pin));
|
||||
|
||||
return((unsigned int)((GPIO->P[port].DOUT >> pin) & 0x1));
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set a single pin in GPIO data out register to 1.
|
||||
*
|
||||
* @note
|
||||
* In order for the setting to take effect on the output pad, the pin must
|
||||
* have been configured properly. If not, it will take effect whenever the
|
||||
* pin has been properly configured.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] pin
|
||||
* The pin to set.
|
||||
******************************************************************************/
|
||||
void GPIO_PinOutSet(GPIO_Port_TypeDef port, unsigned int pin)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port) && GPIO_PIN_VALID(pin));
|
||||
|
||||
GPIO->P[port].DOUTSET = 1 << pin;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Toggle a single pin in GPIO port data out register.
|
||||
*
|
||||
* @note
|
||||
* In order for the setting to take effect on the output pad, the pin must
|
||||
* have been configured properly. If not, it will take effect whenever the
|
||||
* pin has been properly configured.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] pin
|
||||
* The pin to toggle.
|
||||
******************************************************************************/
|
||||
void GPIO_PinOutToggle(GPIO_Port_TypeDef port, unsigned int pin)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port) && GPIO_PIN_VALID(pin));
|
||||
|
||||
GPIO->P[port].DOUTTGL = 1 << pin;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Read the pad values for GPIO port.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
******************************************************************************/
|
||||
uint32_t GPIO_PortInGet(GPIO_Port_TypeDef port)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port));
|
||||
|
||||
return(GPIO->P[port].DIN & _GPIO_P_DIN_DIN_MASK);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set bits in DOUT register for a port to 0.
|
||||
*
|
||||
* @note
|
||||
* In order for the setting to take effect on the output pad, the pin must
|
||||
* have been configured properly. If not, it will take effect whenever the
|
||||
* pin has been properly configured.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] pins
|
||||
* Bit mask for bits to clear in DOUT register.
|
||||
******************************************************************************/
|
||||
void GPIO_PortOutClear(GPIO_Port_TypeDef port, uint32_t pins)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port));
|
||||
|
||||
GPIO->P[port].DOUTCLR = pins & _GPIO_P_DOUTCLR_DOUTCLR_MASK;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get current setting for a GPIO port data out register.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @return
|
||||
* The data out setting for the requested port.
|
||||
******************************************************************************/
|
||||
uint32_t GPIO_PortOutGet(GPIO_Port_TypeDef port)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port));
|
||||
|
||||
return(GPIO->P[port].DOUT & _GPIO_P_DOUT_DOUT_MASK);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set bits GPIO data out register to 1.
|
||||
*
|
||||
* @note
|
||||
* In order for the setting to take effect on the respective output pads, the
|
||||
* pins must have been configured properly. If not, it will take effect
|
||||
* whenever the pin has been properly configured.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] pins
|
||||
* Bit mask for bits to set to 1 in DOUT register.
|
||||
******************************************************************************/
|
||||
void GPIO_PortOutSet(GPIO_Port_TypeDef port, uint32_t pins)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port));
|
||||
|
||||
GPIO->P[port].DOUTSET = pins & _GPIO_P_DOUTSET_DOUTSET_MASK;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set GPIO port data out register.
|
||||
*
|
||||
* @note
|
||||
* In order for the setting to take effect on the respective output pads, the
|
||||
* pins must have been configured properly. If not, it will take effect
|
||||
* whenever the pin has been properly configured.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] val
|
||||
* Value to write to port data out register.
|
||||
*
|
||||
* @param[in] mask
|
||||
* Mask indicating which bits to modify.
|
||||
******************************************************************************/
|
||||
void GPIO_PortOutSetVal(GPIO_Port_TypeDef port, uint32_t val, uint32_t mask)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port));
|
||||
|
||||
GPIO->P[port].DOUT = (GPIO->P[port].DOUT & ~mask) | (val & mask);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Toggle a single pin in GPIO port data out register.
|
||||
*
|
||||
* @note
|
||||
* In order for the setting to take effect on the output pad, the pin must
|
||||
* have been configured properly. If not, it will take effect whenever the
|
||||
* pin has been properly configured.
|
||||
*
|
||||
* @param[in] port
|
||||
* The GPIO port to access.
|
||||
*
|
||||
* @param[in] pins
|
||||
* Bitmask with pins to toggle.
|
||||
******************************************************************************/
|
||||
void GPIO_PortOutToggle(GPIO_Port_TypeDef port, uint32_t pins)
|
||||
{
|
||||
EFM_ASSERT(GPIO_PORT_VALID(port));
|
||||
|
||||
GPIO->P[port].DOUTTGL = pins & _GPIO_P_DOUTTGL_DOUTTGL_MASK;
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup GPIO) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,789 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Inter-integrated Circuit (I2C) Peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#include "efm32.h"
|
||||
#include "efm32_i2c.h"
|
||||
#include "efm32_cmu.h"
|
||||
#include "efm32_bitband.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup I2C
|
||||
* @brief Inter-integrated Circuit (I2C) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/** Validation of I2C register block pointer reference for assert statements. */
|
||||
#if defined(_EFM32_GECKO_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
#define I2C_REF_VALID(ref) ((ref) == I2C0)
|
||||
#endif
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
#define I2C_REF_VALID(ref) ((ref == I2C0) || (ref == I2C1))
|
||||
#endif
|
||||
|
||||
/** Error flags indicating I2C transfer has failed somehow. */
|
||||
/* Notice that I2C_IF_TXOF (transmit overflow) is not really possible with */
|
||||
/* this SW supporting master mode. Likewise for I2C_IF_RXUF (receive underflow) */
|
||||
/* RXUF is only likely to occur with this SW if using a debugger peeking into */
|
||||
/* RXDATA register. Thus, we ignore those types of fault. */
|
||||
#define I2C_IF_ERRORS (I2C_IF_BUSERR | I2C_IF_ARBLOST)
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
******************************** ENUMS ************************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/** Master mode transfer states. */
|
||||
typedef enum
|
||||
{
|
||||
i2cStateStartAddrSend, /**< Send start + (first part of) address. */
|
||||
i2cStateAddrWFAckNack, /**< Wait for ACK/NACK on (first part of) address. */
|
||||
i2cStateAddrWF2ndAckNack, /**< Wait for ACK/NACK on second part of 10 bit address. */
|
||||
i2cStateRStartAddrSend, /**< Send repeated start + (first part of) address. */
|
||||
i2cStateRAddrWFAckNack, /**< Wait for ACK/NACK on address sent after repeated start. */
|
||||
i2cStateDataSend, /**< Send data. */
|
||||
i2cStateDataWFAckNack, /**< Wait for ACK/NACK on data sent. */
|
||||
i2cStateWFData, /**< Wait for data. */
|
||||
i2cStateWFStopSent, /**< Wait for STOP to have been transmitted. */
|
||||
i2cStateDone /**< Transfer completed successfully. */
|
||||
} I2C_TransferState_TypeDef;
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* STRUCTS ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/** Structure used to store state information on an ongoing master mode transfer. */
|
||||
typedef struct
|
||||
{
|
||||
/** Current state. */
|
||||
I2C_TransferState_TypeDef state;
|
||||
|
||||
/** Result return code. */
|
||||
I2C_TransferReturn_TypeDef result;
|
||||
|
||||
/** Offset in current sequence buffer. */
|
||||
uint16_t offset;
|
||||
|
||||
/* Index to current sequence buffer in use. */
|
||||
uint8_t bufIndx;
|
||||
|
||||
/** Reference to I2C transfer sequence definition provided by user. */
|
||||
I2C_TransferSeq_TypeDef *seq;
|
||||
} I2C_Transfer_TypeDef;
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
***************************** LOCAL DATA *******^**************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/**
|
||||
* Lookup table for Nlow + Nhigh setting defined by CLHR. Set undefined
|
||||
* index (0x3) to reflect default setting just in case.
|
||||
*/
|
||||
static const uint8_t i2cNSum[] = { 4 + 4, 6 + 3, 11 + 3, 4 + 4 };
|
||||
|
||||
/** Transfer state info for ongoing master mode transfer */
|
||||
static I2C_Transfer_TypeDef i2cTransfer[I2C_COUNT];
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get current configured I2C bus frequency.
|
||||
*
|
||||
* @details
|
||||
* This frequency is only of relevance when acting as master.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Current I2C frequency in Hz.
|
||||
******************************************************************************/
|
||||
uint32_t I2C_BusFreqGet(I2C_TypeDef *i2c)
|
||||
{
|
||||
uint32_t hfperclk;
|
||||
uint32_t n;
|
||||
|
||||
/* Max frequency is given by fSCL = fHFPERCLK/((Nlow + Nhigh)(DIV + 1) + 4) */
|
||||
hfperclk = CMU_ClockFreqGet(cmuClock_HFPER);
|
||||
n = (uint32_t)(i2cNSum[(i2c->CTRL & _I2C_CTRL_CLHR_MASK) >> _I2C_CTRL_CLHR_SHIFT]);
|
||||
|
||||
return(hfperclk / ((n * (i2c->CLKDIV + 1)) + 4));
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set I2C bus frequency.
|
||||
*
|
||||
* @details
|
||||
* The bus frequency is only of relevance when acting as a master. The bus
|
||||
* frequency should not be set higher than the max frequency accepted by the
|
||||
* slowest device on the bus.
|
||||
*
|
||||
* Notice that due to asymmetric requirements on low and high I2C clock
|
||||
* cycles by the I2C specification, the actual max frequency allowed in order
|
||||
* to comply with the specification may be somewhat lower than expected.
|
||||
*
|
||||
* Please refer to the reference manual, details on I2C clock generation,
|
||||
* for max allowed theoretical frequencies for different modes.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @param[in] refFreq
|
||||
* I2C reference clock frequency in Hz that will be used. If set to 0,
|
||||
* the currently configured reference clock is assumed. Setting it to a higher
|
||||
* than actual configured value only has the consequence of reducing the real
|
||||
* I2C frequency.
|
||||
*
|
||||
* @param[in] freq
|
||||
* Bus frequency to set (actual bus speed may be lower due to integer
|
||||
* prescaling). Safe (according to I2C specification) max frequencies for
|
||||
* standard, fast and fast+ modes are available using I2C_FREQ_ defines.
|
||||
* (Using I2C_FREQ_ defines requires corresponding setting of @p type.)
|
||||
* Slowest slave device on bus must always be considered.
|
||||
*
|
||||
* @param[in] type
|
||||
* Clock low to high ratio type to use. If not using i2cClockHLRStandard,
|
||||
* make sure all devices on the bus support the specified mode. Using a
|
||||
* non-standard ratio is useful to achieve higher bus clock in fast and
|
||||
* fast+ modes.
|
||||
******************************************************************************/
|
||||
void I2C_BusFreqSet(I2C_TypeDef *i2c,
|
||||
uint32_t refFreq,
|
||||
uint32_t freq,
|
||||
I2C_ClockHLR_TypeDef type)
|
||||
{
|
||||
uint32_t n;
|
||||
uint32_t div;
|
||||
|
||||
/* Unused parameter */
|
||||
(void)type;
|
||||
|
||||
/* Avoid divide by 0 */
|
||||
EFM_ASSERT(freq);
|
||||
if (!freq)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
/* Frequency is given by fSCL = fHFPERCLK/((Nlow + Nhigh)(DIV + 1) + 4), thus */
|
||||
/* DIV = ((fHFPERCLK - 4fSCL)/((Nlow + Nhigh)fSCL)) - 1 */
|
||||
|
||||
if (!refFreq)
|
||||
{
|
||||
refFreq = CMU_ClockFreqGet(cmuClock_HFPER);
|
||||
}
|
||||
n = (uint32_t)(i2cNSum[(i2c->CTRL & _I2C_CTRL_CLHR_MASK) >> _I2C_CTRL_CLHR_SHIFT]);
|
||||
|
||||
div = (refFreq - (4 * freq)) / (n * freq);
|
||||
EFM_ASSERT(div);
|
||||
if (div)
|
||||
{
|
||||
div--;
|
||||
}
|
||||
|
||||
/* Clock divisor must be at least 1 in slave mode according to reference */
|
||||
/* manual (in which case there is normally no need to set bus frequency). */
|
||||
if ((i2c->CTRL & I2C_CTRL_SLAVE) && !div)
|
||||
{
|
||||
div = 1;
|
||||
}
|
||||
|
||||
EFM_ASSERT(div <= _I2C_CLKDIV_DIV_MASK);
|
||||
i2c->CLKDIV = div;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable/disable I2C.
|
||||
*
|
||||
* @note
|
||||
* After enabling the I2C (from being disabled), the I2C is in BUSY state.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @param[in] enable
|
||||
* true to enable counting, false to disable.
|
||||
******************************************************************************/
|
||||
void I2C_Enable(I2C_TypeDef *i2c, bool enable)
|
||||
{
|
||||
EFM_ASSERT(I2C_REF_VALID(i2c));
|
||||
|
||||
BITBAND_Peripheral(&(i2c->CTRL), _I2C_CTRL_EN_SHIFT, (unsigned int)enable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize I2C.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to I2C initialization structure.
|
||||
******************************************************************************/
|
||||
void I2C_Init(I2C_TypeDef *i2c, const I2C_Init_TypeDef *init)
|
||||
{
|
||||
EFM_ASSERT(I2C_REF_VALID(i2c));
|
||||
|
||||
i2c->IEN = 0;
|
||||
i2c->IFC = _I2C_IFC_MASK;
|
||||
|
||||
I2C_BusFreqSet(i2c, init->refFreq, init->freq, init->clhr);
|
||||
|
||||
BITBAND_Peripheral(&(i2c->CTRL),
|
||||
_I2C_CTRL_SLAVE_SHIFT,
|
||||
~((unsigned int)(init->master)));
|
||||
|
||||
BITBAND_Peripheral(&(i2c->CTRL),
|
||||
_I2C_CTRL_EN_SHIFT,
|
||||
(unsigned int)(init->enable));
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Reset I2C to same state as after a HW reset.
|
||||
*
|
||||
* @note
|
||||
* The ROUTE register is NOT reset by this function, in order to allow for
|
||||
* centralized setup of this feature.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
******************************************************************************/
|
||||
void I2C_Reset(I2C_TypeDef *i2c)
|
||||
{
|
||||
i2c->CTRL = _I2C_CTRL_RESETVALUE;
|
||||
i2c->CLKDIV = _I2C_CLKDIV_RESETVALUE;
|
||||
i2c->SADDR = _I2C_SADDR_RESETVALUE;
|
||||
i2c->SADDRMASK = _I2C_SADDRMASK_RESETVALUE;
|
||||
i2c->IEN = _I2C_IEN_RESETVALUE;
|
||||
i2c->IFC = _I2C_IFC_MASK;
|
||||
/* Do not reset route register, setting should be done independently */
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Continue an initiated I2C transfer (single master mode only).
|
||||
*
|
||||
* @details
|
||||
* This function is used repeatedly after a I2C_TransferInit() in order to
|
||||
* complete a transfer. It may be used in polled mode as the below example
|
||||
* shows:
|
||||
* @verbatim
|
||||
* I2C_TransferReturn_TypeDef ret;
|
||||
*
|
||||
* // Do a polled transfer
|
||||
* ret = I2C_TransferInit(I2C0, seq);
|
||||
* while (ret == i2cTransferInProgress)
|
||||
* {
|
||||
* ret = I2C_Transfer(I2C0);
|
||||
* }
|
||||
* @endverbatim
|
||||
* It may also be used in interrupt driven mode, where this function is invoked
|
||||
* from the interrupt handler. Notice that if used in interrupt mode, NVIC
|
||||
* interrupts must be configured and enabled for the I2C bus used. I2C
|
||||
* peripheral specific interrupts are managed by this SW.
|
||||
*
|
||||
* @note
|
||||
* Only single master mode is supported.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Returns status for ongoing transfer.
|
||||
* @li #i2cTransferInProgress - indicates that transfer not finished.
|
||||
* @li #i2cTransferDone - transfer completed successfully.
|
||||
* @li otherwise some sort of error has occurred.
|
||||
*
|
||||
******************************************************************************/
|
||||
I2C_TransferReturn_TypeDef I2C_Transfer(I2C_TypeDef *i2c)
|
||||
{
|
||||
uint32_t tmp;
|
||||
uint32_t pending;
|
||||
I2C_Transfer_TypeDef *transfer;
|
||||
I2C_TransferSeq_TypeDef *seq;
|
||||
|
||||
EFM_ASSERT(I2C_REF_VALID(i2c));
|
||||
|
||||
/* Support up to 2 I2C buses */
|
||||
if (i2c == I2C0)
|
||||
{
|
||||
transfer = i2cTransfer;
|
||||
}
|
||||
#if (I2C_COUNT > 1)
|
||||
else if (i2c == I2C1)
|
||||
{
|
||||
transfer = i2cTransfer + 1;
|
||||
}
|
||||
#endif
|
||||
else
|
||||
{
|
||||
return(i2cTransferUsageFault);
|
||||
}
|
||||
|
||||
seq = transfer->seq;
|
||||
for (;; )
|
||||
{
|
||||
pending = i2c->IF;
|
||||
|
||||
/* If some sort of fault, abort transfer. */
|
||||
if (pending & I2C_IF_ERRORS)
|
||||
{
|
||||
if (pending & I2C_IF_ARBLOST)
|
||||
{
|
||||
/* If arbitration fault, it indicates either a slave device */
|
||||
/* not responding as expected, or other master which is not */
|
||||
/* supported by this SW. */
|
||||
transfer->result = i2cTransferArbLost;
|
||||
}
|
||||
else if (pending & I2C_IF_BUSERR)
|
||||
{
|
||||
/* A bus error indicates a misplaced start or stop, which should */
|
||||
/* not occur in master mode controlled by this SW. */
|
||||
transfer->result = i2cTransferBusErr;
|
||||
}
|
||||
|
||||
/* If error situation occurred, it is difficult to know */
|
||||
/* exact cause and how to resolve. It will be up to a wrapper */
|
||||
/* to determine how to handle a fault/recovery if possible. */
|
||||
transfer->state = i2cStateDone;
|
||||
goto done;
|
||||
}
|
||||
|
||||
switch (transfer->state)
|
||||
{
|
||||
/***************************************************/
|
||||
/* Send first start+address (first byte if 10 bit) */
|
||||
/***************************************************/
|
||||
case i2cStateStartAddrSend:
|
||||
if (seq->flags & I2C_FLAG_10BIT_ADDR)
|
||||
{
|
||||
tmp = (((uint32_t)(seq->addr) >> 8) & 0x06) | 0xf0;
|
||||
|
||||
/* In 10 bit address mode, the address following the first */
|
||||
/* start always indicate write. */
|
||||
}
|
||||
else
|
||||
{
|
||||
tmp = (uint32_t)(seq->addr) & 0xfe;
|
||||
|
||||
if (seq->flags & I2C_FLAG_READ)
|
||||
{
|
||||
/* Indicate read request */
|
||||
tmp |= 1;
|
||||
}
|
||||
}
|
||||
|
||||
transfer->state = i2cStateAddrWFAckNack;
|
||||
i2c->TXDATA = tmp; /* Data not transmitted until START sent */
|
||||
i2c->CMD = I2C_CMD_START;
|
||||
goto done;
|
||||
|
||||
/*******************************************************/
|
||||
/* Wait for ACK/NACK on address (first byte if 10 bit) */
|
||||
/*******************************************************/
|
||||
case i2cStateAddrWFAckNack:
|
||||
if (pending & I2C_IF_NACK)
|
||||
{
|
||||
i2c->IFC = I2C_IFC_NACK;
|
||||
transfer->result = i2cTransferNack;
|
||||
transfer->state = i2cStateWFStopSent;
|
||||
i2c->CMD = I2C_CMD_STOP;
|
||||
}
|
||||
else if (pending & I2C_IF_ACK)
|
||||
{
|
||||
i2c->IFC = I2C_IFC_ACK;
|
||||
|
||||
/* If 10 bit address, send 2nd byte of address. */
|
||||
if (seq->flags & I2C_FLAG_10BIT_ADDR)
|
||||
{
|
||||
transfer->state = i2cStateAddrWF2ndAckNack;
|
||||
i2c->TXDATA = (uint32_t)(seq->addr) & 0xff;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Determine whether receiving or sending data */
|
||||
if (seq->flags & I2C_FLAG_READ)
|
||||
{
|
||||
transfer->state = i2cStateWFData;
|
||||
}
|
||||
else
|
||||
{
|
||||
transfer->state = i2cStateDataSend;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
}
|
||||
goto done;
|
||||
|
||||
/******************************************************/
|
||||
/* Wait for ACK/NACK on second byte of 10 bit address */
|
||||
/******************************************************/
|
||||
case i2cStateAddrWF2ndAckNack:
|
||||
if (pending & I2C_IF_NACK)
|
||||
{
|
||||
i2c->IFC = I2C_IFC_NACK;
|
||||
transfer->result = i2cTransferNack;
|
||||
transfer->state = i2cStateWFStopSent;
|
||||
i2c->CMD = I2C_CMD_STOP;
|
||||
}
|
||||
else if (pending & I2C_IF_ACK)
|
||||
{
|
||||
i2c->IFC = I2C_IFC_ACK;
|
||||
|
||||
/* If using plain read sequence with 10 bit address, switch to send */
|
||||
/* repeated start. */
|
||||
if (seq->flags & I2C_FLAG_READ)
|
||||
{
|
||||
transfer->state = i2cStateRStartAddrSend;
|
||||
}
|
||||
/* Otherwise expected to write 0 or more bytes */
|
||||
else
|
||||
{
|
||||
transfer->state = i2cStateDataSend;
|
||||
}
|
||||
continue;
|
||||
}
|
||||
goto done;
|
||||
|
||||
/*******************************/
|
||||
/* Send repeated start+address */
|
||||
/*******************************/
|
||||
case i2cStateRStartAddrSend:
|
||||
if (seq->flags & I2C_FLAG_10BIT_ADDR)
|
||||
{
|
||||
tmp = ((seq->addr >> 8) & 0x06) | 0xf0;
|
||||
}
|
||||
else
|
||||
{
|
||||
tmp = seq->addr & 0xfe;
|
||||
}
|
||||
|
||||
/* If this is a write+read combined sequence, then read is about to start */
|
||||
if (seq->flags & I2C_FLAG_WRITE_READ)
|
||||
{
|
||||
/* Indicate read request */
|
||||
tmp |= 1;
|
||||
}
|
||||
|
||||
transfer->state = i2cStateRAddrWFAckNack;
|
||||
/* We have to write START cmd first since repeated start, otherwise */
|
||||
/* data would be sent first. */
|
||||
i2c->CMD = I2C_CMD_START;
|
||||
i2c->TXDATA = tmp;
|
||||
goto done;
|
||||
|
||||
/**********************************************************************/
|
||||
/* Wait for ACK/NACK on repeated start+address (first byte if 10 bit) */
|
||||
/**********************************************************************/
|
||||
case i2cStateRAddrWFAckNack:
|
||||
if (pending & I2C_IF_NACK)
|
||||
{
|
||||
i2c->IFC = I2C_IFC_NACK;
|
||||
transfer->result = i2cTransferNack;
|
||||
transfer->state = i2cStateWFStopSent;
|
||||
i2c->CMD = I2C_CMD_STOP;
|
||||
}
|
||||
else if (pending & I2C_IF_ACK)
|
||||
{
|
||||
i2c->IFC = I2C_IFC_ACK;
|
||||
|
||||
/* Determine whether receiving or sending data */
|
||||
if (seq->flags & I2C_FLAG_WRITE_READ)
|
||||
{
|
||||
transfer->state = i2cStateWFData;
|
||||
}
|
||||
else
|
||||
{
|
||||
transfer->state = i2cStateDataSend;
|
||||
continue;
|
||||
}
|
||||
}
|
||||
goto done;
|
||||
|
||||
/*****************************/
|
||||
/* Send a data byte to slave */
|
||||
/*****************************/
|
||||
case i2cStateDataSend:
|
||||
/* Reached end of data buffer? */
|
||||
if (transfer->offset >= seq->buf[transfer->bufIndx].len)
|
||||
{
|
||||
/* Move to next message part */
|
||||
transfer->offset = 0;
|
||||
transfer->bufIndx++;
|
||||
|
||||
/* Send repeated start when switching to read mode on 2nd buffer */
|
||||
if (seq->flags & I2C_FLAG_WRITE_READ)
|
||||
{
|
||||
transfer->state = i2cStateRStartAddrSend;
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Only writing from one buffer, or finished both buffers */
|
||||
if ((seq->flags & I2C_FLAG_WRITE) || (transfer->bufIndx > 1))
|
||||
{
|
||||
transfer->state = i2cStateWFStopSent;
|
||||
i2c->CMD = I2C_CMD_STOP;
|
||||
goto done;
|
||||
}
|
||||
|
||||
/* Reprocess in case next buffer is empty */
|
||||
continue;
|
||||
}
|
||||
|
||||
/* Send byte */
|
||||
i2c->TXDATA = (uint32_t)(seq->buf[transfer->bufIndx].data[transfer->offset++]);
|
||||
transfer->state = i2cStateDataWFAckNack;
|
||||
goto done;
|
||||
|
||||
/*********************************************************/
|
||||
/* Wait for ACK/NACK from slave after sending data to it */
|
||||
/*********************************************************/
|
||||
case i2cStateDataWFAckNack:
|
||||
if (pending & I2C_IF_NACK)
|
||||
{
|
||||
i2c->IFC = I2C_IFC_NACK;
|
||||
transfer->result = i2cTransferNack;
|
||||
transfer->state = i2cStateWFStopSent;
|
||||
i2c->CMD = I2C_CMD_STOP;
|
||||
}
|
||||
else if (pending & I2C_IF_ACK)
|
||||
{
|
||||
i2c->IFC = I2C_IFC_ACK;
|
||||
transfer->state = i2cStateDataSend;
|
||||
continue;
|
||||
}
|
||||
goto done;
|
||||
|
||||
/****************************/
|
||||
/* Wait for data from slave */
|
||||
/****************************/
|
||||
case i2cStateWFData:
|
||||
if (pending & I2C_IF_RXDATAV)
|
||||
{
|
||||
uint8_t data;
|
||||
|
||||
/* Must read out data in order to not block further progress */
|
||||
data = (uint8_t)(i2c->RXDATA);
|
||||
|
||||
/* Make sure not storing beyond end of buffer just in case */
|
||||
if (transfer->offset < seq->buf[transfer->bufIndx].len)
|
||||
{
|
||||
seq->buf[transfer->bufIndx].data[transfer->offset++] = data;
|
||||
}
|
||||
|
||||
/* If we have read all requested data, then the sequence should end */
|
||||
if (transfer->offset >= seq->buf[transfer->bufIndx].len)
|
||||
{
|
||||
transfer->state = i2cStateWFStopSent;
|
||||
i2c->CMD = I2C_CMD_NACK;
|
||||
i2c->CMD = I2C_CMD_STOP;
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Send ACK and wait for next byte */
|
||||
i2c->CMD = I2C_CMD_ACK;
|
||||
}
|
||||
}
|
||||
goto done;
|
||||
|
||||
/***********************************/
|
||||
/* Wait for STOP to have been sent */
|
||||
/***********************************/
|
||||
case i2cStateWFStopSent:
|
||||
if (pending & I2C_IF_MSTOP)
|
||||
{
|
||||
i2c->IFC = I2C_IFC_MSTOP;
|
||||
transfer->state = i2cStateDone;
|
||||
}
|
||||
goto done;
|
||||
|
||||
/******************************/
|
||||
/* Unexpected state, SW fault */
|
||||
/******************************/
|
||||
default:
|
||||
transfer->result = i2cTransferSwFault;
|
||||
transfer->state = i2cStateDone;
|
||||
goto done;
|
||||
}
|
||||
}
|
||||
|
||||
done:
|
||||
|
||||
if (transfer->state == i2cStateDone)
|
||||
{
|
||||
/* Disable interrupt sources when done */
|
||||
i2c->IEN = 0;
|
||||
|
||||
/* Update result unless some fault already occurred */
|
||||
if (transfer->result == i2cTransferInProgress)
|
||||
{
|
||||
transfer->result = i2cTransferDone;
|
||||
}
|
||||
}
|
||||
/* Until transfer is done keep returning i2cTransferInProgress */
|
||||
else
|
||||
{
|
||||
return(i2cTransferInProgress);
|
||||
}
|
||||
|
||||
return transfer->result;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Prepare and start an I2C transfer (single master mode only).
|
||||
*
|
||||
* @details
|
||||
* This function must be invoked in order to start an I2C transfer
|
||||
* sequence. In order to actually complete the transfer, I2C_Transfer() must
|
||||
* be used either in polled mode or by adding a small driver wrapper utilizing
|
||||
* interrupts.
|
||||
*
|
||||
* @note
|
||||
* Only single master mode is supported.
|
||||
*
|
||||
* @param[in] i2c
|
||||
* Pointer to I2C peripheral register block.
|
||||
*
|
||||
* @param[in] seq
|
||||
* Pointer to sequence structure defining the I2C transfer to take place. The
|
||||
* referenced structure must exist until the transfer has fully completed.
|
||||
*
|
||||
* @return
|
||||
* Returns status for ongoing transfer:
|
||||
* @li #i2cTransferInProgress - indicates that transfer not finished.
|
||||
* @li otherwise some sort of error has occurred.
|
||||
******************************************************************************/
|
||||
I2C_TransferReturn_TypeDef I2C_TransferInit(I2C_TypeDef *i2c,
|
||||
I2C_TransferSeq_TypeDef *seq)
|
||||
{
|
||||
I2C_Transfer_TypeDef *transfer;
|
||||
|
||||
EFM_ASSERT(I2C_REF_VALID(i2c));
|
||||
EFM_ASSERT(seq);
|
||||
|
||||
/* Support up to 2 I2C buses */
|
||||
if (i2c == I2C0)
|
||||
{
|
||||
transfer = i2cTransfer;
|
||||
}
|
||||
#if (I2C_COUNT > 1)
|
||||
else if (i2c == I2C1)
|
||||
{
|
||||
transfer = i2cTransfer + 1;
|
||||
}
|
||||
#endif
|
||||
else
|
||||
{
|
||||
return(i2cTransferUsageFault);
|
||||
}
|
||||
|
||||
/* Check if in busy state. Since this SW assumes single master, we can */
|
||||
/* just issue an abort. The BUSY state is normal after a reset. */
|
||||
if (i2c->STATE & I2C_STATE_BUSY)
|
||||
{
|
||||
i2c->CMD = I2C_CMD_ABORT;
|
||||
}
|
||||
|
||||
/* Make sure user is not trying to read 0 bytes, it is not */
|
||||
/* possible according to I2C spec, since slave will always start */
|
||||
/* sending first byte ACK on address. The read operation can */
|
||||
/* only be stopped by NACKing a received byte, ie minimum 1 byte. */
|
||||
if (((seq->flags & I2C_FLAG_READ) && !(seq->buf[0].len)) ||
|
||||
((seq->flags & I2C_FLAG_WRITE_READ) && !(seq->buf[1].len))
|
||||
)
|
||||
{
|
||||
return(i2cTransferUsageFault);
|
||||
}
|
||||
|
||||
/* Prepare for a transfer */
|
||||
transfer->state = i2cStateStartAddrSend;
|
||||
transfer->result = i2cTransferInProgress;
|
||||
transfer->offset = 0;
|
||||
transfer->bufIndx = 0;
|
||||
transfer->seq = seq;
|
||||
|
||||
/* Ensure buffers are empty */
|
||||
i2c->CMD = I2C_CMD_CLEARPC | I2C_CMD_CLEARTX;
|
||||
if (i2c->IF & I2C_IF_RXDATAV)
|
||||
{
|
||||
i2c->RXDATA;
|
||||
}
|
||||
|
||||
/* Clear all pending interrupts prior to starting transfer. */
|
||||
i2c->IFC = _I2C_IFC_MASK;
|
||||
|
||||
/* Enable those interrupts we are interested in throughout transfer. */
|
||||
/* Notice that the I2C interrupt must also be enabled in the NVIC, but */
|
||||
/* that is left for an additional driver wrapper. */
|
||||
i2c->IEN = I2C_IF_NACK | I2C_IF_ACK | I2C_IF_MSTOP |
|
||||
I2C_IF_RXDATAV | I2C_IF_ERRORS;
|
||||
|
||||
/* Start transfer */
|
||||
return(I2C_Transfer(i2c));
|
||||
}
|
||||
|
||||
/** @} (end addtogroup I2C) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,66 @@
|
|||
/**************************************************************************//**
|
||||
* @file
|
||||
* @brief Interrupt enable/disable unit API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2011 Energy Micro AS, http://www.energymicro.com</b>
|
||||
******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
*****************************************************************************/
|
||||
#include <stdint.h>
|
||||
#include "efm32_int.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup INT
|
||||
* @brief Safe nesting interrupt disable/enable API for EFM32.
|
||||
* @details
|
||||
* This module contains functions to safely disable and enable interrupts
|
||||
* at cpu level. INT_Disable() disables interrupts and increments a lock
|
||||
* level counter. INT_Enable() decrements the lock level counter and enable
|
||||
* interrupts if the counter was decremented to zero.
|
||||
*
|
||||
* These functions would normally be used to secure critical regions.
|
||||
*
|
||||
* These functions should also be used inside interrupt handlers:
|
||||
* @verbatim
|
||||
* void SysTick_Handler(void)
|
||||
* {
|
||||
* INT_Disable();
|
||||
* .
|
||||
* .
|
||||
* .
|
||||
* INT_Enable();
|
||||
* }
|
||||
* @endverbatim
|
||||
******************************************************************************/
|
||||
|
||||
/** Interrupt lock level counter. Set to zero initially as we normally enter
|
||||
* main with interrupts enabled */
|
||||
uint32_t INT_LockCnt = 0;
|
||||
|
||||
|
||||
/** @} (end addtogroup INT) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,758 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Liquid Crystal Display (LCD) Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#include "efm32_lcd.h"
|
||||
#if defined(LCD_COUNT) && (LCD_COUNT > 0)
|
||||
#include "efm32_assert.h"
|
||||
#include "efm32_bitband.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup LCD
|
||||
* @brief Liquid Crystal Display (LCD) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initalize Liquid Crystal Display (LCD) controller
|
||||
*
|
||||
* @details
|
||||
* This function call will only configure the LCD controller. You must enable
|
||||
* it afterwards, potentially configuring Frame Control and interrupts first
|
||||
* according to requirements.
|
||||
*
|
||||
* @param[in] lcdInit
|
||||
* Pointer to initialization structure which configures LCD controller.
|
||||
*
|
||||
******************************************************************************/
|
||||
void LCD_Initialize(const LCD_Init_TypeDef *lcdInit)
|
||||
{
|
||||
uint32_t dispCtrl = LCD->DISPCTRL;
|
||||
|
||||
EFM_ASSERT(lcdInit != (void *) 0);
|
||||
|
||||
/* Disable controller before reconfiguration */
|
||||
LCD_Enable(false);
|
||||
|
||||
/* Make sure we don't touch other bit fields (i.e. voltage boost) */
|
||||
dispCtrl &= ~(
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
_LCD_DISPCTRL_MUXE_MASK |
|
||||
#endif
|
||||
_LCD_DISPCTRL_MUX_MASK |
|
||||
_LCD_DISPCTRL_BIAS_MASK |
|
||||
_LCD_DISPCTRL_WAVE_MASK |
|
||||
_LCD_DISPCTRL_VLCDSEL_MASK |
|
||||
_LCD_DISPCTRL_CONCONF_MASK);
|
||||
|
||||
/* Configure controller according to initialization structure */
|
||||
dispCtrl |= lcdInit->mux; /* also configures MUXE */
|
||||
dispCtrl |= lcdInit->bias;
|
||||
dispCtrl |= lcdInit->wave;
|
||||
dispCtrl |= lcdInit->vlcd;
|
||||
dispCtrl |= lcdInit->contrast;
|
||||
|
||||
/* Update display controller */
|
||||
LCD->DISPCTRL = dispCtrl;
|
||||
|
||||
/* Enable controller if wanted */
|
||||
if (lcdInit->enable)
|
||||
{
|
||||
LCD_Enable(true);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Select source for VLCD
|
||||
*
|
||||
* @param[in] vlcd
|
||||
* Select source for VLD voltage
|
||||
******************************************************************************/
|
||||
void LCD_VLCDSelect(LCD_VLCDSel_TypeDef vlcd)
|
||||
{
|
||||
uint32_t dispctrl = LCD->DISPCTRL;
|
||||
|
||||
/* Select VEXT or VDD */
|
||||
dispctrl &= ~(_LCD_DISPCTRL_VLCDSEL_MASK);
|
||||
switch (vlcd)
|
||||
{
|
||||
case lcdVLCDSelVExtBoost:
|
||||
dispctrl |= LCD_DISPCTRL_VLCDSEL_VEXTBOOST;
|
||||
break;
|
||||
case lcdVLCDSelVDD:
|
||||
dispctrl |= LCD_DISPCTRL_VLCDSEL_VDD;
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
LCD->DISPCTRL = dispctrl;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure Update Control
|
||||
*
|
||||
* @param[in] ud
|
||||
* Configures LCD update method
|
||||
******************************************************************************/
|
||||
void LCD_UpdateCtrl(LCD_UpdateCtrl_TypeDef ud)
|
||||
{
|
||||
LCD->CTRL = (LCD->CTRL & ~_LCD_CTRL_UDCTRL_MASK) | ud;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize LCD Frame Counter
|
||||
*
|
||||
* @param[in] fcInit
|
||||
* Pointer to Frame Counter initialization structure
|
||||
******************************************************************************/
|
||||
void LCD_FrameCountInit(const LCD_FrameCountInit_TypeDef *fcInit)
|
||||
{
|
||||
uint32_t bactrl = LCD->BACTRL;
|
||||
|
||||
EFM_ASSERT(fcInit != (void *) 0);
|
||||
|
||||
/* Verify FC Top Counter to be within limits */
|
||||
EFM_ASSERT(fcInit->top < 64);
|
||||
|
||||
/* Reconfigure frame count configuration */
|
||||
bactrl &= ~(_LCD_BACTRL_FCTOP_MASK |
|
||||
_LCD_BACTRL_FCPRESC_MASK);
|
||||
bactrl |= (fcInit->top << _LCD_BACTRL_FCTOP_SHIFT);
|
||||
bactrl |= fcInit->prescale;
|
||||
|
||||
/* Set Blink and Animation Control Register */
|
||||
LCD->BACTRL = bactrl;
|
||||
|
||||
LCD_FrameCountEnable(fcInit->enable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configures LCD controller Animation feature
|
||||
*
|
||||
* @param[in] animInit
|
||||
* Pointer to LCD Animation initialization structure
|
||||
******************************************************************************/
|
||||
void LCD_AnimInit(const LCD_AnimInit_TypeDef *animInit)
|
||||
{
|
||||
uint32_t bactrl = LCD->BACTRL;
|
||||
|
||||
EFM_ASSERT(animInit != (void *) 0);
|
||||
|
||||
/* Set Animation Register Values */
|
||||
LCD->AREGA = animInit->AReg;
|
||||
LCD->AREGB = animInit->BReg;
|
||||
|
||||
/* Configure Animation Shift and Logic */
|
||||
bactrl &= ~(_LCD_BACTRL_AREGASC_MASK |
|
||||
_LCD_BACTRL_AREGBSC_MASK |
|
||||
_LCD_BACTRL_ALOGSEL_MASK);
|
||||
|
||||
bactrl |= (animInit->AShift << _LCD_BACTRL_AREGASC_SHIFT);
|
||||
bactrl |= (animInit->BShift << _LCD_BACTRL_AREGBSC_SHIFT);
|
||||
bactrl |= animInit->animLogic;
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
if(animInit->startSeg == 0)
|
||||
{
|
||||
bactrl |= LCD_BACTRL_ALOC_SEG0TO7;
|
||||
}
|
||||
else if(animInit->startSeg == 8)
|
||||
{
|
||||
bactrl |= LCD_BACTRL_ALOC_SEG8TO15;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Reconfigure */
|
||||
LCD->BACTRL = bactrl;
|
||||
|
||||
/* Enable */
|
||||
LCD_AnimEnable(animInit->enable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enables update of this range of LCD segment lines
|
||||
*
|
||||
* @param[in] segmentRange
|
||||
* Range of 4 LCD segments lines to enable or disable, for all enabled COM
|
||||
* lines
|
||||
*
|
||||
* @param[in] enable
|
||||
* Bool true to enable segment updates, false to disable updates
|
||||
******************************************************************************/
|
||||
void LCD_SegmentRangeEnable(LCD_SegmentRange_TypeDef segmentRange, bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
LCD->SEGEN |= segmentRange;
|
||||
}
|
||||
else
|
||||
{
|
||||
LCD->SEGEN &= ~((uint32_t)segmentRange);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Turn on or clear a segment
|
||||
*
|
||||
* @note
|
||||
* On Gecko Family, max configuration is (COM-lines x Segment-Lines) 4x40
|
||||
* On Tiny Family, max configuration is 8x20 or 4x24
|
||||
* On Giant Family, max configuration is 8x36 or 4x40
|
||||
*
|
||||
* @param[in] com
|
||||
* COM line to change
|
||||
*
|
||||
* @param[in] bit
|
||||
* Bit index of which field to change
|
||||
*
|
||||
* @param[in] enable
|
||||
* When true will set segment, when false will clear segment
|
||||
******************************************************************************/
|
||||
void LCD_SegmentSet(int com, int bit, bool enable)
|
||||
{
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/* Tiny and Giant Family supports up to 8 COM lines */
|
||||
EFM_ASSERT(com < 8);
|
||||
#else
|
||||
/* Gecko Family supports up to 4 COM lines */
|
||||
EFM_ASSERT(com < 4);
|
||||
#endif
|
||||
|
||||
#if defined(_EFM32_GECKO_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
EFM_ASSERT(bit < 40);
|
||||
#else
|
||||
/* Tiny Gecko Family supports only "low" segment registers */
|
||||
EFM_ASSERT(bit < 32);
|
||||
#endif
|
||||
|
||||
/* Use bitband access for atomic bit set/clear of segment */
|
||||
switch (com)
|
||||
{
|
||||
case 0:
|
||||
if (bit < 32)
|
||||
{
|
||||
BITBAND_Peripheral(&(LCD->SEGD0L), bit, (unsigned int)enable);
|
||||
}
|
||||
#if defined(_EFM32_GECKO_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
else
|
||||
{
|
||||
bit -= 32;
|
||||
BITBAND_Peripheral(&(LCD->SEGD0H), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
case 1:
|
||||
if (bit < 32)
|
||||
{
|
||||
BITBAND_Peripheral(&(LCD->SEGD1L), bit, (unsigned int)enable);
|
||||
}
|
||||
#if defined(_EFM32_GECKO_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
else
|
||||
{
|
||||
bit -= 32;
|
||||
BITBAND_Peripheral(&(LCD->SEGD1H), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
case 2:
|
||||
if (bit < 32)
|
||||
{
|
||||
BITBAND_Peripheral(&(LCD->SEGD2L), bit, (unsigned int)enable);
|
||||
}
|
||||
#if defined(_EFM32_GECKO_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
else
|
||||
{
|
||||
bit -= 32;
|
||||
BITBAND_Peripheral(&(LCD->SEGD2H), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
case 3:
|
||||
if (bit < 32)
|
||||
{
|
||||
BITBAND_Peripheral(&(LCD->SEGD3L), bit, (unsigned int)enable);
|
||||
}
|
||||
#if defined(_EFM32_GECKO_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
else
|
||||
{
|
||||
bit -= 32;
|
||||
BITBAND_Peripheral(&(LCD->SEGD3H), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
case 4:
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
if (bit < 32)
|
||||
{
|
||||
BITBAND_Peripheral(&(LCD->SEGD4L), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
else
|
||||
{
|
||||
bit -= 32;
|
||||
BITBAND_Peripheral(&(LCD->SEGD4H), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
case 5:
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
if (bit < 32)
|
||||
{
|
||||
BITBAND_Peripheral(&(LCD->SEGD5L), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
else
|
||||
{
|
||||
bit -= 32;
|
||||
BITBAND_Peripheral(&(LCD->SEGD5H), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
case 6:
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
if (bit < 32)
|
||||
{
|
||||
BITBAND_Peripheral(&(LCD->SEGD6L), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
else
|
||||
{
|
||||
bit -= 32;
|
||||
BITBAND_Peripheral(&(LCD->SEGD6H), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
case 7:
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
if (bit < 32)
|
||||
{
|
||||
BITBAND_Peripheral(&(LCD->SEGD7L), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
else
|
||||
{
|
||||
bit -= 32;
|
||||
BITBAND_Peripheral(&(LCD->SEGD7H), bit, (unsigned int)enable);
|
||||
}
|
||||
#endif
|
||||
break;
|
||||
|
||||
default:
|
||||
EFM_ASSERT(0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Updates the 0-31 lowest segments on a given COM-line in one operation,
|
||||
* according to bit mask
|
||||
*
|
||||
* @param[in] com
|
||||
* Which COM line to update
|
||||
*
|
||||
* @param[in] mask
|
||||
* Bit mask for segments 0-31
|
||||
*
|
||||
* @param[in] bits
|
||||
* Bit pattern for segments 0-31
|
||||
******************************************************************************/
|
||||
void LCD_SegmentSetLow(int com, uint32_t mask, uint32_t bits)
|
||||
{
|
||||
uint32_t segData;
|
||||
|
||||
/* Maximum number of com lines */
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
EFM_ASSERT(com < 8);
|
||||
#else
|
||||
/* Gecko Family supports up to 4 COM lines */
|
||||
EFM_ASSERT(com < 4);
|
||||
#endif
|
||||
|
||||
switch (com)
|
||||
{
|
||||
case 0:
|
||||
segData = LCD->SEGD0L;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD0L = segData;
|
||||
break;
|
||||
case 1:
|
||||
segData = LCD->SEGD1L;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD1L = segData;
|
||||
break;
|
||||
case 2:
|
||||
segData = LCD->SEGD2L;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD2L = segData;
|
||||
break;
|
||||
case 3:
|
||||
segData = LCD->SEGD3L;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD3L = segData;
|
||||
break;
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
case 4:
|
||||
segData = LCD->SEGD4L;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD4L = segData;
|
||||
break;
|
||||
#endif
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
case 5:
|
||||
segData = LCD->SEGD5L;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD5L = segData;
|
||||
break;
|
||||
#endif
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
case 6:
|
||||
segData = LCD->SEGD6L;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD6L = segData;
|
||||
break;
|
||||
#endif
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
case 7:
|
||||
segData = LCD->SEGD7L;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD7L = segData;
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
EFM_ASSERT(0);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
#if defined(_EFM32_GECKO_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Updated the high (32-39) segments on a given COM-line in one operation
|
||||
*
|
||||
* @param[in] com
|
||||
* Which COM line to update
|
||||
*
|
||||
* @param[in] mask
|
||||
* Bit mask for segments 32-39
|
||||
*
|
||||
* @param[in] bits
|
||||
* Bit pattern for segments 32-39
|
||||
******************************************************************************/
|
||||
void LCD_SegmentSetHigh(int com, uint32_t mask, uint32_t bits)
|
||||
{
|
||||
uint32_t segData;
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
EFM_ASSERT(com < 8);
|
||||
#endif
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
EFM_ASSERT(com < 4);
|
||||
#endif
|
||||
|
||||
/* Maximum number of com lines */
|
||||
switch (com)
|
||||
{
|
||||
case 0:
|
||||
segData = LCD->SEGD0H;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD0H = segData;
|
||||
break;
|
||||
case 1:
|
||||
segData = LCD->SEGD1H;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD1H = segData;
|
||||
break;
|
||||
case 2:
|
||||
segData = LCD->SEGD2H;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD2H = segData;
|
||||
break;
|
||||
case 3:
|
||||
segData = LCD->SEGD3H;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD3H = segData;
|
||||
break;
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
case 4:
|
||||
segData = LCD->SEGD4H;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD4H = segData;
|
||||
break;
|
||||
#endif
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
case 5:
|
||||
segData = LCD->SEGD5H;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD5H = segData;
|
||||
break;
|
||||
#endif
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
case 6:
|
||||
segData = LCD->SEGD6H;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD6H = segData;
|
||||
break;
|
||||
#endif
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
case 7:
|
||||
segData = LCD->SEGD7H;
|
||||
segData &= ~(mask);
|
||||
segData |= (mask & bits);
|
||||
LCD->SEGD7H = segData;
|
||||
break;
|
||||
#endif
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure contrast level on LCD panel
|
||||
*
|
||||
* @param[in] level
|
||||
* Contrast level in the range 0-31
|
||||
******************************************************************************/
|
||||
void LCD_ContrastSet(int level)
|
||||
{
|
||||
EFM_ASSERT(level < 32);
|
||||
|
||||
LCD->DISPCTRL = (LCD->DISPCTRL & ~_LCD_DISPCTRL_CONLEV_MASK)
|
||||
| (level << _LCD_DISPCTRL_CONLEV_SHIFT);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure voltage booster
|
||||
*
|
||||
* The resulting voltage level is described in each part number's data sheet
|
||||
*
|
||||
* @param[in] vboost
|
||||
* Voltage boost level
|
||||
******************************************************************************/
|
||||
void LCD_VBoostSet(LCD_VBoostLevel_TypeDef vboost)
|
||||
{
|
||||
/* Reconfigure Voltage Boost */
|
||||
LCD->DISPCTRL = (LCD->DISPCTRL & ~_LCD_DISPCTRL_VBLEV_MASK) | vboost;
|
||||
}
|
||||
|
||||
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure bias level for a specific segment line for Direct Segment Control
|
||||
*
|
||||
* @note
|
||||
* When DSC is active, each configuration takes up 4 bits in the Segment
|
||||
* Registers (SEGD0L/SEGD1H) which defines bias level.
|
||||
* For optimal use of this feature, the entire SEGD-registers should be set
|
||||
* at once in a optimized routine, so this function is mainly here to
|
||||
* demonstrate how to correctly configure the bias levels, and should be used
|
||||
* with care.
|
||||
*
|
||||
* @param[in] segmentLine
|
||||
* Segment line number
|
||||
*
|
||||
* @param[in] biasLevel
|
||||
* Bias configuration level, 0-4. This value must be within the constraint
|
||||
* defined by the LCD_DISPCTRL bias setting, see Reference Manual/Datasheet
|
||||
******************************************************************************/
|
||||
void LCD_BiasSegmentSet(int segmentLine, int biasLevel)
|
||||
{
|
||||
int biasRegister;
|
||||
int bitShift;
|
||||
volatile uint32_t *segmentRegister;
|
||||
|
||||
#if defined(_EFM32_TINY_FAMILY)
|
||||
EFM_ASSERT(segmentLine < 20);
|
||||
#endif
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
EFM_ASSERT(segmentLine < 40);
|
||||
#endif
|
||||
#if defined(_EFM32_TINY_FAMILY)
|
||||
/* Bias config for 8 segment lines per SEGDnL register */
|
||||
biasRegister = segmentLine / 8;
|
||||
bitShift = (segmentLine % 8) * 4;
|
||||
|
||||
switch (biasRegister)
|
||||
{
|
||||
case 0:
|
||||
segmentRegister = &LCD->SEGD0L;
|
||||
break;
|
||||
case 1:
|
||||
segmentRegister = &LCD->SEGD1L;
|
||||
break;
|
||||
case 2:
|
||||
segmentRegister = &LCD->SEGD2L;
|
||||
break;
|
||||
case 3:
|
||||
segmentRegister = &LCD->SEGD3L;
|
||||
break;
|
||||
default:
|
||||
segmentRegister = (uint32_t *)0x00000000;
|
||||
EFM_ASSERT(0);
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/* Bias config for 10 segment lines per SEGDn L+H registers */
|
||||
biasRegister = segmentLine / 10;
|
||||
bitShift = (segmentLine % 10) * 4;
|
||||
|
||||
switch (biasRegister)
|
||||
{
|
||||
case 0:
|
||||
if (bitShift < 32)
|
||||
{
|
||||
segmentRegister = &LCD->SEGD0L;
|
||||
}
|
||||
else
|
||||
{
|
||||
segmentRegister = &LCD->SEGD0H;
|
||||
bitShift -= 32;
|
||||
}
|
||||
break;
|
||||
case 1:
|
||||
if (bitShift < 32)
|
||||
{
|
||||
segmentRegister = &LCD->SEGD1L;
|
||||
}
|
||||
else
|
||||
{
|
||||
segmentRegister = &LCD->SEGD1H;
|
||||
bitShift -= 32;
|
||||
}
|
||||
break;
|
||||
case 2:
|
||||
if (bitShift < 32)
|
||||
{
|
||||
segmentRegister = &LCD->SEGD2L;
|
||||
}
|
||||
else
|
||||
{
|
||||
segmentRegister = &LCD->SEGD1H;
|
||||
bitShift -= 32;
|
||||
}
|
||||
break;
|
||||
case 3:
|
||||
if (bitShift < 32)
|
||||
{
|
||||
segmentRegister = &LCD->SEGD3L;
|
||||
}
|
||||
else
|
||||
{
|
||||
segmentRegister = &LCD->SEGD3H;
|
||||
bitShift -= 32;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
segmentRegister = (uint32_t *)0x00000000;
|
||||
EFM_ASSERT(0);
|
||||
break;
|
||||
}
|
||||
#endif
|
||||
|
||||
/* Configure new bias setting */
|
||||
*segmentRegister = (*segmentRegister & ~(0xF << bitShift)) | (biasLevel << bitShift);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure bias level for a specific segment line
|
||||
*
|
||||
* @note
|
||||
* When DSC is active, each configuration takes up 4 bits in the Segment
|
||||
* Registers (SEGD4L/SEGD4H) which defines bias level.
|
||||
* For optimal use of this feature, the entire SEGD-registers should be set
|
||||
* at once in a optimized routine, so this function is mainly here to
|
||||
* demonstrate how to correctly configure the bias levels, and should be used
|
||||
* with care.
|
||||
*
|
||||
* @param[in] comLine
|
||||
* COM line number, 0-7
|
||||
*
|
||||
* @param[in] biasLevel
|
||||
* Bias configuration level, 0-4. This value must be within the constraint
|
||||
* defined by the LCD_DISPCTRL bias setting, see Reference Manual/Datasheet
|
||||
******************************************************************************/
|
||||
void LCD_BiasComSet(int comLine, int biasLevel)
|
||||
{
|
||||
int bitShift;
|
||||
EFM_ASSERT(comLine < 8);
|
||||
|
||||
bitShift = comLine * 4;
|
||||
LCD->SEGD4L = (LCD->SEGD4L & ~(0xF << bitShift)) | (biasLevel << bitShift);
|
||||
}
|
||||
#endif
|
||||
|
||||
/** @} (end addtogroup LCD) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#endif /* defined(LCD_COUNT) && (LCD_COUNT > 0) */
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,529 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Low Energy Timer (LETIMER) Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32_letimer.h"
|
||||
#include "efm32_cmu.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup LETIMER
|
||||
* @brief Low Energy Timer (LETIMER) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/** Validation of valid comparator register for assert statements. */
|
||||
#define LETIMER_COMP_REG_VALID(reg) (((reg) <= 1))
|
||||
|
||||
/** Validation of LETIMER register block pointer reference for assert statements. */
|
||||
#define LETIMER_REF_VALID(ref) ((ref) == LETIMER0)
|
||||
|
||||
/** Validation of valid repeat counter register for assert statements. */
|
||||
#define LETIMER_REP_REG_VALID(reg) (((reg) <= 1))
|
||||
|
||||
/** @endcond */
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
************************** LOCAL FUNCTIONS ********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Wait for ongoing sync of register(s) to low frequency domain to complete.
|
||||
*
|
||||
* @note
|
||||
* This only applies to the Gecko Family, see the reference manual
|
||||
* chapter about Access to Low Energy Peripherals (Asynchronos Registers)
|
||||
* for details.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block
|
||||
*
|
||||
* @param[in] mask
|
||||
* Bitmask corresponding to SYNCBUSY register defined bits, indicating
|
||||
* registers that must complete any ongoing synchronization.
|
||||
******************************************************************************/
|
||||
static __INLINE void LETIMER_Sync(LETIMER_TypeDef *letimer, uint32_t mask)
|
||||
{
|
||||
/* Avoid deadlock if modifying the same register twice when freeze mode is */
|
||||
/* activated. */
|
||||
if (letimer->FREEZE & LETIMER_FREEZE_REGFREEZE)
|
||||
return;
|
||||
|
||||
/* Wait for any pending previous write operation to have been completed */
|
||||
/* in low frequency domain, only required for Gecko Family of devices */
|
||||
while (letimer->SYNCBUSY & mask)
|
||||
;
|
||||
}
|
||||
#endif
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get LETIMER compare register value.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block
|
||||
*
|
||||
* @param[in] comp
|
||||
* Compare register to get, either 0 or 1
|
||||
*
|
||||
* @return
|
||||
* Compare register value, 0 if invalid register selected.
|
||||
******************************************************************************/
|
||||
uint32_t LETIMER_CompareGet(LETIMER_TypeDef *letimer, unsigned int comp)
|
||||
{
|
||||
uint32_t ret;
|
||||
|
||||
EFM_ASSERT(LETIMER_REF_VALID(letimer) && LETIMER_COMP_REG_VALID(comp));
|
||||
|
||||
/* Initialize selected compare value */
|
||||
switch (comp)
|
||||
{
|
||||
case 0:
|
||||
ret = letimer->COMP0;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
ret = letimer->COMP1;
|
||||
break;
|
||||
|
||||
default:
|
||||
/* Unknown compare register selected */
|
||||
ret = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set LETIMER compare register value.
|
||||
*
|
||||
* @note
|
||||
* The setting of a compare register requires synchronization into the
|
||||
* low frequency domain. If the same register is modified before a previous
|
||||
* update has completed, this function will stall until the previous
|
||||
* synchronization has completed. This only applies to the Gecko Family, see
|
||||
* comment in the LETIMER_Sync() internal function call.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block
|
||||
*
|
||||
* @param[in] comp
|
||||
* Compare register to set, either 0 or 1
|
||||
*
|
||||
* @param[in] value
|
||||
* Initialization value (<= 0x0000ffff)
|
||||
******************************************************************************/
|
||||
void LETIMER_CompareSet(LETIMER_TypeDef *letimer,
|
||||
unsigned int comp,
|
||||
uint32_t value)
|
||||
{
|
||||
volatile uint32_t *compReg;
|
||||
uint32_t syncbusy;
|
||||
|
||||
EFM_ASSERT(LETIMER_REF_VALID(letimer) &&
|
||||
LETIMER_COMP_REG_VALID(comp) &&
|
||||
((value & ~(_LETIMER_COMP0_COMP0_MASK >> _LETIMER_COMP0_COMP0_SHIFT)) == 0));
|
||||
|
||||
/* Initialize selected compare value */
|
||||
switch (comp)
|
||||
{
|
||||
case 0:
|
||||
compReg = &(letimer->COMP0);
|
||||
syncbusy = LETIMER_SYNCBUSY_COMP0;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
compReg = &(letimer->COMP1);
|
||||
syncbusy = LETIMER_SYNCBUSY_COMP1;
|
||||
break;
|
||||
|
||||
default:
|
||||
/* Unknown compare register selected, abort */
|
||||
return;
|
||||
}
|
||||
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LETIMER_Sync(letimer, syncbusy);
|
||||
#endif
|
||||
|
||||
*compReg = value;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Start/stop LETIMER.
|
||||
*
|
||||
* @note
|
||||
* The enabling/disabling of the LETIMER modifies the LETIMER CMD register
|
||||
* which requires synchronization into the low frequency domain. If this
|
||||
* register is modified before a previous update to the same register has
|
||||
* completed, this function will stall until the previous synchronization has
|
||||
* completed. This only applies to the Gecko Family, see comment in the
|
||||
* LETIMER_Sync() internal function call.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block.
|
||||
*
|
||||
* @param[in] enable
|
||||
* true to enable counting, false to disable.
|
||||
******************************************************************************/
|
||||
void LETIMER_Enable(LETIMER_TypeDef *letimer, bool enable)
|
||||
{
|
||||
EFM_ASSERT(LETIMER_REF_VALID(letimer));
|
||||
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LETIMER_Sync(letimer, LETIMER_SYNCBUSY_CMD);
|
||||
#endif
|
||||
|
||||
if (enable)
|
||||
{
|
||||
letimer->CMD = LETIMER_CMD_START;
|
||||
}
|
||||
else
|
||||
{
|
||||
letimer->CMD = LETIMER_CMD_STOP;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* LETIMER register synchronization freeze control.
|
||||
*
|
||||
* @details
|
||||
* Some LETIMER registers require synchronization into the low frequency (LF)
|
||||
* domain. The freeze feature allows for several such registers to be
|
||||
* modified before passing them to the LF domain simultaneously (which
|
||||
* takes place when the freeze mode is disabled).
|
||||
*
|
||||
* @note
|
||||
* When enabling freeze mode, this function will wait for all current
|
||||
* ongoing LETIMER synchronization to LF domain to complete (Normally
|
||||
* synchronization will not be in progress.) However for this reason, when
|
||||
* using freeze mode, modifications of registers requiring LF synchronization
|
||||
* should be done within one freeze enable/disable block to avoid unecessary
|
||||
* stalling.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block.
|
||||
*
|
||||
* @param[in] enable
|
||||
* @li true - enable freeze, modified registers are not propagated to the
|
||||
* LF domain
|
||||
* @li false - disables freeze, modified registers are propagated to LF
|
||||
* domain
|
||||
******************************************************************************/
|
||||
void LETIMER_FreezeEnable(LETIMER_TypeDef *letimer, bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
/*
|
||||
* Wait for any ongoing LF synchronization to complete. This is just to
|
||||
* protect against the rare case when a user
|
||||
* - modifies a register requiring LF sync
|
||||
* - then enables freeze before LF sync completed
|
||||
* - then modifies the same register again
|
||||
* since modifying a register while it is in sync progress should be
|
||||
* avoided.
|
||||
*/
|
||||
while (letimer->SYNCBUSY)
|
||||
;
|
||||
|
||||
letimer->FREEZE = LETIMER_FREEZE_REGFREEZE;
|
||||
}
|
||||
else
|
||||
{
|
||||
letimer->FREEZE = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize LETIMER.
|
||||
*
|
||||
* @details
|
||||
* Note that the compare/repeat values must be set separately with
|
||||
* LETIMER_CompareSet() and LETIMER_RepeatSet(). That should probably be done
|
||||
* prior to the use of this function if configuring the LETIMER to start when
|
||||
* initialization is completed.
|
||||
*
|
||||
* @note
|
||||
* The initialization of the LETIMER modifies the LETIMER CTRL/CMD registers
|
||||
* which require synchronization into the low frequency domain. If any of those
|
||||
* registers are modified before a previous update to the same register has
|
||||
* completed, this function will stall until the previous synchronization has
|
||||
* completed. This only applies to the Gecko Family, see comment in the
|
||||
* LETIMER_Sync() internal function call.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to LETIMER initialization structure.
|
||||
******************************************************************************/
|
||||
void LETIMER_Init(LETIMER_TypeDef *letimer, const LETIMER_Init_TypeDef *init)
|
||||
{
|
||||
uint32_t tmp = 0;
|
||||
|
||||
EFM_ASSERT(LETIMER_REF_VALID(letimer));
|
||||
|
||||
/* Stop timer if specified to be disabled and running */
|
||||
if (!(init->enable) && (letimer->STATUS & LETIMER_STATUS_RUNNING))
|
||||
{
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LETIMER_Sync(letimer, LETIMER_SYNCBUSY_CMD);
|
||||
#endif
|
||||
letimer->CMD = LETIMER_CMD_STOP;
|
||||
}
|
||||
|
||||
/* Configure DEBUGRUN flag, sets whether or not counter should be
|
||||
* updated when debugger is active */
|
||||
if (init->debugRun)
|
||||
{
|
||||
tmp |= LETIMER_CTRL_DEBUGRUN;
|
||||
}
|
||||
|
||||
if (init->rtcComp0Enable)
|
||||
{
|
||||
tmp |= LETIMER_CTRL_RTCC0TEN;
|
||||
}
|
||||
|
||||
if (init->rtcComp1Enable)
|
||||
{
|
||||
tmp |= LETIMER_CTRL_RTCC1TEN;
|
||||
}
|
||||
|
||||
if (init->comp0Top)
|
||||
{
|
||||
tmp |= LETIMER_CTRL_COMP0TOP;
|
||||
}
|
||||
|
||||
if (init->bufTop)
|
||||
{
|
||||
tmp |= LETIMER_CTRL_BUFTOP;
|
||||
}
|
||||
|
||||
if (init->out0Pol)
|
||||
{
|
||||
tmp |= LETIMER_CTRL_OPOL0;
|
||||
}
|
||||
|
||||
if (init->out1Pol)
|
||||
{
|
||||
tmp |= LETIMER_CTRL_OPOL1;
|
||||
}
|
||||
|
||||
tmp |= init->ufoa0 << _LETIMER_CTRL_UFOA0_SHIFT;
|
||||
tmp |= init->ufoa1 << _LETIMER_CTRL_UFOA1_SHIFT;
|
||||
tmp |= init->repMode << _LETIMER_CTRL_REPMODE_SHIFT;
|
||||
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LETIMER_Sync(letimer, LETIMER_SYNCBUSY_CTRL);
|
||||
#endif
|
||||
letimer->CTRL = tmp;
|
||||
|
||||
/* Start timer if specified to be enabled and not already running */
|
||||
if (init->enable && !(letimer->STATUS & LETIMER_STATUS_RUNNING))
|
||||
{
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LETIMER_Sync(letimer, LETIMER_SYNCBUSY_CMD);
|
||||
#endif
|
||||
letimer->CMD = LETIMER_CMD_START;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get LETIMER repeat register value.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block
|
||||
*
|
||||
* @param[in] rep
|
||||
* Repeat register to get, either 0 or 1
|
||||
*
|
||||
* @return
|
||||
* Repeat register value, 0 if invalid register selected.
|
||||
******************************************************************************/
|
||||
uint32_t LETIMER_RepeatGet(LETIMER_TypeDef *letimer, unsigned int rep)
|
||||
{
|
||||
uint32_t ret;
|
||||
|
||||
EFM_ASSERT(LETIMER_REF_VALID(letimer) && LETIMER_REP_REG_VALID(rep));
|
||||
|
||||
/* Initialize selected compare value */
|
||||
switch (rep)
|
||||
{
|
||||
case 0:
|
||||
ret = letimer->REP0;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
ret = letimer->REP1;
|
||||
break;
|
||||
|
||||
default:
|
||||
/* Unknown compare register selected */
|
||||
ret = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
return(ret);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set LETIMER repeat counter register value.
|
||||
*
|
||||
* @note
|
||||
* The setting of a repeat counter register requires synchronization into the
|
||||
* low frequency domain. If the same register is modified before a previous
|
||||
* update has completed, this function will stall until the previous
|
||||
* synchronization has completed. This only applies to the Gecko Family, see
|
||||
* comment in the LETIMER_Sync() internal function call.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block
|
||||
*
|
||||
* @param[in] rep
|
||||
* Repeat counter register to set, either 0 or 1
|
||||
*
|
||||
* @param[in] value
|
||||
* Initialization value (<= 0x0000ffff)
|
||||
******************************************************************************/
|
||||
void LETIMER_RepeatSet(LETIMER_TypeDef *letimer,
|
||||
unsigned int rep,
|
||||
uint32_t value)
|
||||
{
|
||||
volatile uint32_t *repReg;
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
uint32_t syncbusy;
|
||||
#endif
|
||||
EFM_ASSERT(LETIMER_REF_VALID(letimer) &&
|
||||
LETIMER_REP_REG_VALID(rep) &&
|
||||
((value & ~(_LETIMER_REP0_REP0_MASK >> _LETIMER_REP0_REP0_SHIFT)) == 0));
|
||||
|
||||
/* Initialize selected compare value */
|
||||
switch (rep)
|
||||
{
|
||||
case 0:
|
||||
repReg = &(letimer->REP0);
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
syncbusy = LETIMER_SYNCBUSY_REP0;
|
||||
#endif
|
||||
break;
|
||||
|
||||
case 1:
|
||||
repReg = &(letimer->REP1);
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
syncbusy = LETIMER_SYNCBUSY_REP1;
|
||||
#endif
|
||||
break;
|
||||
|
||||
default:
|
||||
/* Unknown compare register selected, abort */
|
||||
return;
|
||||
}
|
||||
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LETIMER_Sync(letimer, syncbusy);
|
||||
#endif
|
||||
|
||||
*repReg = value;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Reset LETIMER to same state as after a HW reset.
|
||||
*
|
||||
* @note
|
||||
* The ROUTE register is NOT reset by this function, in order to allow for
|
||||
* centralized setup of this feature.
|
||||
*
|
||||
* @param[in] letimer
|
||||
* Pointer to LETIMER peripheral register block.
|
||||
******************************************************************************/
|
||||
void LETIMER_Reset(LETIMER_TypeDef *letimer)
|
||||
{
|
||||
/* Freeze registers to avoid stalling for LF synchronization */
|
||||
LETIMER_FreezeEnable(letimer, true);
|
||||
|
||||
/* Make sure disabled first, before resetting other registers */
|
||||
letimer->CMD = LETIMER_CMD_STOP | LETIMER_CMD_CLEAR |
|
||||
LETIMER_CMD_CTO0 | LETIMER_CMD_CTO1;
|
||||
letimer->CTRL = _LETIMER_CTRL_RESETVALUE;
|
||||
letimer->COMP0 = _LETIMER_COMP0_RESETVALUE;
|
||||
letimer->COMP1 = _LETIMER_COMP1_RESETVALUE;
|
||||
letimer->REP0 = _LETIMER_REP0_RESETVALUE;
|
||||
letimer->REP1 = _LETIMER_REP1_RESETVALUE;
|
||||
letimer->IEN = _LETIMER_IEN_RESETVALUE;
|
||||
letimer->IFC = _LETIMER_IFC_MASK;
|
||||
/* Do not reset route register, setting should be done independently */
|
||||
|
||||
/* Unfreeze registers, pass new settings on to LETIMER */
|
||||
LETIMER_FreezeEnable(letimer, false);
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup LETIMER) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,635 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Low Energy Universal Asynchronous Receiver/Transmitter (LEUART)
|
||||
* peripheral module peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32_leuart.h"
|
||||
#include "efm32_cmu.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup LEUART
|
||||
* @brief Low Energy Universal Asynchronous Receiver/Transmitter (LEUART)
|
||||
* Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
|
||||
/** Validation of LEUART register block pointer reference
|
||||
* for assert statements. */
|
||||
#if (LEUART_COUNT == 1)
|
||||
#define LEUART_REF_VALID(ref) ((ref) == LEUART0)
|
||||
#elif (LEUART_COUNT == 2)
|
||||
#define LEUART_REF_VALID(ref) (((ref) == LEUART0) || ((ref) == LEUART1))
|
||||
#else
|
||||
#error Undefined number of low energy UARTs (LEUART).
|
||||
#endif
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
************************** LOCAL FUNCTIONS ********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Wait for ongoing sync of register(s) to low frequency domain to complete.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block
|
||||
*
|
||||
* @param[in] mask
|
||||
* Bitmask corresponding to SYNCBUSY register defined bits, indicating
|
||||
* registers that must complete any ongoing synchronization.
|
||||
******************************************************************************/
|
||||
static __INLINE void LEUART_Sync(LEUART_TypeDef *leuart, uint32_t mask)
|
||||
{
|
||||
/* Avoid deadlock if modifying the same register twice when freeze mode is */
|
||||
/* activated. */
|
||||
if (leuart->FREEZE & LEUART_FREEZE_REGFREEZE)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
/* Wait for any pending previous write operation to have been completed */
|
||||
/* in low frequency domain */
|
||||
while (leuart->SYNCBUSY & mask)
|
||||
;
|
||||
}
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Calculate baudrate for LEUART given reference frequency and clock division.
|
||||
*
|
||||
* @details
|
||||
* This function returns the baudrate that a LEUART module will use if
|
||||
* configured with the given frequency and clock divisor. Notice that
|
||||
* this function will not use actual HW configuration. It can be used
|
||||
* to determinate if a given configuration is sufficiently accurate for the
|
||||
* application.
|
||||
*
|
||||
* @param[in] refFreq
|
||||
* LEUART peripheral frequency used.
|
||||
*
|
||||
* @param[in] clkdiv
|
||||
* Clock division factor to be used.
|
||||
*
|
||||
* @return
|
||||
* Baudrate with given settings.
|
||||
******************************************************************************/
|
||||
uint32_t LEUART_BaudrateCalc(uint32_t refFreq, uint32_t clkdiv)
|
||||
{
|
||||
uint32_t divisor;
|
||||
uint32_t remainder;
|
||||
uint32_t quotient;
|
||||
uint32_t br;
|
||||
|
||||
/* Mask out unused bits */
|
||||
clkdiv &= _LEUART_CLKDIV_MASK;
|
||||
|
||||
/* We want to use integer division to avoid forcing in float division */
|
||||
/* utils, and yet keep rounding effect errors to a minimum. */
|
||||
|
||||
/*
|
||||
* Baudrate is given by:
|
||||
*
|
||||
* br = fLEUARTn/(1 + (CLKDIV / 256))
|
||||
*
|
||||
* which can be rewritten to
|
||||
*
|
||||
* br = (256 * fLEUARTn)/(256 + CLKDIV)
|
||||
*
|
||||
* Normally, with fLEUARTn appr 32768Hz, there is no problem with overflow
|
||||
* if using 32 bit arithmetic. However, since fLEUARTn may be derived from
|
||||
* HFCORECLK as well, we must consider overflow when using integer arithmetic.
|
||||
*/
|
||||
|
||||
/*
|
||||
* The basic problem with integer division in the above formula is that
|
||||
* the dividend (256 * fLEUARTn) may become higher than max 32 bit
|
||||
* integer. Yet we want to evaluate dividend first before dividing in
|
||||
* order to get as small rounding effects as possible. We do not want
|
||||
* to make too harsh restrictions on max fLEUARTn value either.
|
||||
*
|
||||
* For division a/b, we can write
|
||||
*
|
||||
* a = qb + r
|
||||
*
|
||||
* where q is the quotient and r is the remainder, both integers.
|
||||
*
|
||||
* The orignal baudrate formula can be rewritten as
|
||||
*
|
||||
* br = 256a / b = 256(qb + r)/b = 256q + 256r/b
|
||||
*
|
||||
* where a is 'refFreq' and b is 'divisor', referring to variable names.
|
||||
*/
|
||||
|
||||
divisor = 256 + clkdiv;
|
||||
|
||||
quotient = refFreq / divisor;
|
||||
remainder = refFreq % divisor;
|
||||
|
||||
/* Since divisor >= 256, the below cannot exceed max 32 bit value. */
|
||||
br = 256 * quotient;
|
||||
|
||||
/*
|
||||
* Remainder < (256 + clkdiv), which means dividend (256 * remainder) worst case is
|
||||
* 256*(256 + 0x7ff8) = 0x80F800.
|
||||
*/
|
||||
br += (256 * remainder) / divisor;
|
||||
|
||||
return br;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get current baudrate for LEUART.
|
||||
*
|
||||
* @details
|
||||
* This function returns the actual baudrate (not considering oscillator
|
||||
* inaccuracies) used by a LEUART peripheral.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Current baudrate.
|
||||
******************************************************************************/
|
||||
uint32_t LEUART_BaudrateGet(LEUART_TypeDef *leuart)
|
||||
{
|
||||
uint32_t freq;
|
||||
CMU_Clock_TypeDef clock;
|
||||
|
||||
/* Get current frequency */
|
||||
if (leuart == LEUART0)
|
||||
{
|
||||
clock = cmuClock_LEUART0;
|
||||
}
|
||||
#if (LEUART_COUNT > 1)
|
||||
else if (leuart == LEUART1)
|
||||
{
|
||||
clock = cmuClock_LEUART1;
|
||||
}
|
||||
#endif
|
||||
else
|
||||
{
|
||||
EFM_ASSERT(0);
|
||||
return 0;
|
||||
}
|
||||
|
||||
freq = CMU_ClockFreqGet(clock);
|
||||
|
||||
return LEUART_BaudrateCalc(freq, leuart->CLKDIV);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure baudrate (or as close as possible to specified baudrate).
|
||||
*
|
||||
* @note
|
||||
* The setting of a baudrate requires synchronization into the
|
||||
* low frequency domain. If the same register is modified before a previous
|
||||
* update has completed, this function will stall until the previous
|
||||
* synchronization has completed.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @param[in] refFreq
|
||||
* LEUART reference clock frequency in Hz that will be used. If set to 0,
|
||||
* the currently configured reference clock is assumed.
|
||||
*
|
||||
* @param[in] baudrate
|
||||
* Baudrate to try to achieve for LEUART.
|
||||
******************************************************************************/
|
||||
void LEUART_BaudrateSet(LEUART_TypeDef *leuart,
|
||||
uint32_t refFreq,
|
||||
uint32_t baudrate)
|
||||
{
|
||||
uint32_t clkdiv;
|
||||
CMU_Clock_TypeDef clock;
|
||||
|
||||
/* Inhibit divide by 0 */
|
||||
EFM_ASSERT(baudrate);
|
||||
|
||||
/*
|
||||
* We want to use integer division to avoid forcing in float division
|
||||
* utils, and yet keep rounding effect errors to a minimum.
|
||||
*
|
||||
* CLKDIV in asynchronous mode is given by:
|
||||
*
|
||||
* CLKDIV = 256*(fLEUARTn/br - 1) = ((256*fLEUARTn)/br) - 256
|
||||
*
|
||||
* Normally, with fLEUARTn appr 32768Hz, there is no problem with overflow
|
||||
* if using 32 bit arithmetic. However, since fLEUARTn may be derived from
|
||||
* HFCORECLK as well, we must consider overflow when using integer arithmetic.
|
||||
*
|
||||
* The basic problem with integer division in the above formula is that
|
||||
* the dividend (256 * fLEUARTn) may become higher than max 32 bit
|
||||
* integer. Yet, we want to evaluate dividend first before dividing in
|
||||
* order to get as small rounding effects as possible. We do not want
|
||||
* to make too harsh restrictions on max fLEUARTn value either.
|
||||
*
|
||||
* Since the last 3 bits of CLKDIV are don't care, we can base our
|
||||
* integer arithmetic on the below formula
|
||||
*
|
||||
* CLKDIV/8 = ((32*fLEUARTn)/br) - 32
|
||||
*
|
||||
* and calculate 1/8 of CLKDIV first. This allows for fLEUARTn
|
||||
* up to 128MHz without overflowing a 32 bit value!
|
||||
*/
|
||||
|
||||
/* Get current frequency? */
|
||||
if (!refFreq)
|
||||
{
|
||||
if (leuart == LEUART0)
|
||||
{
|
||||
clock = cmuClock_LEUART0;
|
||||
}
|
||||
#if (LEUART_COUNT > 1)
|
||||
else if (leuart == LEUART1)
|
||||
{
|
||||
clock = cmuClock_LEUART1;
|
||||
}
|
||||
#endif
|
||||
else
|
||||
{
|
||||
EFM_ASSERT(0);
|
||||
return;
|
||||
}
|
||||
|
||||
refFreq = CMU_ClockFreqGet(clock);
|
||||
}
|
||||
|
||||
/* Calculate and set CLKDIV with fractional bits */
|
||||
clkdiv = (32 * refFreq) / baudrate;
|
||||
clkdiv -= 32;
|
||||
clkdiv *= 8;
|
||||
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LEUART_Sync(leuart, LEUART_SYNCBUSY_CLKDIV);
|
||||
|
||||
leuart->CLKDIV = clkdiv;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable/disable LEUART receiver and/or transmitter.
|
||||
*
|
||||
* @details
|
||||
* Notice that this function does not do any configuration. Enabling should
|
||||
* normally be done after initialization is done (if not enabled as part
|
||||
* of init).
|
||||
*
|
||||
* @note
|
||||
* Enabling/disabling requires synchronization into the low frequency domain.
|
||||
* If the same register is modified before a previous update has completed,
|
||||
* this function will stall until the previous synchronization has completed.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @param[in] enable
|
||||
* Select status for receiver/transmitter.
|
||||
******************************************************************************/
|
||||
void LEUART_Enable(LEUART_TypeDef *leuart, LEUART_Enable_TypeDef enable)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
/* Make sure the module exists on the selected chip */
|
||||
EFM_ASSERT(LEUART_REF_VALID(leuart));
|
||||
|
||||
/* Disable as specified */
|
||||
tmp = ~((uint32_t)(enable));
|
||||
tmp &= (_LEUART_CMD_RXEN_MASK | _LEUART_CMD_TXEN_MASK);
|
||||
tmp <<= 1;
|
||||
/* Enable as specified */
|
||||
tmp |= (uint32_t)(enable);
|
||||
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LEUART_Sync(leuart, LEUART_SYNCBUSY_CMD);
|
||||
|
||||
leuart->CMD = tmp;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* LEUART register synchronization freeze control.
|
||||
*
|
||||
* @details
|
||||
* Some LEUART registers require synchronization into the low frequency (LF)
|
||||
* domain. The freeze feature allows for several such registers to be
|
||||
* modified before passing them to the LF domain simultaneously (which
|
||||
* takes place when the freeze mode is disabled).
|
||||
*
|
||||
* @note
|
||||
* When enabling freeze mode, this function will wait for all current
|
||||
* ongoing LEUART synchronization to LF domain to complete (Normally
|
||||
* synchronization will not be in progress.) However for this reason, when
|
||||
* using freeze mode, modifications of registers requiring LF synchronization
|
||||
* should be done within one freeze enable/disable block to avoid unecessary
|
||||
* stalling.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @param[in] enable
|
||||
* @li true - enable freeze, modified registers are not propagated to the
|
||||
* LF domain
|
||||
* @li false - disables freeze, modified registers are propagated to LF
|
||||
* domain
|
||||
******************************************************************************/
|
||||
void LEUART_FreezeEnable(LEUART_TypeDef *leuart, bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
/*
|
||||
* Wait for any ongoing LF synchronization to complete. This is just to
|
||||
* protect against the rare case when a user
|
||||
* - modifies a register requiring LF sync
|
||||
* - then enables freeze before LF sync completed
|
||||
* - then modifies the same register again
|
||||
* since modifying a register while it is in sync progress should be
|
||||
* avoided.
|
||||
*/
|
||||
while (leuart->SYNCBUSY)
|
||||
;
|
||||
|
||||
leuart->FREEZE = LEUART_FREEZE_REGFREEZE;
|
||||
}
|
||||
else
|
||||
{
|
||||
leuart->FREEZE = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Init LEUART.
|
||||
*
|
||||
* @details
|
||||
* This function will configure basic settings in order to operate in normal
|
||||
* asynchronous mode. Consider using LEUART_Reset() prior to this function if
|
||||
* state of configuration is not known, since only configuration settings
|
||||
* specified by @p init are set.
|
||||
*
|
||||
* Special control setup not covered by this function may be done either
|
||||
* before or after using this function (but normally before enabling)
|
||||
* by direct modification of the CTRL register.
|
||||
*
|
||||
* Notice that pins used by the LEUART module must be properly configured
|
||||
* by the user explicitly, in order for the LEUART to work as intended.
|
||||
* (When configuring pins, one should remember to consider the sequence of
|
||||
* configuration, in order to avoid unintended pulses/glitches on output
|
||||
* pins.)
|
||||
*
|
||||
* @note
|
||||
* Initializing requires synchronization into the low frequency domain.
|
||||
* If the same register is modified before a previous update has completed,
|
||||
* this function will stall until the previous synchronization has completed.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to initialization structure used to configure basic async setup.
|
||||
******************************************************************************/
|
||||
void LEUART_Init(LEUART_TypeDef *leuart, LEUART_Init_TypeDef *init)
|
||||
{
|
||||
/* Make sure the module exists on the selected chip */
|
||||
EFM_ASSERT(LEUART_REF_VALID(leuart));
|
||||
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LEUART_Sync(leuart, LEUART_SYNCBUSY_CMD);
|
||||
|
||||
/* Ensure disabled while doing config */
|
||||
leuart->CMD = LEUART_CMD_RXDIS | LEUART_CMD_TXDIS;
|
||||
|
||||
/* Freeze registers to avoid stalling for LF synchronization */
|
||||
LEUART_FreezeEnable(leuart, true);
|
||||
|
||||
/* Configure databits and stopbits */
|
||||
leuart->CTRL = (leuart->CTRL & ~(_LEUART_CTRL_PARITY_MASK |
|
||||
_LEUART_CTRL_STOPBITS_MASK)) |
|
||||
(uint32_t)(init->databits) |
|
||||
(uint32_t)(init->parity) |
|
||||
(uint32_t)(init->stopbits);
|
||||
|
||||
/* Configure baudrate */
|
||||
LEUART_BaudrateSet(leuart, init->refFreq, init->baudrate);
|
||||
|
||||
/* Finally enable (as specified) */
|
||||
leuart->CMD = (uint32_t)(init->enable);
|
||||
|
||||
/* Unfreeze registers, pass new settings on to LEUART */
|
||||
LEUART_FreezeEnable(leuart, false);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Reset LEUART to same state as after a HW reset.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
******************************************************************************/
|
||||
void LEUART_Reset(LEUART_TypeDef *leuart)
|
||||
{
|
||||
/* Make sure the module exists on the selected chip */
|
||||
EFM_ASSERT(LEUART_REF_VALID(leuart));
|
||||
|
||||
/* Freeze registers to avoid stalling for LF synchronization */
|
||||
LEUART_FreezeEnable(leuart, true);
|
||||
|
||||
/* Make sure disabled first, before resetting other registers */
|
||||
leuart->CMD = LEUART_CMD_RXDIS | LEUART_CMD_TXDIS | LEUART_CMD_RXBLOCKDIS |
|
||||
LEUART_CMD_CLEARTX | LEUART_CMD_CLEARRX;
|
||||
leuart->CTRL = _LEUART_CTRL_RESETVALUE;
|
||||
leuart->CLKDIV = _LEUART_CLKDIV_RESETVALUE;
|
||||
leuart->STARTFRAME = _LEUART_STARTFRAME_RESETVALUE;
|
||||
leuart->SIGFRAME = _LEUART_SIGFRAME_RESETVALUE;
|
||||
leuart->IEN = _LEUART_IEN_RESETVALUE;
|
||||
leuart->IFC = _LEUART_IFC_MASK;
|
||||
leuart->PULSECTRL = _LEUART_PULSECTRL_RESETVALUE;
|
||||
leuart->ROUTE = _LEUART_ROUTE_RESETVALUE;
|
||||
/* Do not reset route register, setting should be done independently */
|
||||
|
||||
/* Unfreeze registers, pass new settings on to LEUART */
|
||||
LEUART_FreezeEnable(leuart, false);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Receive one 8 bit frame, (or part of 9 bit frame).
|
||||
*
|
||||
* @details
|
||||
* This function is normally used to receive one frame when operating with
|
||||
* frame length 8 bits. Please refer to LEUART_RxExt() for reception of
|
||||
* 9 bit frames.
|
||||
*
|
||||
* Notice that possible parity/stop bits are not considered part of specified
|
||||
* frame bit length.
|
||||
*
|
||||
* @note
|
||||
* This function will stall if buffer is empty, until data is received.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Data received.
|
||||
******************************************************************************/
|
||||
uint8_t LEUART_Rx(LEUART_TypeDef *leuart)
|
||||
{
|
||||
while (!(leuart->STATUS & LEUART_STATUS_RXDATAV))
|
||||
;
|
||||
|
||||
return (uint8_t)(leuart->RXDATA);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Receive one 8-9 bit frame, with extended information.
|
||||
*
|
||||
* @details
|
||||
* This function is normally used to receive one frame and additional RX
|
||||
* status information is required.
|
||||
*
|
||||
* @note
|
||||
* This function will stall if buffer is empty, until data is received.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @return
|
||||
* Data received.
|
||||
******************************************************************************/
|
||||
uint16_t LEUART_RxExt(LEUART_TypeDef *leuart)
|
||||
{
|
||||
while (!(leuart->STATUS & LEUART_STATUS_RXDATAV))
|
||||
;
|
||||
|
||||
return (uint16_t)(leuart->RXDATAX);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Transmit one frame.
|
||||
*
|
||||
* @details
|
||||
* Depending on frame length configuration, 8 (least significant) bits from
|
||||
* @p data are transmitted. If frame length is 9, 8 bits are transmitted from
|
||||
* @p data and one bit as specified by CTRL register, BIT8DV field. Please
|
||||
* refer to LEUART_TxExt() for transmitting 9 bit frame with full control of
|
||||
* all 9 bits.
|
||||
*
|
||||
* Notice that possible parity/stop bits in asynchronous mode are not
|
||||
* considered part of specified frame bit length.
|
||||
*
|
||||
* @note
|
||||
* This function will stall if buffer is full, until buffer becomes available.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @param[in] data
|
||||
* Data to transmit. See details above for further info.
|
||||
******************************************************************************/
|
||||
void LEUART_Tx(LEUART_TypeDef *leuart, uint8_t data)
|
||||
{
|
||||
/* Check that transmit buffer is empty */
|
||||
while (!(leuart->STATUS & LEUART_STATUS_TXBL))
|
||||
;
|
||||
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LEUART_Sync(leuart, LEUART_SYNCBUSY_TXDATA);
|
||||
|
||||
leuart->TXDATA = (uint32_t)data;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Transmit one 8-9 bit frame with extended control.
|
||||
*
|
||||
* @details
|
||||
* Notice that possible parity/stop bits in asynchronous mode are not
|
||||
* considered part of specified frame bit length.
|
||||
*
|
||||
* @note
|
||||
* This function will stall if buffer is full, until buffer becomes available.
|
||||
*
|
||||
* @param[in] leuart
|
||||
* Pointer to LEUART peripheral register block.
|
||||
*
|
||||
* @param[in] data
|
||||
* Data to transmit with extended control. Least significant bits contains
|
||||
* frame bits, and additional control bits are available as documented in
|
||||
* the EFM32 reference manual (set to 0 if not used).
|
||||
******************************************************************************/
|
||||
void LEUART_TxExt(LEUART_TypeDef *leuart, uint16_t data)
|
||||
{
|
||||
/* Check that transmit buffer is empty */
|
||||
while (!(leuart->STATUS & LEUART_STATUS_TXBL))
|
||||
;
|
||||
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
LEUART_Sync(leuart, LEUART_SYNCBUSY_TXDATAX);
|
||||
|
||||
leuart->TXDATAX = (uint32_t)data;
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup LEUART) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,117 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Memory Protection Unit (MPU) Peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#include "efm32_mpu.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup MPU
|
||||
* @brief Memory Protection Unit (MPU) Peripheral API for EFM32
|
||||
* @details
|
||||
* This module contains functions to enable, disable and setup the MPU.
|
||||
* The MPU is used to control access attributes and permissions in the
|
||||
* memory map. The settings that can be controlled are:
|
||||
*
|
||||
* @li Executable attribute.
|
||||
* @li Cachable, bufferable and shareable attributes.
|
||||
* @li Cache policy.
|
||||
* @li Access permissions: Priviliged or User state, read or write access,
|
||||
* and combinations of all these.
|
||||
*
|
||||
* The MPU can be activated and deactivated with functions:
|
||||
* @verbatim
|
||||
* MPU_Enable(..);
|
||||
* MPU_Disable();@endverbatim
|
||||
* The MPU can control 8 memory regions with individual access control
|
||||
* settings. Section attributes and permissions are set with:
|
||||
* @verbatim
|
||||
* MPU_ConfigureRegion(..);@endverbatim
|
||||
* It is advisable to disable the MPU when altering region settings.
|
||||
*
|
||||
*
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure an MPU region.
|
||||
*
|
||||
* @details
|
||||
* Writes to MPU RBAR and RASR registers.
|
||||
* Refer to Cortex-M3 Reference Manual, MPU chapter for further details.
|
||||
* To disable a region it is only required to set init->regionNo to the
|
||||
* desired value and init->regionEnable = false.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to a structure containing MPU region init information.
|
||||
******************************************************************************/
|
||||
void MPU_ConfigureRegion(const MPU_RegionInit_TypeDef *init)
|
||||
{
|
||||
EFM_ASSERT(init->regionNo < ((MPU->TYPE & MPU_TYPE_DREGION_Msk) >>
|
||||
MPU_TYPE_DREGION_Pos));
|
||||
|
||||
MPU->RNR = init->regionNo;
|
||||
|
||||
if (init->regionEnable)
|
||||
{
|
||||
EFM_ASSERT(!(init->baseAddress & ~MPU_RBAR_ADDR_Msk));
|
||||
EFM_ASSERT(init->tex <= 0x7);
|
||||
|
||||
MPU->RBAR = init->baseAddress;
|
||||
MPU->RASR = ((init->disableExec ? 1 : 0) << MPU_RASR_XN_Pos) |
|
||||
(init->accessPermission << MPU_RASR_AP_Pos) |
|
||||
(init->tex << MPU_RASR_TEX_Pos) |
|
||||
((init->shareable ? 1 : 0) << MPU_RASR_S_Pos) |
|
||||
((init->cacheable ? 1 : 0) << MPU_RASR_C_Pos) |
|
||||
((init->bufferable ? 1 : 0) << MPU_RASR_B_Pos) |
|
||||
(init->srd << MPU_RASR_SRD_Pos) |
|
||||
(init->size << MPU_RASR_SIZE_Pos) |
|
||||
(1 << MPU_RASR_ENA_Pos);
|
||||
}
|
||||
else
|
||||
{
|
||||
MPU->RBAR = 0;
|
||||
MPU->RASR = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup CMU) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,369 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Flash controller (MSC) Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#include "efm32_msc.h"
|
||||
#if defined (_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
#include "efm32_cmu.h"
|
||||
#endif
|
||||
#include "efm32_assert.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup MSC
|
||||
* @brief Flash controller (MSC) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enables the flash controller for writing.
|
||||
* @note
|
||||
* IMPORTANT: This function must be called before flash operations when
|
||||
* AUXHFRCO clock has been changed from default 14MHz band.
|
||||
******************************************************************************/
|
||||
void MSC_Init(void)
|
||||
{
|
||||
#if defined (_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
uint32_t freq, cycles;
|
||||
#endif
|
||||
/* Enable writing to the MSC */
|
||||
MSC->WRITECTRL |= MSC_WRITECTRL_WREN;
|
||||
/* Unlock the MSC */
|
||||
MSC->LOCK = MSC_UNLOCK_CODE;
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
|
||||
#if defined (_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/* Configure MSC->TIMEBASE according to selected frequency */
|
||||
freq = CMU_ClockFreqGet(cmuClock_AUX);
|
||||
|
||||
if( freq > 7000000)
|
||||
{
|
||||
/* Calculate number of clock cycles for 1us as base period */
|
||||
freq = (freq * 11) / 10;
|
||||
cycles = (freq / 1000000) + 1;
|
||||
|
||||
/* Configure clock cycles for flash timing */
|
||||
MSC->TIMEBASE = (MSC->TIMEBASE & ~(_MSC_TIMEBASE_BASE_MASK|
|
||||
_MSC_TIMEBASE_PERIOD_MASK))|
|
||||
MSC_TIMEBASE_PERIOD_1US|
|
||||
(cycles << _MSC_TIMEBASE_BASE_SHIFT);
|
||||
}
|
||||
else
|
||||
{
|
||||
/* Calculate number of clock cycles for 5us as base period */
|
||||
freq = (freq * 5 * 11) / 10;
|
||||
cycles = (freq / 1000000) + 1;
|
||||
|
||||
/* Configure clock cycles for flash timing */
|
||||
MSC->TIMEBASE = (MSC->TIMEBASE & ~(_MSC_TIMEBASE_BASE_MASK|
|
||||
_MSC_TIMEBASE_PERIOD_MASK))|
|
||||
MSC_TIMEBASE_PERIOD_5US|
|
||||
(cycles << _MSC_TIMEBASE_BASE_SHIFT);
|
||||
}
|
||||
#endif
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disables the flash controller for writing.
|
||||
******************************************************************************/
|
||||
void MSC_Deinit(void)
|
||||
{
|
||||
/* Enable writing to the MSC */
|
||||
MSC->WRITECTRL |= MSC_WRITECTRL_WREN;
|
||||
/* Lock the MSC */
|
||||
MSC->LOCK = 0;
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Erases a page in flash memory.
|
||||
* @note
|
||||
* This function MUST be executed from RAM. Failure to execute this portion
|
||||
* of the code in RAM will result in a hardfault. For IAR, Rowley and
|
||||
* Codesourcery this will be achieved automatically. For Keil uVision 4 you
|
||||
* must define a section called "ram_code" and place this manually in your
|
||||
* project's scatter file.
|
||||
* @param[in] startAddress
|
||||
* Pointer to the flash page to erase. Must be aligned to beginning of page
|
||||
* boundary.
|
||||
* @return
|
||||
* Returns the status of erase operation, #msc_Return_TypeDef
|
||||
* @verbatim
|
||||
* flashReturnOk - Operation completed successfully.
|
||||
* flashReturnInvalidAddr - Operation tried to erase a non-flash area.
|
||||
* flashReturnLocked - Operation tried to erase a locked area of the flash.
|
||||
* flashReturnTimeOut - Operation timed out waiting for flash operation
|
||||
* to complete.
|
||||
* @endverbatim
|
||||
******************************************************************************/
|
||||
#ifdef __CC_ARM /* MDK-ARM compiler */
|
||||
#pragma arm section code="ram_code"
|
||||
#endif /* __CC_ARM */
|
||||
#if defined( __ICCARM__ )
|
||||
/* Suppress warnings originating from use of EFM_ASSERT(): */
|
||||
/* "Call to a non __ramfunc function from within a __ramfunc function" */
|
||||
/* "Possible rom access from within a __ramfunc function" */
|
||||
#pragma diag_suppress=Ta022
|
||||
#pragma diag_suppress=Ta023
|
||||
#endif
|
||||
msc_Return_TypeDef MSC_ErasePage(uint32_t *startAddress)
|
||||
{
|
||||
int timeOut = MSC_PROGRAM_TIMEOUT;
|
||||
|
||||
/* Address must be aligned to pages */
|
||||
EFM_ASSERT((((uint32_t)startAddress) & 0x1FF) == 0);
|
||||
|
||||
/* Enable writing to the MSC */
|
||||
MSC->WRITECTRL |= MSC_WRITECTRL_WREN;
|
||||
|
||||
/* Load address */
|
||||
MSC->ADDRB = (uint32_t)startAddress;
|
||||
MSC->WRITECMD = MSC_WRITECMD_LADDRIM;
|
||||
|
||||
/* Check for invalid address */
|
||||
if (MSC->STATUS & MSC_STATUS_INVADDR)
|
||||
{
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
return mscReturnInvalidAddr;
|
||||
}
|
||||
|
||||
/* Check for write protected page */
|
||||
if (MSC->STATUS & MSC_STATUS_LOCKED)
|
||||
{
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
return mscReturnLocked;
|
||||
}
|
||||
|
||||
/* Send erase page command */
|
||||
MSC->WRITECMD = MSC_WRITECMD_ERASEPAGE;
|
||||
|
||||
/* Wait for the erase to complete */
|
||||
while ((MSC->STATUS & MSC_STATUS_BUSY) && (timeOut != 0))
|
||||
{
|
||||
timeOut--;
|
||||
}
|
||||
|
||||
if (timeOut == 0)
|
||||
{
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
return mscReturnTimeOut;
|
||||
}
|
||||
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
return mscReturnOk;
|
||||
}
|
||||
#if defined( __ICCARM__ )
|
||||
#pragma diag_default=Ta022
|
||||
#pragma diag_default=Ta023
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Writes a single word to flash memory. Data to write must be aligned to
|
||||
* words and contain a number of bytes that is divisable by four.
|
||||
* @note
|
||||
* The flash must be erased prior to writing a new word.
|
||||
* This function must be run from RAM. Failure to execute this portion
|
||||
* of the code in RAM will result in a hardfault. For IAR, Rowley and
|
||||
* Codesourcery this will be achieved automatically. For Keil uVision 4 you
|
||||
* must define a section called "ram_code" and place this manually in your
|
||||
* project's scatter file.
|
||||
*
|
||||
* @param[in] address
|
||||
* Pointer to the flash word to write to. Must be aligned to words.
|
||||
* @param[in] data
|
||||
* Data to write to flash.
|
||||
* @param[in] numBytes
|
||||
* Number of bytes to write from flash. NB: Must be divisable by four.
|
||||
* @return
|
||||
* Returns the status of the write operation, #msc_Return_TypeDef
|
||||
* @verbatim
|
||||
* flashReturnOk - Operation completed successfully.
|
||||
* flashReturnInvalidAddr - Operation tried to erase a non-flash area.
|
||||
* flashReturnLocked - Operation tried to erase a locked area of the flash.
|
||||
* flashReturnTimeOut - Operation timed out waiting for flash operation
|
||||
* to complete.
|
||||
* @endverbatim
|
||||
******************************************************************************/
|
||||
#ifdef __CC_ARM /* MDK-ARM compiler */
|
||||
#pragma arm section code="ram_code"
|
||||
#endif /* __CC_ARM */
|
||||
#if defined( __ICCARM__ )
|
||||
/* Suppress warnings originating from use of EFM_ASSERT(): */
|
||||
/* "Call to a non __ramfunc function from within a __ramfunc function" */
|
||||
/* "Possible rom access from within a __ramfunc function" */
|
||||
#pragma diag_suppress=Ta022
|
||||
#pragma diag_suppress=Ta023
|
||||
#endif
|
||||
msc_Return_TypeDef MSC_WriteWord(uint32_t *address, void const *data, int numBytes)
|
||||
{
|
||||
int timeOut;
|
||||
int wordCount;
|
||||
int numWords;
|
||||
|
||||
/* Check alignment (Must be aligned to words) */
|
||||
EFM_ASSERT(((uint32_t) address & 0x3) == 0);
|
||||
|
||||
/* Check number of bytes. Must be divisable by four */
|
||||
EFM_ASSERT((numBytes & 0x3) == 0);
|
||||
|
||||
/* Enable writing to the MSC */
|
||||
MSC->WRITECTRL |= MSC_WRITECTRL_WREN;
|
||||
|
||||
/* Convert bytes to words */
|
||||
numWords = numBytes >> 2;
|
||||
|
||||
for (wordCount = 0; wordCount < numWords; wordCount++)
|
||||
{
|
||||
/* Load address */
|
||||
MSC->ADDRB = (uint32_t)(address + wordCount);
|
||||
MSC->WRITECMD = MSC_WRITECMD_LADDRIM;
|
||||
|
||||
/* Check for invalid address */
|
||||
if (MSC->STATUS & MSC_STATUS_INVADDR)
|
||||
{
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
return mscReturnInvalidAddr;
|
||||
}
|
||||
|
||||
/* Check for write protected page */
|
||||
if (MSC->STATUS & MSC_STATUS_LOCKED)
|
||||
{
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
return mscReturnLocked;
|
||||
}
|
||||
|
||||
/* Wait for the MSC to be ready for a new data word */
|
||||
/* Due to the timing of this function, the MSC should already by ready */
|
||||
timeOut = MSC_PROGRAM_TIMEOUT;
|
||||
while (((MSC->STATUS & MSC_STATUS_WDATAREADY) == 0) && (timeOut != 0))
|
||||
{
|
||||
timeOut--;
|
||||
}
|
||||
|
||||
/* Check for timeout */
|
||||
if (timeOut == 0)
|
||||
{
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
return mscReturnTimeOut;
|
||||
}
|
||||
|
||||
/* Load data into write data register */
|
||||
MSC->WDATA = *(((uint32_t *)data) + wordCount);
|
||||
|
||||
/* Trigger write once */
|
||||
MSC->WRITECMD = MSC_WRITECMD_WRITEONCE;
|
||||
|
||||
/* Wait for the write to complete */
|
||||
timeOut = MSC_PROGRAM_TIMEOUT;
|
||||
while ((MSC->STATUS & MSC_STATUS_BUSY) && (timeOut != 0))
|
||||
{
|
||||
timeOut--;
|
||||
}
|
||||
|
||||
/* Check for timeout */
|
||||
if (timeOut == 0)
|
||||
{
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
return mscReturnTimeOut;
|
||||
}
|
||||
}
|
||||
/* Disable writing to the MSC */
|
||||
MSC->WRITECTRL &= ~MSC_WRITECTRL_WREN;
|
||||
return mscReturnOk;
|
||||
}
|
||||
#if defined( __ICCARM__ )
|
||||
#pragma diag_default=Ta022
|
||||
#pragma diag_default=Ta023
|
||||
#endif
|
||||
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY)
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Erase entire flash in one operation
|
||||
* @note
|
||||
* This command will erase the entire contents of the device.
|
||||
* Use with care, both a debug session and all contents of the flash will be
|
||||
* lost. The lock bit, MLW will prevent this operation from executing and
|
||||
* might prevent successful mass erase.
|
||||
******************************************************************************/
|
||||
#ifdef __CC_ARM /* MDK-ARM compiler */
|
||||
#pragma arm section code="ram_code"
|
||||
#endif /* __CC_ARM */
|
||||
msc_Return_TypeDef MSC_MassErase(void)
|
||||
{
|
||||
/* Enable writing to the MSC */
|
||||
MSC->WRITECTRL |= MSC_WRITECTRL_WREN;
|
||||
|
||||
/* Unlock device mass erase */
|
||||
MSC->MASSLOCK = MSC_MASSLOCK_LOCKKEY_UNLOCK;
|
||||
|
||||
/* Erase first 512K block */
|
||||
MSC->WRITECMD = MSC_WRITECMD_ERASEMAIN0;
|
||||
|
||||
/* Waiting for erase to complete */
|
||||
while ((MSC->STATUS & MSC_STATUS_BUSY)){}
|
||||
|
||||
#if FLASH_SIZE >= (512*1024)
|
||||
/* Erase second 512K block */
|
||||
MSC->WRITECMD = MSC_WRITECMD_ERASEMAIN1;
|
||||
|
||||
/* Waiting for erase to complete */
|
||||
while ((MSC->STATUS & MSC_STATUS_BUSY)){}
|
||||
#endif
|
||||
|
||||
/* Restore mass erase lock */
|
||||
MSC->MASSLOCK = MSC_MASSLOCK_LOCKKEY_LOCK;
|
||||
|
||||
/* This will only successfully return if calling function is also in SRAM */
|
||||
return mscReturnOk;
|
||||
}
|
||||
#endif
|
||||
|
||||
/** @} (end addtogroup MSC) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,402 @@
|
|||
/**************************************************************************//**
|
||||
* @file
|
||||
* @brief Operational Amplifier (OPAMP) peripheral API for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2011 Energy Micro AS, http://www.energymicro.com</b>
|
||||
******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
*****************************************************************************/
|
||||
#include "efm32.h"
|
||||
#if defined( OPAMP_PRESENT ) && ( OPAMP_COUNT == 1 )
|
||||
|
||||
#include "efm32_system.h"
|
||||
#include "efm32_assert.h"
|
||||
#include "efm32_opamp.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup OPAMP
|
||||
* @brief Operational Amplifier (OPAMP) peripheral API for EFM32.
|
||||
* @details
|
||||
* This module contains functions to:
|
||||
* @li OPAMP_Enable() Configure and enable an opamp.
|
||||
* @li OPAMP_Disable() Disable an opamp.
|
||||
*
|
||||
* All OPAMP functions assume that the DAC clock is running. If the DAC is not
|
||||
* used, the clock can be turned off when the opamp's are configured.
|
||||
*
|
||||
* If the available gain values dont suit the application at hand, the resistor
|
||||
* ladders can be disabled and external gain programming resistors used.
|
||||
*
|
||||
* A number of predefined opamp setup macros are available for configuration
|
||||
* of the most common opamp topologies (see figures below).
|
||||
*
|
||||
* @note
|
||||
* <em>The terms POSPAD and NEGPAD in the figures are used to indicate that these
|
||||
* pads should be connected to a suitable signal ground.</em>
|
||||
*
|
||||
* \n<b>Unity gain voltage follower.</b>\n
|
||||
* Use predefined macros @ref OPA_INIT_UNITY_GAIN and
|
||||
* @ref OPA_INIT_UNITY_GAIN_OPA2.
|
||||
* @verbatim
|
||||
|
||||
|\
|
||||
___________|+\
|
||||
| \_______
|
||||
___|_ / |
|
||||
| | / |
|
||||
| |/ |
|
||||
|___________|
|
||||
@endverbatim
|
||||
*
|
||||
* \n<b>Non-inverting amplifier.</b>\n
|
||||
* Use predefined macros @ref OPA_INIT_NON_INVERTING and
|
||||
* @ref OPA_INIT_NON_INVERTING_OPA2.
|
||||
* @verbatim
|
||||
|
||||
|\
|
||||
___________|+\
|
||||
| \_______
|
||||
___|_ / |
|
||||
| | / |
|
||||
| |/ |
|
||||
|_____R2____|
|
||||
|
|
||||
R1
|
||||
|
|
||||
NEGPAD @endverbatim
|
||||
*
|
||||
* \n<b>Inverting amplifier.</b>\n
|
||||
* Use predefined macros @ref OPA_INIT_INVERTING and
|
||||
* @ref OPA_INIT_INVERTING_OPA2.
|
||||
* @verbatim
|
||||
|
||||
_____R2____
|
||||
| |
|
||||
| |\ |
|
||||
____R1_|___|_\ |
|
||||
| \____|___
|
||||
___| /
|
||||
| |+/
|
||||
| |/
|
||||
|
|
||||
POSPAD @endverbatim
|
||||
*
|
||||
* \n<b>Cascaded non-inverting amplifiers.</b>\n
|
||||
* Use predefined macros @ref OPA_INIT_CASCADED_NON_INVERTING_OPA0,
|
||||
* @ref OPA_INIT_CASCADED_NON_INVERTING_OPA1 and
|
||||
* @ref OPA_INIT_CASCADED_NON_INVERTING_OPA2.
|
||||
* @verbatim
|
||||
|
||||
|\ |\ |\
|
||||
___________|+\ OPA0 ___________|+\ OPA1 ___________|+\ OPA2
|
||||
| \_________| | \_________| | \_______
|
||||
___|_ / | ___|_ / | ___|_ / |
|
||||
| | / | | | / | | | / |
|
||||
| |/ | | |/ | | |/ |
|
||||
|_____R2____| |_____R2____| |_____R2____|
|
||||
| | |
|
||||
R1 R1 R1
|
||||
| | |
|
||||
NEGPAD NEGPAD NEGPAD @endverbatim
|
||||
*
|
||||
* \n<b>Cascaded inverting amplifiers.</b>\n
|
||||
* Use predefined macros @ref OPA_INIT_CASCADED_INVERTING_OPA0,
|
||||
* @ref OPA_INIT_CASCADED_INVERTING_OPA1 and
|
||||
* @ref OPA_INIT_CASCADED_INVERTING_OPA2.
|
||||
* @verbatim
|
||||
|
||||
_____R2____ _____R2____ _____R2____
|
||||
| | | | | |
|
||||
| |\ | | |\ | | |\ |
|
||||
____R1_|___|_\ | ____R1_|___|_\ | ____R1_|___|_\ |
|
||||
| \____|____| | \____|___| | \____|__
|
||||
___| / ___| / ___| /
|
||||
| |+/ OPA0 | |+/ OPA1 | |+/ OPA2
|
||||
| |/ | |/ | |/
|
||||
| | |
|
||||
POSPAD POSPAD POSPAD @endverbatim
|
||||
*
|
||||
* \n<b>Differential driver with two opamp's.</b>\n
|
||||
* Use predefined macros @ref OPA_INIT_DIFF_DRIVER_OPA0 and
|
||||
* @ref OPA_INIT_DIFF_DRIVER_OPA1.
|
||||
* @verbatim
|
||||
|
||||
__________________________
|
||||
| +
|
||||
| _____R2____
|
||||
|\ | | |
|
||||
___________|+\ OPA0 | | |\ OPA1 |
|
||||
| \_________|____R1_|___|_\ | _
|
||||
___|_ / | | \____|______
|
||||
| | / | ___| /
|
||||
| |/ | | |+/
|
||||
|________________| | |/
|
||||
|
|
||||
POSPAD @endverbatim
|
||||
*
|
||||
* \n<b>Differential receiver with three opamp's.</b>\n
|
||||
* Use predefined macros @ref OPA_INIT_DIFF_RECEIVER_OPA0,
|
||||
* @ref OPA_INIT_DIFF_RECEIVER_OPA1 and @ref OPA_INIT_DIFF_RECEIVER_OPA2.
|
||||
* @verbatim
|
||||
|
||||
|\
|
||||
__________|+\ OPA1
|
||||
_ | \_________
|
||||
___|_ / | | _____R2____
|
||||
| | / | | | |
|
||||
| |/ | | | |\ |
|
||||
|___________| |____R1_|___|_\ |
|
||||
| \____|___
|
||||
|\ ____R1_ ___| /
|
||||
+__________|+\ OPA0 | | |+/ OPA2
|
||||
| \_________| | |/
|
||||
___|_ / | R2
|
||||
| | / | |
|
||||
| |/ | NEGPAD OPA0
|
||||
|___________|
|
||||
@endverbatim
|
||||
*
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable an Operational Amplifier.
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to DAC peripheral register block.
|
||||
*
|
||||
* @param[in] opa
|
||||
* Selects an OPA, valid vaules are @ref OPA0, @ref OPA1 and @ref OPA2.
|
||||
******************************************************************************/
|
||||
void OPAMP_Disable( DAC_TypeDef *dac, OPAMP_TypeDef opa )
|
||||
{
|
||||
EFM_ASSERT( DAC_REF_VALID( dac ) );
|
||||
EFM_ASSERT( DAC_OPA_VALID( opa ) );
|
||||
|
||||
if ( opa == OPA0 )
|
||||
{
|
||||
dac->CH0CTRL &= ~DAC_CH0CTRL_EN;
|
||||
dac->OPACTRL &= ~DAC_OPACTRL_OPA0EN;
|
||||
}
|
||||
else if ( opa == OPA1 )
|
||||
{
|
||||
dac->CH1CTRL &= ~DAC_CH1CTRL_EN;
|
||||
dac->OPACTRL &= ~DAC_OPACTRL_OPA1EN;
|
||||
}
|
||||
else /* OPA2 */
|
||||
{
|
||||
dac->OPACTRL &= ~DAC_OPACTRL_OPA2EN;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure and enable an Operational Amplifier.
|
||||
*
|
||||
* @details
|
||||
*
|
||||
* @param[in] dac
|
||||
* Pointer to DAC peripheral register block.
|
||||
*
|
||||
* @param[in] opa
|
||||
* Selects an OPA, valid vaules are @ref OPA0, @ref OPA1 and @ref OPA2.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to a structure containing OPAMP init information.
|
||||
******************************************************************************/
|
||||
void OPAMP_Enable( DAC_TypeDef *dac, OPAMP_TypeDef opa, const OPAMP_Init_TypeDef *init )
|
||||
{
|
||||
uint32_t offset;
|
||||
|
||||
EFM_ASSERT( DAC_REF_VALID( dac ) );
|
||||
EFM_ASSERT( DAC_OPA_VALID( opa ) );
|
||||
EFM_ASSERT( init->bias <= ( _DAC_BIASPROG_BIASPROG_MASK >>
|
||||
_DAC_BIASPROG_BIASPROG_SHIFT ) );
|
||||
|
||||
if ( opa == OPA0 )
|
||||
{
|
||||
EFM_ASSERT( ( init->outPen & ~_DAC_OPA0MUX_OUTPEN_MASK ) == 0 );
|
||||
|
||||
dac->BIASPROG = ( dac->BIASPROG
|
||||
& ~( _DAC_BIASPROG_BIASPROG_MASK |
|
||||
DAC_BIASPROG_HALFBIAS ) ) |
|
||||
( init->bias << _DAC_BIASPROG_BIASPROG_SHIFT ) |
|
||||
( init->halfBias ? DAC_BIASPROG_HALFBIAS : 0 );
|
||||
|
||||
if ( init->defaultOffset )
|
||||
{
|
||||
offset = SYSTEM_GetCalibrationValue( &dac->CAL );
|
||||
dac->CAL = ( dac->CAL & ~_DAC_CAL_CH0OFFSET_MASK ) |
|
||||
( offset & _DAC_CAL_CH0OFFSET_MASK );
|
||||
}
|
||||
else
|
||||
{
|
||||
EFM_ASSERT( init->offset <= ( _DAC_CAL_CH0OFFSET_MASK >>
|
||||
_DAC_CAL_CH0OFFSET_SHIFT ) );
|
||||
|
||||
dac->CAL = ( dac->CAL & ~_DAC_CAL_CH0OFFSET_MASK ) |
|
||||
( init->offset << _DAC_CAL_CH0OFFSET_SHIFT );
|
||||
}
|
||||
|
||||
dac->OPA0MUX = (uint32_t)init->resSel |
|
||||
(uint32_t)init->outMode |
|
||||
init->outPen |
|
||||
(uint32_t)init->resInMux |
|
||||
(uint32_t)init->negSel |
|
||||
(uint32_t)init->posSel |
|
||||
( init->nextOut ? DAC_OPA0MUX_NEXTOUT : 0 ) |
|
||||
( init->npEn ? DAC_OPA0MUX_NPEN : 0 ) |
|
||||
( init->ppEn ? DAC_OPA0MUX_PPEN : 0 );
|
||||
|
||||
dac->CH0CTRL |= DAC_CH0CTRL_EN;
|
||||
dac->OPACTRL = ( dac->OPACTRL
|
||||
& ~( DAC_OPACTRL_OPA0SHORT |
|
||||
_DAC_OPACTRL_OPA0LPFDIS_MASK |
|
||||
DAC_OPACTRL_OPA0HCMDIS ) ) |
|
||||
( init->shortInputs ? DAC_OPACTRL_OPA0SHORT : 0 ) |
|
||||
( init->lpfPosPadDisable ?
|
||||
DAC_OPACTRL_OPA0LPFDIS_PLPFDIS : 0 ) |
|
||||
( init->lpfNegPadDisable ?
|
||||
DAC_OPACTRL_OPA0LPFDIS_NLPFDIS : 0 ) |
|
||||
( init->hcmDisable ? DAC_OPACTRL_OPA0HCMDIS : 0 ) |
|
||||
( DAC_OPACTRL_OPA0EN );
|
||||
}
|
||||
else if ( opa == OPA1 )
|
||||
{
|
||||
EFM_ASSERT( ( init->outPen & ~_DAC_OPA1MUX_OUTPEN_MASK ) == 0 );
|
||||
|
||||
dac->BIASPROG = ( dac->BIASPROG
|
||||
& ~( _DAC_BIASPROG_BIASPROG_MASK |
|
||||
DAC_BIASPROG_HALFBIAS ) ) |
|
||||
( init->bias << _DAC_BIASPROG_BIASPROG_SHIFT ) |
|
||||
( init->halfBias ? DAC_BIASPROG_HALFBIAS : 0 );
|
||||
|
||||
if ( init->defaultOffset )
|
||||
{
|
||||
offset = SYSTEM_GetCalibrationValue( &dac->CAL );
|
||||
dac->CAL = ( dac->CAL & ~_DAC_CAL_CH1OFFSET_MASK ) |
|
||||
( offset & _DAC_CAL_CH1OFFSET_MASK );
|
||||
}
|
||||
else
|
||||
{
|
||||
EFM_ASSERT( init->offset <= ( _DAC_CAL_CH1OFFSET_MASK >>
|
||||
_DAC_CAL_CH1OFFSET_SHIFT ) );
|
||||
|
||||
dac->CAL = ( dac->CAL & ~_DAC_CAL_CH1OFFSET_MASK ) |
|
||||
( init->offset << _DAC_CAL_CH1OFFSET_SHIFT );
|
||||
}
|
||||
|
||||
dac->OPA1MUX = (uint32_t)init->resSel |
|
||||
(uint32_t)init->outMode |
|
||||
init->outPen |
|
||||
(uint32_t)init->resInMux |
|
||||
(uint32_t)init->negSel |
|
||||
(uint32_t)init->posSel |
|
||||
( init->nextOut ? DAC_OPA1MUX_NEXTOUT : 0 ) |
|
||||
( init->npEn ? DAC_OPA1MUX_NPEN : 0 ) |
|
||||
( init->ppEn ? DAC_OPA1MUX_PPEN : 0 );
|
||||
|
||||
dac->CH1CTRL |= DAC_CH1CTRL_EN;
|
||||
dac->OPACTRL = ( dac->OPACTRL
|
||||
& ~( DAC_OPACTRL_OPA1SHORT |
|
||||
_DAC_OPACTRL_OPA1LPFDIS_MASK |
|
||||
DAC_OPACTRL_OPA1HCMDIS ) ) |
|
||||
( init->shortInputs ? DAC_OPACTRL_OPA1SHORT : 0 ) |
|
||||
( init->lpfPosPadDisable ?
|
||||
DAC_OPACTRL_OPA1LPFDIS_PLPFDIS : 0 ) |
|
||||
( init->lpfNegPadDisable ?
|
||||
DAC_OPACTRL_OPA1LPFDIS_NLPFDIS : 0 ) |
|
||||
( init->hcmDisable ? DAC_OPACTRL_OPA1HCMDIS : 0 ) |
|
||||
( DAC_OPACTRL_OPA1EN );
|
||||
}
|
||||
else /* OPA2 */
|
||||
{
|
||||
EFM_ASSERT( ( init->posSel == DAC_OPA2MUX_POSSEL_DISABLE ) ||
|
||||
( init->posSel == DAC_OPA2MUX_POSSEL_POSPAD ) ||
|
||||
( init->posSel == DAC_OPA2MUX_POSSEL_OPA1INP ) ||
|
||||
( init->posSel == DAC_OPA2MUX_POSSEL_OPATAP ) );
|
||||
|
||||
EFM_ASSERT( ( init->outMode & ~DAC_OPA2MUX_OUTMODE ) == 0 );
|
||||
|
||||
EFM_ASSERT( ( init->outPen & ~_DAC_OPA2MUX_OUTPEN_MASK ) == 0 );
|
||||
|
||||
dac->BIASPROG = ( dac->BIASPROG
|
||||
& ~( _DAC_BIASPROG_OPA2BIASPROG_MASK |
|
||||
DAC_BIASPROG_OPA2HALFBIAS ) ) |
|
||||
( init->bias << _DAC_BIASPROG_OPA2BIASPROG_SHIFT ) |
|
||||
( init->halfBias ? DAC_BIASPROG_OPA2HALFBIAS : 0 );
|
||||
|
||||
if ( init->defaultOffset )
|
||||
{
|
||||
offset = SYSTEM_GetCalibrationValue( &dac->OPAOFFSET );
|
||||
dac->OPAOFFSET = ( dac->OPAOFFSET & ~_DAC_OPAOFFSET_OPA2OFFSET_MASK ) |
|
||||
( offset & _DAC_OPAOFFSET_OPA2OFFSET_MASK );
|
||||
}
|
||||
else
|
||||
{
|
||||
EFM_ASSERT( init->offset <= ( _DAC_OPAOFFSET_OPA2OFFSET_MASK >>
|
||||
_DAC_OPAOFFSET_OPA2OFFSET_SHIFT ) );
|
||||
|
||||
dac->CAL = ( dac->CAL & ~_DAC_OPAOFFSET_OPA2OFFSET_MASK ) |
|
||||
( init->offset << _DAC_OPAOFFSET_OPA2OFFSET_SHIFT );
|
||||
}
|
||||
|
||||
dac->OPA2MUX = (uint32_t)init->resSel |
|
||||
(uint32_t)init->outMode |
|
||||
init->outPen |
|
||||
(uint32_t)init->resInMux |
|
||||
(uint32_t)init->negSel |
|
||||
(uint32_t)init->posSel |
|
||||
( init->nextOut ? DAC_OPA2MUX_NEXTOUT : 0 ) |
|
||||
( init->npEn ? DAC_OPA2MUX_NPEN : 0 ) |
|
||||
( init->ppEn ? DAC_OPA2MUX_PPEN : 0 );
|
||||
|
||||
dac->OPACTRL = ( dac->OPACTRL
|
||||
& ~( DAC_OPACTRL_OPA2SHORT |
|
||||
_DAC_OPACTRL_OPA2LPFDIS_MASK |
|
||||
DAC_OPACTRL_OPA2HCMDIS ) ) |
|
||||
( init->shortInputs ? DAC_OPACTRL_OPA2SHORT : 0 ) |
|
||||
( init->lpfPosPadDisable ?
|
||||
DAC_OPACTRL_OPA2LPFDIS_PLPFDIS : 0 ) |
|
||||
( init->lpfNegPadDisable ?
|
||||
DAC_OPACTRL_OPA2LPFDIS_NLPFDIS : 0 ) |
|
||||
( init->hcmDisable ? DAC_OPACTRL_OPA2HCMDIS : 0 ) |
|
||||
( DAC_OPACTRL_OPA2EN );
|
||||
}
|
||||
}
|
||||
|
||||
/** @} (end addtogroup OPAMP) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
||||
|
||||
#endif /* defined( OPAMP_PRESENT ) && ( OPAMP_COUNT == 1 ) */
|
|
@ -0,0 +1,654 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Pulse Counter (PCNT) peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#include "efm32_pcnt.h"
|
||||
#include "efm32_cmu.h"
|
||||
#include "efm32_assert.h"
|
||||
#include "efm32_bitband.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup PCNT
|
||||
* @brief Pulse Counter (PCNT) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
|
||||
/** Validation of PCNT register block pointer reference for assert statements. */
|
||||
#if (PCNT_COUNT == 1)
|
||||
#define PCNT_REF_VALID(ref) ((ref) == PCNT0)
|
||||
#elif (PCNT_COUNT == 2)
|
||||
#define PCNT_REF_VALID(ref) (((ref) == PCNT0) || ((ref) == PCNT1))
|
||||
#elif (PCNT_COUNT == 3)
|
||||
#define PCNT_REF_VALID(ref) (((ref) == PCNT0) || ((ref) == PCNT1) || \
|
||||
((ref) == PCNT2))
|
||||
#else
|
||||
#error Undefined number of pulse counters (PCNT).
|
||||
#endif
|
||||
|
||||
/** @endcond */
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
************************** LOCAL FUNCTIONS ********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Map PCNT structure into instance number.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block
|
||||
*
|
||||
* @return
|
||||
* Instance number.
|
||||
******************************************************************************/
|
||||
static __INLINE unsigned int PCNT_Map(PCNT_TypeDef *pcnt)
|
||||
{
|
||||
return(((uint32_t)pcnt - PCNT0_BASE) / 0x400);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Wait for ongoing sync of register(s) to low frequency domain to complete.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block
|
||||
*
|
||||
* @param[in] mask
|
||||
* Bitmask corresponding to SYNCBUSY register defined bits, indicating
|
||||
* registers that must complete any ongoing synchronization.
|
||||
******************************************************************************/
|
||||
static __INLINE void PCNT_Sync(PCNT_TypeDef *pcnt, uint32_t mask)
|
||||
{
|
||||
/* Avoid deadlock if modifying the same register twice when freeze mode is
|
||||
* activated. */
|
||||
if (pcnt->FREEZE & PCNT_FREEZE_REGFREEZE)
|
||||
{
|
||||
return;
|
||||
}
|
||||
|
||||
/* Wait for any pending previous write operation to have been completed in low
|
||||
* frequency domain. */
|
||||
while (pcnt->SYNCBUSY & mask)
|
||||
;
|
||||
}
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Reset PCNT counters and TOP register.
|
||||
*
|
||||
* @note
|
||||
* Notice that special SYNCBUSY handling is not applicable for the RSTEN
|
||||
* bit of the control register, so we don't need to wait for it when only
|
||||
* modifying RSTEN. (It would mean undefined wait time if clocked by external
|
||||
* clock.) The SYNCBUSY bit will however be set, leading to a synchronization
|
||||
* in the LF domain, with in reality no changes.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
******************************************************************************/
|
||||
void PCNT_CounterReset(PCNT_TypeDef *pcnt)
|
||||
{
|
||||
EFM_ASSERT(PCNT_REF_VALID(pcnt));
|
||||
|
||||
/* Enable reset of CNT and TOP register */
|
||||
BITBAND_Peripheral(&(pcnt->CTRL), _PCNT_CTRL_RSTEN_SHIFT, 1);
|
||||
|
||||
/* Disable reset of CNT and TOP register */
|
||||
BITBAND_Peripheral(&(pcnt->CTRL), _PCNT_CTRL_RSTEN_SHIFT, 0);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set counter and top values.
|
||||
*
|
||||
* @details
|
||||
* The pulse counter is disabled while changing these values, and reenabled
|
||||
* (if originally enabled) when values have been set.
|
||||
*
|
||||
* @note
|
||||
* This function will stall until synchronization to low frequency domain is
|
||||
* completed. For that reason, it should normally not be used when using
|
||||
* an external clock to clock the PCNT module, since stall time may be
|
||||
* undefined in that case. The counter should normally only be set when
|
||||
* operating in (or about to enable) #pcntModeOvsSingle mode.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] count
|
||||
* Value to set in counter register.
|
||||
*
|
||||
* @param[in] top
|
||||
* Value to set in top register.
|
||||
******************************************************************************/
|
||||
void PCNT_CounterTopSet(PCNT_TypeDef *pcnt, uint32_t count, uint32_t top)
|
||||
{
|
||||
uint32_t ctrl;
|
||||
|
||||
EFM_ASSERT(PCNT_REF_VALID(pcnt));
|
||||
|
||||
/* Keep current control setting, must be restored */
|
||||
ctrl = pcnt->CTRL;
|
||||
|
||||
/* If enabled, disable pulse counter before changing values */
|
||||
if ((ctrl & _PCNT_CTRL_MODE_MASK) != PCNT_CTRL_MODE_DISABLE)
|
||||
{
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_CTRL);
|
||||
pcnt->CTRL = (ctrl & ~_PCNT_CTRL_MODE_MASK) | PCNT_CTRL_MODE_DISABLE;
|
||||
}
|
||||
|
||||
/* Load into TOPB */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_TOPB);
|
||||
pcnt->TOPB = count;
|
||||
|
||||
/* Load TOPB value into TOP */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_TOPB | PCNT_SYNCBUSY_CMD);
|
||||
|
||||
/* This bit has no effect on rev. C and onwards parts - for compatibility */
|
||||
pcnt->CMD = PCNT_CMD_LTOPBIM;
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_CMD);
|
||||
|
||||
/* Load TOP into CNT */
|
||||
pcnt->CMD = PCNT_CMD_LCNTIM;
|
||||
|
||||
/* Restore TOP? ('count' setting has been loaded into pcnt->TOP, better
|
||||
* to use 'top' than pcnt->TOP in compare, since latter may in theory not
|
||||
* be visible yet.) */
|
||||
if (top != count)
|
||||
{
|
||||
/* Wait for command to sync LCNTIM before setting TOPB */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_CMD);
|
||||
|
||||
/* Load into TOPB, we don't need to check for TOPB sync complete here,
|
||||
* it has been ensured above. */
|
||||
pcnt->TOPB = top;
|
||||
|
||||
/* Load TOPB value into TOP */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_TOPB | PCNT_SYNCBUSY_CMD);
|
||||
pcnt->CMD = PCNT_CMD_LTOPBIM;
|
||||
}
|
||||
|
||||
/* Reenable if it was enabled */
|
||||
if ((ctrl & _PCNT_CTRL_MODE_MASK) != PCNT_CTRL_MODE_DISABLE)
|
||||
{
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_CTRL | PCNT_SYNCBUSY_CMD);
|
||||
pcnt->CTRL = ctrl;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set PCNT operational mode.
|
||||
*
|
||||
* @details
|
||||
* Notice that this function does not do any configuration. Setting operational
|
||||
* mode is normally only required after initialization is done, and if not
|
||||
* done as part of initialization. Or if requiring to disable/reenable pulse
|
||||
* counter.
|
||||
*
|
||||
* @note
|
||||
* This function may stall until synchronization to low frequency domain is
|
||||
* completed. For that reason, it should normally not be used when using
|
||||
* an external clock to clock the PCNT module, since stall time may be
|
||||
* undefined in that case.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] mode
|
||||
* Operational mode to use for PCNT.
|
||||
******************************************************************************/
|
||||
void PCNT_Enable(PCNT_TypeDef *pcnt, PCNT_Mode_TypeDef mode)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
EFM_ASSERT(PCNT_REF_VALID(pcnt));
|
||||
|
||||
/* Set as specified */
|
||||
tmp = pcnt->CTRL & ~_PCNT_CTRL_MODE_MASK;
|
||||
tmp |= (uint32_t)mode << _PCNT_CTRL_MODE_SHIFT;
|
||||
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_CTRL);
|
||||
pcnt->CTRL = tmp;
|
||||
}
|
||||
|
||||
#if (defined (_EFM32_TINY_FAMILY) || defined (_EFM32_GIANT_FAMILY))
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable/disable the selected PRS input of PCNT.
|
||||
*
|
||||
* @details
|
||||
* Notice that this function does not do any configuration.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] prsInput
|
||||
* PRS input (S0 or S1) of the selected PCNT module.
|
||||
*
|
||||
* @param[in] enable
|
||||
* Set to true to enable, false to disable the selected PRS input.
|
||||
******************************************************************************/
|
||||
void PCNT_PRSInputEnable(PCNT_TypeDef *pcnt,
|
||||
PCNT_PRSInput_TypeDef prsInput,
|
||||
bool enable)
|
||||
{
|
||||
EFM_ASSERT(PCNT_REF_VALID(pcnt));
|
||||
|
||||
/* Enable/disable the selected PRS input on the selected PCNT module. */
|
||||
switch (prsInput)
|
||||
{
|
||||
/* Enable/disable PRS input S0. */
|
||||
case pcntPRSInputS0:
|
||||
{
|
||||
BITBAND_Peripheral(&(pcnt->INPUT), _PCNT_INPUT_S0PRSEN_SHIFT, (uint32_t)enable);
|
||||
}
|
||||
break;
|
||||
|
||||
/* Enable/disable PRS input S1. */
|
||||
case pcntPRSInputS1:
|
||||
{
|
||||
BITBAND_Peripheral(&(pcnt->INPUT), _PCNT_INPUT_S1PRSEN_SHIFT, (uint32_t)enable);
|
||||
}
|
||||
break;
|
||||
|
||||
/* Invalid parameter, asserted. */
|
||||
default:
|
||||
{
|
||||
EFM_ASSERT(0);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* PCNT register synchronization freeze control.
|
||||
*
|
||||
* @details
|
||||
* Some PCNT registers require synchronization into the low frequency (LF)
|
||||
* domain. The freeze feature allows for several such registers to be
|
||||
* modified before passing them to the LF domain simultaneously (which
|
||||
* takes place when the freeze mode is disabled).
|
||||
*
|
||||
* @note
|
||||
* When enabling freeze mode, this function will wait for all current
|
||||
* ongoing PCNT synchronization to LF domain to complete (Normally
|
||||
* synchronization will not be in progress.) However for this reason, when
|
||||
* using freeze mode, modifications of registers requiring LF synchronization
|
||||
* should be done within one freeze enable/disable block to avoid unecessary
|
||||
* stalling.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] enable
|
||||
* @li true - enable freeze, modified registers are not propagated to the
|
||||
* LF domain
|
||||
* @li false - disables freeze, modified registers are propagated to LF
|
||||
* domain
|
||||
******************************************************************************/
|
||||
void PCNT_FreezeEnable(PCNT_TypeDef *pcnt, bool enable)
|
||||
{
|
||||
EFM_ASSERT(PCNT_REF_VALID(pcnt));
|
||||
|
||||
if (enable)
|
||||
{
|
||||
/* Wait for any ongoing LF synchronization to complete. This is just to
|
||||
* protect against the rare case when a user:
|
||||
* - modifies a register requiring LF sync
|
||||
* - then enables freeze before LF sync completed
|
||||
* - then modifies the same register again
|
||||
* since modifying a register while it is in sync progress should be
|
||||
* avoided. */
|
||||
while (pcnt->SYNCBUSY)
|
||||
;
|
||||
|
||||
pcnt->FREEZE = PCNT_FREEZE_REGFREEZE;
|
||||
}
|
||||
else
|
||||
{
|
||||
pcnt->FREEZE = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Init pulse counter.
|
||||
*
|
||||
* @details
|
||||
* This function will configure the pulse counter. The clock selection is
|
||||
* configured as follows, depending on operational mode:
|
||||
*
|
||||
* @li #pcntModeOvsSingle - Use LFACLK.
|
||||
* @li #pcntModeExtSingle - Use external PCNTn_S0 pin.
|
||||
* @li #pcntModeExtQuad - Use external PCNTn_S0 pin.
|
||||
*
|
||||
* Notice that the LFACLK must be enabled in all modes, since some basic setup
|
||||
* is done with this clock even if external pin clock usage mode is chosen.
|
||||
* The pulse counter clock for the selected instance must also be enabled
|
||||
* prior to init.
|
||||
*
|
||||
* Notice that pins used by the PCNT module must be properly configured
|
||||
* by the user explicitly through setting the ROUTE register, in order for
|
||||
* the PCNT to work as intended.
|
||||
*
|
||||
* Writing to CNT will not occur in external clock modes (EXTCLKQUAD and
|
||||
* EXTCLKSINGLE) because the external clock rate is unknown. The user should
|
||||
* handle it manually depending on the application
|
||||
*
|
||||
* TOPB is written for all modes but in external clock mode it will take
|
||||
* 3 external clock cycles to sync to TOP
|
||||
*
|
||||
*
|
||||
* @note
|
||||
* Initializing requires synchronization into the low frequency domain. This
|
||||
* may cause some delay.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to initialization structure used to initialize.
|
||||
******************************************************************************/
|
||||
void PCNT_Init(PCNT_TypeDef *pcnt, const PCNT_Init_TypeDef *init)
|
||||
{
|
||||
unsigned int inst;
|
||||
uint32_t tmp;
|
||||
|
||||
EFM_ASSERT(PCNT_REF_VALID(pcnt));
|
||||
|
||||
/* Map pointer to instance */
|
||||
inst = PCNT_Map(pcnt);
|
||||
|
||||
#if (defined (_EFM32_TINY_FAMILY) || defined (_EFM32_GIANT_FAMILY))
|
||||
/* Selecting the PRS channels for the PRS input sources of the PCNT. These are
|
||||
* written with a Read-Modify-Write sequence in order to keep the value of the
|
||||
* input enable bits which can be modified using PCNT_PRSInputEnable(). */
|
||||
tmp = pcnt->INPUT & ~(_PCNT_INPUT_S0PRSSEL_MASK | _PCNT_INPUT_S1PRSSEL_MASK);
|
||||
tmp |= ((uint32_t)init->s0PRS << _PCNT_INPUT_S0PRSSEL_SHIFT) |
|
||||
((uint32_t)init->s1PRS << _PCNT_INPUT_S1PRSSEL_SHIFT);
|
||||
pcnt->INPUT = tmp;
|
||||
#endif
|
||||
|
||||
/* Build CTRL setting, except for mode */
|
||||
tmp = 0;
|
||||
if (init->negEdge)
|
||||
{
|
||||
tmp |= PCNT_CTRL_EDGE_NEG;
|
||||
}
|
||||
|
||||
if (init->countDown)
|
||||
{
|
||||
tmp |= PCNT_CTRL_CNTDIR_DOWN;
|
||||
}
|
||||
|
||||
if (init->filter)
|
||||
{
|
||||
tmp |= PCNT_CTRL_FILT;
|
||||
}
|
||||
|
||||
#if (defined (_EFM32_TINY_FAMILY) || defined (_EFM32_GIANT_FAMILY))
|
||||
if (init->hyst)
|
||||
{
|
||||
tmp |= PCNT_CTRL_HYST;
|
||||
}
|
||||
|
||||
if (init->s1CntDir)
|
||||
{
|
||||
tmp |= PCNT_CTRL_S1CDIR;
|
||||
}
|
||||
|
||||
/* Configure counter events for regular and auxiliary counter. */
|
||||
tmp |= init->cntEvent << _PCNT_CTRL_CNTEV_SHIFT;
|
||||
tmp |= init->auxCntEvent << _PCNT_CTRL_AUXCNTEV_SHIFT;
|
||||
#endif
|
||||
|
||||
/* Reset pulse counter while changing clock source. The reset bit */
|
||||
/* is asynchronous, we don't have to check for SYNCBUSY. */
|
||||
BITBAND_Peripheral(&(pcnt->CTRL), _PCNT_CTRL_RSTEN_SHIFT, 1);
|
||||
|
||||
/* Select LFACLK to clock in control setting */
|
||||
CMU_PCNTClockExternalSet(inst, false);
|
||||
|
||||
/* Handling depends on whether using external clock or not. */
|
||||
switch (init->mode)
|
||||
{
|
||||
case pcntModeExtSingle:
|
||||
case pcntModeExtQuad:
|
||||
tmp |= init->mode << _PCNT_CTRL_MODE_SHIFT;
|
||||
|
||||
/* In most cases, the SYNCBUSY bit is set due to reset bit set, and waiting
|
||||
* for asynchronous reset bit is strictly not necessary.
|
||||
* But in theory, other operations on CTRL register may have been done
|
||||
* outside this function, so wait. */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_CTRL);
|
||||
|
||||
/* Enable PCNT Clock Domain Reset. The PCNT must be in reset before changing
|
||||
* the clock source to an external clock */
|
||||
pcnt->CTRL = PCNT_CTRL_RSTEN;
|
||||
|
||||
/* Wait until CTRL write synchronized into LF domain. */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_CTRL);
|
||||
|
||||
/* Change to external clock BEFORE disabling reset */
|
||||
CMU_PCNTClockExternalSet(inst, true);
|
||||
|
||||
/* Write to TOPB. If using external clock TOPB will sync to TOP at the same
|
||||
* time as the mode. This will insure that if the user chooses to count
|
||||
* down, the first "countable" pulse will make CNT go to TOP and not 0xFF
|
||||
* (default TOP value). */
|
||||
pcnt->TOPB = init->top;
|
||||
|
||||
/* This bit has no effect on rev. C and onwards parts - for compatibility */
|
||||
pcnt->CMD = PCNT_CMD_LTOPBIM;
|
||||
|
||||
/* Write the CTRL register with the configurations.
|
||||
* This should be written after TOPB in the eventuality of a pulse between
|
||||
* these two writes that would cause the CTRL register to be synced one
|
||||
* clock cycle earlier than the TOPB. */
|
||||
pcnt->CTRL = tmp;
|
||||
|
||||
/* There are no syncs for TOP, CMD or CTRL because the clock rate is unknown
|
||||
* and the program could stall
|
||||
* These will be synced within 3 clock cycles of the external clock /
|
||||
* For the same reason CNT cannot be written here. */
|
||||
break;
|
||||
|
||||
/* pcntModeDisable */
|
||||
/* pcntModeOvsSingle */
|
||||
default:
|
||||
/* No need to set disabled mode if already disabled. */
|
||||
if ((pcnt->CTRL & _PCNT_CTRL_MODE_MASK) != PCNT_CTRL_MODE_DISABLE)
|
||||
{
|
||||
/* Set control to disabled mode, leave reset on until ensured disabled.
|
||||
* We don't need to wait for CTRL SYNCBUSY completion here, it was
|
||||
* triggered by reset bit above, which is asynchronous. */
|
||||
pcnt->CTRL = tmp | PCNT_CTRL_MODE_DISABLE | PCNT_CTRL_RSTEN;
|
||||
|
||||
/* Wait until CTRL write synchronized into LF domain before proceeding
|
||||
* to disable reset. */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_CTRL);
|
||||
}
|
||||
|
||||
/* Disable reset bit, counter should now be in disabled mode. */
|
||||
BITBAND_Peripheral(&(pcnt->CTRL), _PCNT_CTRL_RSTEN_SHIFT, 0);
|
||||
|
||||
/* Set counter and top values as specified. */
|
||||
PCNT_CounterTopSet(pcnt, init->counter, init->top);
|
||||
|
||||
/* Enter oversampling mode if selected. */
|
||||
if (init->mode == pcntModeOvsSingle)
|
||||
{
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_CTRL);
|
||||
pcnt->CTRL = tmp | (init->mode << _PCNT_CTRL_MODE_SHIFT);
|
||||
}
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Reset PCNT to same state as after a HW reset.
|
||||
*
|
||||
* @details
|
||||
* Notice the LFACLK must be enabled, since some basic reset is done with
|
||||
* this clock. The pulse counter clock for the selected instance must also
|
||||
* be enabled prior to init.
|
||||
*
|
||||
* @note
|
||||
* The ROUTE register is NOT reset by this function, in order to allow for
|
||||
* centralized setup of this feature.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
******************************************************************************/
|
||||
void PCNT_Reset(PCNT_TypeDef *pcnt)
|
||||
{
|
||||
unsigned int inst;
|
||||
|
||||
EFM_ASSERT(PCNT_REF_VALID(pcnt));
|
||||
|
||||
/* Map pointer to instance and clock info */
|
||||
inst = PCNT_Map(pcnt);
|
||||
|
||||
pcnt->IEN = _PCNT_IEN_RESETVALUE;
|
||||
|
||||
/* Notice that special SYNCBUSY handling is not applicable for the RSTEN
|
||||
* bit of the control register, so we don't need to wait for it when only
|
||||
* modifying RSTEN. The SYNCBUSY bit will be set, leading to a
|
||||
* synchronization in the LF domain, with in reality no changes to LF domain.
|
||||
* Enable reset of CNT and TOP register. */
|
||||
BITBAND_Peripheral(&(pcnt->CTRL), _PCNT_CTRL_RSTEN_SHIFT, 1);
|
||||
|
||||
/* Select LFACLK as default */
|
||||
CMU_PCNTClockExternalSet(inst, false);
|
||||
|
||||
PCNT_TopBufferSet(pcnt, _PCNT_TOPB_RESETVALUE);
|
||||
|
||||
/* Reset CTRL leaving RSTEN set */
|
||||
pcnt->CTRL = _PCNT_CTRL_RESETVALUE | PCNT_CTRL_RSTEN;
|
||||
|
||||
/* Disable reset after CTRL reg has been synchronized */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_CTRL);
|
||||
BITBAND_Peripheral(&(pcnt->CTRL), _PCNT_CTRL_RSTEN_SHIFT, 0);
|
||||
|
||||
/* Clear pending interrupts */
|
||||
pcnt->IFC = _PCNT_IFC_MASK;
|
||||
|
||||
/* Do not reset route register, setting should be done independently */
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set top buffer value.
|
||||
*
|
||||
* @note
|
||||
* This function may stall until synchronization to low frequency domain is
|
||||
* completed. For that reason, it should normally not be used when using
|
||||
* an external clock to clock the PCNT module, since stall time may be
|
||||
* undefined in that case.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] val
|
||||
* Value to set in top buffer register.
|
||||
******************************************************************************/
|
||||
void PCNT_TopBufferSet(PCNT_TypeDef *pcnt, uint32_t val)
|
||||
{
|
||||
EFM_ASSERT(PCNT_REF_VALID(pcnt));
|
||||
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_TOPB);
|
||||
pcnt->TOPB = val;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set top value.
|
||||
*
|
||||
* @note
|
||||
* This function will stall until synchronization to low frequency domain is
|
||||
* completed. For that reason, it should normally not be used when using
|
||||
* an external clock to clock the PCNT module, since stall time may be
|
||||
* undefined in that case.
|
||||
*
|
||||
* @param[in] pcnt
|
||||
* Pointer to PCNT peripheral register block.
|
||||
*
|
||||
* @param[in] val
|
||||
* Value to set in top register.
|
||||
******************************************************************************/
|
||||
void PCNT_TopSet(PCNT_TypeDef *pcnt, uint32_t val)
|
||||
{
|
||||
EFM_ASSERT(PCNT_REF_VALID(pcnt));
|
||||
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
|
||||
/* Load into TOPB */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_TOPB);
|
||||
pcnt->TOPB = val;
|
||||
|
||||
/* Load TOPB value into TOP */
|
||||
PCNT_Sync(pcnt, PCNT_SYNCBUSY_TOPB | PCNT_SYNCBUSY_CMD);
|
||||
pcnt->CMD = PCNT_CMD_LTOPBIM;
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup PCNT) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,122 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Peripheral Reflex System (PRS) Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32_prs.h"
|
||||
#include "efm32_assert.h"
|
||||
#include "efm32_bitband.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup PRS
|
||||
* @brief Peripheral Reflex System (PRS) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set source and signal to be used for a channel.
|
||||
*
|
||||
* @param[in] ch
|
||||
* Channel to define signal and source for.
|
||||
*
|
||||
* @param[in] source
|
||||
* Source to select for channel. Use one of PRS_CH_CTRL_SOURCESEL_x defines.
|
||||
*
|
||||
* @param[in] signal
|
||||
* Signal (for selected @p source) to use. Use one of PRS_CH_CTRL_SIGSEL_x
|
||||
* defines.
|
||||
*
|
||||
* @param[in] edge
|
||||
* Edge (for selected source/signal) to generate pulse for.
|
||||
******************************************************************************/
|
||||
void PRS_SourceSignalSet(unsigned int ch,
|
||||
uint32_t source,
|
||||
uint32_t signal,
|
||||
PRS_Edge_TypeDef edge)
|
||||
{
|
||||
EFM_ASSERT(ch < 8);
|
||||
|
||||
PRS->CH[ch].CTRL = (source & _PRS_CH_CTRL_SOURCESEL_MASK) |
|
||||
(signal & _PRS_CH_CTRL_SIGSEL_MASK) |
|
||||
(uint32_t)edge;
|
||||
}
|
||||
|
||||
#if ((defined _EFM32_TINY_FAMILY) || (defined _EFM32_GIANT_FAMILY))
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set source and asynchronous signal to be used for a channel.
|
||||
*
|
||||
* @details
|
||||
* Asynchronous reflexes are not clocked on HFPERCLK, and can be used even in
|
||||
* EM2/EM3.
|
||||
* There is a limitation to reflexes operating in asynchronous mode: they can
|
||||
* only be used by a subset of the reflex consumers. Please refer to PRS
|
||||
* chapter in the reference manual for the complete list of supported
|
||||
* asynchronous signals and consumers.
|
||||
*
|
||||
* @note
|
||||
* This function is only supported on the following device families:
|
||||
* @li Tiny Gecko (EFM32TGxxxFxx)
|
||||
* @li Giant Gecko (EFM32GGxxxFxxx)
|
||||
* In asynchronous mode, the edge detector only works in EM0, hence it shall
|
||||
* not be used. The EDSEL parameter in PRS_CHx_CTRL register is set to 0 (OFF)
|
||||
* by default.
|
||||
*
|
||||
* @param[in] ch
|
||||
* Channel to define source and asynchronous signal for.
|
||||
*
|
||||
* @param[in] source
|
||||
* Source to select for channel. Use one of PRS_CH_CTRL_SOURCESEL_x defines.
|
||||
*
|
||||
* @param[in] signal
|
||||
* Asynchronous signal (for selected @p source) to use. Use one of the
|
||||
* PRS_CH_CTRL_SIGSEL_x defines that support asynchronous operation.
|
||||
******************************************************************************/
|
||||
void PRS_SourceAsyncSignalSet(unsigned int ch,
|
||||
uint32_t source,
|
||||
uint32_t signal)
|
||||
{
|
||||
EFM_ASSERT(ch < 8);
|
||||
|
||||
PRS->CH[ch].CTRL = PRS_CH_CTRL_ASYNC |
|
||||
(source & _PRS_CH_CTRL_SOURCESEL_MASK) |
|
||||
(signal & _PRS_CH_CTRL_SIGSEL_MASK) |
|
||||
PRS_CH_CTRL_EDSEL_OFF;
|
||||
}
|
||||
#endif
|
||||
|
||||
/** @} (end addtogroup PRS) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,175 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Reset Management Unit (RMU) peripheral module peripheral API
|
||||
* for EFM32.
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32_rmu.h"
|
||||
#include "efm32_emu.h"
|
||||
#include "efm32_bitband.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup RMU
|
||||
* @brief Reset Management Unit (RMU) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Disable/enable the lockup signal from the Cortex M-3.
|
||||
*
|
||||
* @param[in] disable
|
||||
* @li false - Allow lockup signal to reset.
|
||||
* @li true - Do not allow lockup signal to reset.
|
||||
******************************************************************************/
|
||||
void RMU_LockupResetDisable(bool disable)
|
||||
{
|
||||
BITBAND_Peripheral(&(RMU->CTRL), _RMU_CTRL_LOCKUPRDIS_SHIFT, (unsigned int)disable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Clear the reset cause register.
|
||||
******************************************************************************/
|
||||
void RMU_ResetCauseClear(void)
|
||||
{
|
||||
uint32_t locked;
|
||||
|
||||
RMU->CMD = RMU_CMD_RCCLR;
|
||||
|
||||
/* Clear some reset causes not cleared with RMU CMD register */
|
||||
/* (If EMU registers locked, they must be unlocked first) */
|
||||
locked = EMU->LOCK & EMU_LOCK_LOCKKEY_LOCKED;
|
||||
if (locked)
|
||||
{
|
||||
EMU_Unlock();
|
||||
}
|
||||
|
||||
BITBAND_Peripheral(&(EMU->AUXCTRL), 0, 1);
|
||||
BITBAND_Peripheral(&(EMU->AUXCTRL), 0, 0);
|
||||
|
||||
if (locked)
|
||||
{
|
||||
EMU_Lock();
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get the cause of the last reset.
|
||||
*
|
||||
* @details
|
||||
* In order to be useful, the reset cause must be cleared by SW before a new
|
||||
* reset occurs, otherwise reset causes may accumulate. See
|
||||
* RMU_ResetCauseClear().
|
||||
*
|
||||
* @return
|
||||
* The reset cause, a bit mask of (typically, but not always, only one) of:
|
||||
* @li RMU_RSTCAUSE_PORST - Power on reset
|
||||
* @li RMU_RSTCAUSE_BODUNREGRST - Brown out detector, unregulated power
|
||||
* @li RMU_RSTCAUSE_BODREGRST - Brown out detector, regulated power
|
||||
* @li RMU_RSTCAUSE_EXTRST - External reset
|
||||
* @li RMU_RSTCAUSE_WDOGRST - Watchdog reset
|
||||
* @li RMU_RSTCAUSE_LOCKUPRST - Cortex-M3 lockup reset
|
||||
* @li RMU_RSTCAUSE_SYSREQRST - Cortex-M3 system request reset
|
||||
******************************************************************************/
|
||||
uint32_t RMU_ResetCauseGet(void)
|
||||
{
|
||||
uint32_t ret = RMU->RSTCAUSE;
|
||||
|
||||
/* Inspect and decode bits. The decoding must be done in correct order, */
|
||||
/* since some reset causes may trigger other reset causes due to internal */
|
||||
/* design. We are only interested in the main cause. */
|
||||
#if defined(_EFM32_TINY_FAMILY) || defined(_EFM32_GIANT_FAMILY)
|
||||
/* Clear "stray" bits if EM4 bit is set, they will always be active */
|
||||
if (ret & RMU_RSTCAUSE_EM4RST)
|
||||
{
|
||||
ret &= ~(RMU_RSTCAUSE_BODREGRST|
|
||||
RMU_RSTCAUSE_BODUNREGRST|
|
||||
RMU_RSTCAUSE_LOCKUPRST|
|
||||
RMU_RSTCAUSE_SYSREQRST);
|
||||
}
|
||||
if (ret == RMU_RSTCAUSE_BODAVDD0)
|
||||
{
|
||||
ret = RMU_RSTCAUSE_BODAVDD0;
|
||||
}
|
||||
else if (ret == RMU_RSTCAUSE_BODAVDD1)
|
||||
{
|
||||
ret = RMU_RSTCAUSE_BODAVDD1;
|
||||
}
|
||||
else if (ret == (RMU_RSTCAUSE_EM4WURST|RMU_RSTCAUSE_EM4RST))
|
||||
{
|
||||
ret &= (RMU_RSTCAUSE_EM4WURST|RMU_RSTCAUSE_EM4RST);
|
||||
}
|
||||
else if (ret & (RMU_RSTCAUSE_EM4RST|RMU_RSTCAUSE_EXTRST))
|
||||
{
|
||||
ret &= (RMU_RSTCAUSE_EM4RST|RMU_RSTCAUSE_EXTRST);
|
||||
}
|
||||
else
|
||||
#endif
|
||||
if (ret & RMU_RSTCAUSE_PORST)
|
||||
{
|
||||
ret = RMU_RSTCAUSE_PORST;
|
||||
}
|
||||
else if (ret & RMU_RSTCAUSE_BODUNREGRST)
|
||||
{
|
||||
ret = RMU_RSTCAUSE_BODUNREGRST;
|
||||
}
|
||||
else if ((ret & 0x1f) == RMU_RSTCAUSE_BODREGRST)
|
||||
{
|
||||
ret = RMU_RSTCAUSE_BODREGRST;
|
||||
}
|
||||
/* Both external and watchdog reset may occur at the same time */
|
||||
else if (ret & (RMU_RSTCAUSE_EXTRST | RMU_RSTCAUSE_WDOGRST))
|
||||
{
|
||||
ret &= RMU_RSTCAUSE_EXTRST | RMU_RSTCAUSE_WDOGRST;
|
||||
}
|
||||
/* Both lockup and system reset may occur at the same time */
|
||||
else if (ret & (RMU_RSTCAUSE_LOCKUPRST | RMU_RSTCAUSE_SYSREQRST))
|
||||
{
|
||||
ret &= RMU_RSTCAUSE_LOCKUPRST | RMU_RSTCAUSE_SYSREQRST;
|
||||
}
|
||||
else
|
||||
{
|
||||
ret = 0;
|
||||
}
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup RMU) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,355 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Real Time Counter (RTC) Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32_rtc.h"
|
||||
#include "efm32_assert.h"
|
||||
#include "efm32_bitband.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup RTC
|
||||
* @brief Real Time Counter (RTC) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
/** Validation of valid comparator register for assert statements. */
|
||||
#define RTC_COMP_REG_VALID(reg) (((reg) <= 1))
|
||||
|
||||
/** @endcond */
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
************************** LOCAL FUNCTIONS ********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Wait for ongoing sync of register(s) to low frequency domain to complete.
|
||||
*
|
||||
* @note
|
||||
* This only applies to the Gecko Family, see the reference manual
|
||||
* chapter about Access to Low Energy Peripherals (Asynchronos Registers)
|
||||
* for details. For Tiny Gecko and Giant Gecko, the RTC supports immediate
|
||||
* updates of registers, and will automatically hold the bus until the
|
||||
* register has been updated.
|
||||
*
|
||||
* @param[in] mask
|
||||
* Bitmask corresponding to SYNCBUSY register defined bits, indicating
|
||||
* registers that must complete any ongoing synchronization.
|
||||
******************************************************************************/
|
||||
static __INLINE void RTC_Sync(uint32_t mask)
|
||||
{
|
||||
/* Avoid deadlock if modifying the same register twice when freeze mode is */
|
||||
/* activated. */
|
||||
if (RTC->FREEZE & RTC_FREEZE_REGFREEZE)
|
||||
return;
|
||||
|
||||
/* Wait for any pending previous write operation to have been completed */
|
||||
/* in low frequency domain. This is only required for the Gecko Family */
|
||||
while (RTC->SYNCBUSY & mask)
|
||||
;
|
||||
}
|
||||
#endif
|
||||
|
||||
/** @endcond */
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get RTC compare register value.
|
||||
*
|
||||
* @param[in] comp
|
||||
* Compare register to get, either 0 or 1
|
||||
*
|
||||
* @return
|
||||
* Compare register value, 0 if invalid register selected.
|
||||
******************************************************************************/
|
||||
uint32_t RTC_CompareGet(unsigned int comp)
|
||||
{
|
||||
uint32_t ret;
|
||||
|
||||
EFM_ASSERT(RTC_COMP_REG_VALID(comp));
|
||||
|
||||
/* Initialize selected compare value */
|
||||
switch (comp)
|
||||
{
|
||||
case 0:
|
||||
ret = RTC->COMP0;
|
||||
break;
|
||||
|
||||
case 1:
|
||||
ret = RTC->COMP1;
|
||||
break;
|
||||
|
||||
default:
|
||||
/* Unknown compare register selected */
|
||||
ret = 0;
|
||||
break;
|
||||
}
|
||||
|
||||
return ret;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Set RTC compare register value.
|
||||
*
|
||||
* @note
|
||||
* The setting of a compare register requires synchronization into the
|
||||
* low frequency domain. If the same register is modified before a previous
|
||||
* update has completed, this function will stall until the previous
|
||||
* synchronization has completed. This only applies to the Gecko Family, see
|
||||
* comment in the RTC_Sync() internal function call.
|
||||
*
|
||||
* @param[in] comp
|
||||
* Compare register to set, either 0 or 1
|
||||
*
|
||||
* @param[in] value
|
||||
* Initialization value (<= 0x00ffffff)
|
||||
******************************************************************************/
|
||||
void RTC_CompareSet(unsigned int comp, uint32_t value)
|
||||
{
|
||||
volatile uint32_t *compReg;
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
uint32_t syncbusy;
|
||||
#endif
|
||||
|
||||
EFM_ASSERT(RTC_COMP_REG_VALID(comp) &&
|
||||
((value & ~(_RTC_COMP0_COMP0_MASK >> _RTC_COMP0_COMP0_SHIFT)) == 0));
|
||||
|
||||
/* Initialize selected compare value */
|
||||
switch (comp)
|
||||
{
|
||||
case 0:
|
||||
compReg = &(RTC->COMP0);
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
syncbusy = RTC_SYNCBUSY_COMP0;
|
||||
#endif
|
||||
break;
|
||||
|
||||
case 1:
|
||||
compReg = &(RTC->COMP1);
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
syncbusy = RTC_SYNCBUSY_COMP1;
|
||||
#endif
|
||||
break;
|
||||
|
||||
default:
|
||||
/* Unknown compare register selected, abort */
|
||||
return;
|
||||
}
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
RTC_Sync(syncbusy);
|
||||
#endif
|
||||
|
||||
*compReg = value;
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable/disable RTC.
|
||||
*
|
||||
* @note
|
||||
* The enabling/disabling of the RTC modifies the RTC CTRL register which
|
||||
* requires synchronization into the low frequency domain. If this register is
|
||||
* modified before a previous update to the same register has completed, this
|
||||
* function will stall until the previous synchronization has completed. This
|
||||
* only applies to the Gecko Family, see comment in the RTC_Sync() internal
|
||||
* function call.
|
||||
*
|
||||
* @param[in] enable
|
||||
* true to enable counting, false to disable.
|
||||
******************************************************************************/
|
||||
void RTC_Enable(bool enable)
|
||||
{
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
RTC_Sync(RTC_SYNCBUSY_CTRL);
|
||||
#endif
|
||||
|
||||
BITBAND_Peripheral(&(RTC->CTRL), _RTC_CTRL_EN_SHIFT, (unsigned int) enable);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* RTC register synchronization freeze control.
|
||||
*
|
||||
* @details
|
||||
* Some RTC registers require synchronization into the low frequency (LF)
|
||||
* domain. The freeze feature allows for several such registers to be
|
||||
* modified before passing them to the LF domain simultaneously (which
|
||||
* takes place when the freeze mode is disabled).
|
||||
*
|
||||
* @note
|
||||
* When enabling freeze mode, this function will wait for all current
|
||||
* ongoing RTC synchronization to LF domain to complete (Normally
|
||||
* synchronization will not be in progress.) However for this reason, when
|
||||
* using freeze mode, modifications of registers requiring LF synchronization
|
||||
* should be done within one freeze enable/disable block to avoid unecessary
|
||||
* stalling. This only applies to the Gecko Family, see the reference manual
|
||||
* chapter about Access to Low Energy Peripherals (Asynchronos Registers)
|
||||
* for details.
|
||||
*
|
||||
* @param[in] enable
|
||||
* @li true - enable freeze, modified registers are not propagated to the
|
||||
* LF domain
|
||||
* @li false - disables freeze, modified registers are propagated to LF
|
||||
* domain
|
||||
******************************************************************************/
|
||||
void RTC_FreezeEnable(bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/* Wait for any ongoing LF synchronization to complete. This is just to */
|
||||
/* protect against the rare case when a user */
|
||||
/* - modifies a register requiring LF sync */
|
||||
/* - then enables freeze before LF sync completed */
|
||||
/* - then modifies the same register again */
|
||||
/* since modifying a register while it is in sync progress should be */
|
||||
/* avoided. */
|
||||
while (RTC->SYNCBUSY)
|
||||
;
|
||||
#endif
|
||||
RTC->FREEZE = RTC_FREEZE_REGFREEZE;
|
||||
}
|
||||
else
|
||||
{
|
||||
RTC->FREEZE = 0;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize RTC.
|
||||
*
|
||||
* @details
|
||||
* Note that the compare values must be set separately with RTC_CompareSet().
|
||||
* That should probably be done prior to the use of this function if
|
||||
* configuring the RTC to start when initialization is completed.
|
||||
*
|
||||
* @note
|
||||
* The initialization of the RTC modifies the RTC CTRL register which requires
|
||||
* synchronization into the low frequency domain. If this register is
|
||||
* modified before a previous update to the same register has completed, this
|
||||
* function will stall until the previous synchronization has completed. This
|
||||
* only applies to the Gecko Family, see comment in the RTC_Sync() internal
|
||||
* function call.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to RTC initialization structure.
|
||||
******************************************************************************/
|
||||
void RTC_Init(const RTC_Init_TypeDef *init)
|
||||
{
|
||||
uint32_t tmp;
|
||||
|
||||
if (init->enable)
|
||||
{
|
||||
tmp = RTC_CTRL_EN;
|
||||
}
|
||||
else
|
||||
{
|
||||
tmp = 0;
|
||||
}
|
||||
|
||||
/* Configure DEBUGRUN flag, sets whether or not counter should be
|
||||
* updated when debugger is active */
|
||||
if (init->debugRun)
|
||||
{
|
||||
tmp |= RTC_CTRL_DEBUGRUN;
|
||||
}
|
||||
|
||||
/* Configure COMP0TOP, this will use the COMP0 compare value as an
|
||||
* overflow value, instead of default 24-bit 0x00ffffff */
|
||||
if (init->comp0Top)
|
||||
{
|
||||
tmp |= RTC_CTRL_COMP0TOP;
|
||||
}
|
||||
|
||||
#if defined(_EFM32_GECKO_FAMILY)
|
||||
/* LF register about to be modified require sync. busy check */
|
||||
RTC_Sync(RTC_SYNCBUSY_CTRL);
|
||||
#endif
|
||||
|
||||
RTC->CTRL = tmp;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Restore RTC to reset state
|
||||
******************************************************************************/
|
||||
void RTC_Reset(void)
|
||||
{
|
||||
/* Restore all essential RTC register to default config */
|
||||
RTC->FREEZE = _RTC_FREEZE_RESETVALUE;
|
||||
RTC->CTRL = _RTC_CTRL_RESETVALUE;
|
||||
RTC->COMP0 = _RTC_COMP0_RESETVALUE;
|
||||
RTC->COMP1 = _RTC_COMP1_RESETVALUE;
|
||||
RTC->IEN = _RTC_IEN_RESETVALUE;
|
||||
RTC->IFC = _RTC_IFC_RESETVALUE;
|
||||
}
|
||||
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Restart RTC counter from zero
|
||||
******************************************************************************/
|
||||
void RTC_CounterReset(void)
|
||||
{
|
||||
/* A disable/enable sequnce will start the counter at zero */
|
||||
RTC_Enable(false);
|
||||
RTC_Enable(true);
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup RTC) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,106 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief System Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
|
||||
#include "efm32.h"
|
||||
#include "efm32_system.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup SYSTEM
|
||||
* @brief System Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get chip major/minor revision.
|
||||
*
|
||||
* @param[out] rev
|
||||
* Location to place chip revision info.
|
||||
******************************************************************************/
|
||||
void SYSTEM_ChipRevisionGet(SYSTEM_ChipRevision_TypeDef *rev)
|
||||
{
|
||||
uint8_t tmp;
|
||||
|
||||
EFM_ASSERT(rev);
|
||||
|
||||
rev->major = (ROMTABLE->PID0 & _ROMTABLE_PID0_REVMAJOR_MASK) >> _ROMTABLE_PID0_REVMAJOR_SHIFT;
|
||||
|
||||
tmp = (ROMTABLE->PID2 & _ROMTABLE_PID2_REVMINORMSB_MASK);
|
||||
tmp |= ((ROMTABLE->PID3 & _ROMTABLE_PID3_REVMINORLSB_MASK) >> _ROMTABLE_PID3_REVMINORLSB_SHIFT);
|
||||
rev->minor = tmp;
|
||||
}
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Get factory calibration value for a given peripheral register.
|
||||
*
|
||||
* @param[in] regAddress
|
||||
* Address of register to get a calibration value for.
|
||||
*
|
||||
* @return
|
||||
* Calibration value for the requested register.
|
||||
******************************************************************************/
|
||||
uint32_t SYSTEM_GetCalibrationValue(volatile uint32_t *regAddress)
|
||||
{
|
||||
int regCount;
|
||||
CALIBRATE_TypeDef *p;
|
||||
|
||||
regCount = 1;
|
||||
p = CALIBRATE;
|
||||
|
||||
for (;; )
|
||||
{
|
||||
if ((regCount > CALIBRATE_MAX_REGISTERS) ||
|
||||
(p->VALUE == 0xFFFFFFFF))
|
||||
{
|
||||
EFM_ASSERT(false);
|
||||
return 0; /* End of device calibration table reached. */
|
||||
}
|
||||
|
||||
if (p->ADDRESS == (uint32_t)regAddress)
|
||||
{
|
||||
return p->VALUE; /* Calibration value found ! */
|
||||
}
|
||||
|
||||
p++;
|
||||
regCount++;
|
||||
}
|
||||
}
|
||||
|
||||
/** @} (end addtogroup SYSTEM) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
|
@ -0,0 +1,295 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Timer/counter (TIMER) Peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#include "efm32_timer.h"
|
||||
#include "efm32_cmu.h"
|
||||
#include "efm32_assert.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup TIMER
|
||||
* @brief Timer/Counter (TIMER) Peripheral API for EFM32
|
||||
* @details
|
||||
* The timer module consists of three main parts:
|
||||
* @li General timer config and enable control.
|
||||
* @li Compare/capture control.
|
||||
* @li Dead time insertion control (may not be available for all timers).
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/*******************************************************************************
|
||||
******************************* DEFINES ***********************************
|
||||
******************************************************************************/
|
||||
|
||||
/** @cond DO_NOT_INCLUDE_WITH_DOXYGEN */
|
||||
|
||||
|
||||
/** Validation of TIMER register block pointer reference for assert statements. */
|
||||
#if (TIMER_COUNT == 1)
|
||||
#define TIMER_REF_VALID(ref) ((ref) == TIMER0)
|
||||
#elif (TIMER_COUNT == 2)
|
||||
#define TIMER_REF_VALID(ref) (((ref) == TIMER0) || ((ref) == TIMER1))
|
||||
#elif (TIMER_COUNT == 3)
|
||||
#define TIMER_REF_VALID(ref) (((ref) == TIMER0) || \
|
||||
((ref) == TIMER1) || \
|
||||
((ref) == TIMER2))
|
||||
#elif (TIMER_COUNT == 4)
|
||||
#define TIMER_REF_VALID(ref) (((ref) == TIMER0) || \
|
||||
((ref) == TIMER1) || \
|
||||
((ref) == TIMER2) || \
|
||||
((ref) == TIMER3))
|
||||
#else
|
||||
#error Undefined number of timers.
|
||||
#endif
|
||||
|
||||
/** Validation of TIMER compare/capture channel number */
|
||||
#define TIMER_CH_VALID(ch) ((ch) < 3)
|
||||
|
||||
/** @endcond */
|
||||
|
||||
|
||||
/*******************************************************************************
|
||||
************************** GLOBAL FUNCTIONS *******************************
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Start/stop TIMER.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] enable
|
||||
* true to enable counting, false to disable.
|
||||
******************************************************************************/
|
||||
void TIMER_Enable(TIMER_TypeDef *timer, bool enable)
|
||||
{
|
||||
EFM_ASSERT(TIMER_REF_VALID(timer));
|
||||
|
||||
if (enable)
|
||||
{
|
||||
timer->CMD = TIMER_CMD_START;
|
||||
}
|
||||
else
|
||||
{
|
||||
timer->CMD = TIMER_CMD_STOP;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize TIMER.
|
||||
*
|
||||
* @details
|
||||
* Notice that counter top must be configured separately with for instance
|
||||
* TIMER_TopSet(). In addition, compare/capture and dead-time insertion
|
||||
* init must be initialized separately if used. That should probably
|
||||
* be done prior to the use of this function if configuring the TIMER to
|
||||
* start when initialization is completed.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to TIMER initialization structure.
|
||||
******************************************************************************/
|
||||
void TIMER_Init(TIMER_TypeDef *timer, const TIMER_Init_TypeDef *init)
|
||||
{
|
||||
EFM_ASSERT(TIMER_REF_VALID(timer));
|
||||
|
||||
/* Stop timer if specified to be disabled (dosn't hurt if already stopped) */
|
||||
if (!(init->enable))
|
||||
{
|
||||
timer->CMD = TIMER_CMD_STOP;
|
||||
}
|
||||
|
||||
/* Reset counter */
|
||||
timer->CNT = _TIMER_CNT_RESETVALUE;
|
||||
|
||||
timer->CTRL =
|
||||
((uint32_t)(init->prescale) << _TIMER_CTRL_PRESC_SHIFT) |
|
||||
((uint32_t)(init->clkSel) << _TIMER_CTRL_CLKSEL_SHIFT) |
|
||||
((uint32_t)(init->fallAction) << _TIMER_CTRL_FALLA_SHIFT) |
|
||||
((uint32_t)(init->riseAction) << _TIMER_CTRL_RISEA_SHIFT) |
|
||||
((uint32_t)(init->mode) << _TIMER_CTRL_MODE_SHIFT) |
|
||||
(init->debugRun ? TIMER_CTRL_DEBUGRUN : 0) |
|
||||
(init->dmaClrAct ? TIMER_CTRL_DMACLRACT : 0) |
|
||||
(init->quadModeX4 ? TIMER_CTRL_QDM_X4 : 0) |
|
||||
(init->oneShot ? TIMER_CTRL_OSMEN : 0) |
|
||||
|
||||
#if defined(_EFM32_GIANT_FAMILY) || defined(_EFM32_TINY_FAMILY)
|
||||
(init->count2x ? TIMER_CTRL_X2CNT : 0) |
|
||||
(init->ati ? TIMER_CTRL_ATI : 0) |
|
||||
#endif
|
||||
(init->sync ? TIMER_CTRL_SYNC : 0);
|
||||
|
||||
/* Start timer if specified to be enabled (dosn't hurt if already started) */
|
||||
if (init->enable)
|
||||
{
|
||||
timer->CMD = TIMER_CMD_START;
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Initialize TIMER compare/capture channel.
|
||||
*
|
||||
* @details
|
||||
* Notice that if operating channel in compare mode, the CCV and CCVB register
|
||||
* must be set separately as required.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
*
|
||||
* @param[in] ch
|
||||
* Compare/capture channel to init for.
|
||||
*
|
||||
* @param[in] init
|
||||
* Pointer to TIMER initialization structure.
|
||||
******************************************************************************/
|
||||
void TIMER_InitCC(TIMER_TypeDef *timer,
|
||||
unsigned int ch,
|
||||
const TIMER_InitCC_TypeDef *init)
|
||||
{
|
||||
EFM_ASSERT(TIMER_REF_VALID(timer));
|
||||
EFM_ASSERT(TIMER_CH_VALID(ch));
|
||||
|
||||
timer->CC[ch].CTRL =
|
||||
((uint32_t)(init->eventCtrl) << _TIMER_CC_CTRL_ICEVCTRL_SHIFT) |
|
||||
((uint32_t)(init->edge) << _TIMER_CC_CTRL_ICEDGE_SHIFT) |
|
||||
((uint32_t)(init->prsSel) << _TIMER_CC_CTRL_PRSSEL_SHIFT) |
|
||||
((uint32_t)(init->cufoa) << _TIMER_CC_CTRL_CUFOA_SHIFT) |
|
||||
((uint32_t)(init->cofoa) << _TIMER_CC_CTRL_COFOA_SHIFT) |
|
||||
((uint32_t)(init->cmoa) << _TIMER_CC_CTRL_CMOA_SHIFT) |
|
||||
((uint32_t)(init->mode) << _TIMER_CC_CTRL_MODE_SHIFT) |
|
||||
(init->filter ? TIMER_CC_CTRL_FILT_ENABLE : 0) |
|
||||
(init->prsInput ? TIMER_CC_CTRL_INSEL_PRS : 0) |
|
||||
(init->coist ? TIMER_CC_CTRL_COIST : 0) |
|
||||
(init->outInvert ? TIMER_CC_CTRL_OUTINV : 0);
|
||||
}
|
||||
|
||||
#ifdef TIMER_DTLOCK_LOCKKEY_LOCK
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Lock the TIMER in order to protect some of its registers against unintended
|
||||
* modification.
|
||||
*
|
||||
* @details
|
||||
* Please refer to the reference manual for TIMER registers that will be
|
||||
* locked.
|
||||
*
|
||||
* @note
|
||||
* If locking the TIMER registers, they must be unlocked prior to using any
|
||||
* TIMER API functions modifying TIMER registers protected by the lock.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
******************************************************************************/
|
||||
void TIMER_Lock(TIMER_TypeDef *timer)
|
||||
{
|
||||
EFM_ASSERT(TIMER_REF_VALID(timer));
|
||||
|
||||
timer->DTLOCK = TIMER_DTLOCK_LOCKKEY_LOCK;
|
||||
}
|
||||
#endif
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Reset TIMER to same state as after a HW reset.
|
||||
*
|
||||
* @note
|
||||
* The ROUTE register is NOT reset by this function, in order to allow for
|
||||
* centralized setup of this feature.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
******************************************************************************/
|
||||
void TIMER_Reset(TIMER_TypeDef *timer)
|
||||
{
|
||||
int i;
|
||||
|
||||
EFM_ASSERT(TIMER_REF_VALID(timer));
|
||||
|
||||
/* Make sure disabled first, before resetting other registers */
|
||||
timer->CMD = TIMER_CMD_STOP;
|
||||
|
||||
timer->CTRL = _TIMER_CTRL_RESETVALUE;
|
||||
timer->IEN = _TIMER_IEN_RESETVALUE;
|
||||
timer->IFC = _TIMER_IFC_MASK;
|
||||
timer->TOP = _TIMER_TOP_RESETVALUE;
|
||||
timer->TOPB = _TIMER_TOPB_RESETVALUE;
|
||||
timer->CNT = _TIMER_CNT_RESETVALUE;
|
||||
/* Do not reset route register, setting should be done independently */
|
||||
/* (Note: ROUTE register may be locked by DTLOCK register.) */
|
||||
|
||||
for (i = 0; TIMER_CH_VALID(i); i++)
|
||||
{
|
||||
timer->CC[i].CTRL = _TIMER_CC_CTRL_RESETVALUE;
|
||||
timer->CC[i].CCV = _TIMER_CC_CCV_RESETVALUE;
|
||||
timer->CC[i].CCVB = _TIMER_CC_CCVB_RESETVALUE;
|
||||
}
|
||||
|
||||
/* Reset dead time insertion module, no effect on timers without DTI */
|
||||
|
||||
#ifdef TIMER_DTLOCK_LOCKKEY_UNLOCK
|
||||
/* Unlock DTI registers first in case locked */
|
||||
timer->DTLOCK = TIMER_DTLOCK_LOCKKEY_UNLOCK;
|
||||
|
||||
timer->DTCTRL = _TIMER_DTCTRL_RESETVALUE;
|
||||
timer->DTTIME = _TIMER_DTTIME_RESETVALUE;
|
||||
timer->DTFC = _TIMER_DTFC_RESETVALUE;
|
||||
timer->DTOGEN = _TIMER_DTOGEN_RESETVALUE;
|
||||
timer->DTFAULTC = _TIMER_DTFAULTC_MASK;
|
||||
#endif
|
||||
}
|
||||
|
||||
|
||||
#ifdef TIMER_DTLOCK_LOCKKEY_UNLOCK
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Unlock the TIMER so that writing to locked registers again is possible.
|
||||
*
|
||||
* @param[in] timer
|
||||
* Pointer to TIMER peripheral register block.
|
||||
******************************************************************************/
|
||||
void TIMER_Unlock(TIMER_TypeDef *timer)
|
||||
{
|
||||
EFM_ASSERT(TIMER_REF_VALID(timer));
|
||||
|
||||
timer->DTLOCK = TIMER_DTLOCK_LOCKKEY_UNLOCK;
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
/** @} (end addtogroup TIMER) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
File diff suppressed because it is too large
Load Diff
|
@ -0,0 +1,176 @@
|
|||
/***************************************************************************//**
|
||||
* @file
|
||||
* @brief Voltage Comparator (VCMP) peripheral API for EFM32
|
||||
* @author Energy Micro AS
|
||||
* @version 2.3.2
|
||||
*******************************************************************************
|
||||
* @section License
|
||||
* <b>(C) Copyright 2010 Energy Micro AS, http://www.energymicro.com</b>
|
||||
*******************************************************************************
|
||||
*
|
||||
* This source code is the property of Energy Micro AS. The source and compiled
|
||||
* code may only be used on Energy Micro "EFM32" microcontrollers.
|
||||
*
|
||||
* This copyright notice may not be removed from the source code nor changed.
|
||||
*
|
||||
* DISCLAIMER OF WARRANTY/LIMITATION OF REMEDIES: Energy Micro AS has no
|
||||
* obligation to support this Software. Energy Micro AS is providing the
|
||||
* Software "AS IS", with no express or implied warranties of any kind,
|
||||
* including, but not limited to, any implied warranties of merchantability
|
||||
* or fitness for any particular purpose or warranties against infringement
|
||||
* of any proprietary rights of a third party.
|
||||
*
|
||||
* Energy Micro AS will not be liable for any consequential, incidental, or
|
||||
* special damages, or any other relief, or for any claim by any third party,
|
||||
* arising from your use of this Software.
|
||||
*
|
||||
******************************************************************************/
|
||||
#include "efm32_assert.h"
|
||||
#include "efm32_vcmp.h"
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup EFM32_Library
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @addtogroup VCMP
|
||||
* @brief Voltage Comparator (VCMP) Peripheral API for EFM32
|
||||
* @{
|
||||
******************************************************************************/
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure and enable Voltage Comparator
|
||||
*
|
||||
* @param[in] vcmpInit
|
||||
* VCMP Initialization structure
|
||||
******************************************************************************/
|
||||
void VCMP_Init(const VCMP_Init_TypeDef *vcmpInit)
|
||||
{
|
||||
/* Verify input */
|
||||
EFM_ASSERT((vcmpInit->inactive == 0) || (vcmpInit->inactive == 1));
|
||||
EFM_ASSERT((vcmpInit->biasProg >= 0) && (vcmpInit->biasProg < 16));
|
||||
|
||||
/* Configure Half Bias setting */
|
||||
if (vcmpInit->halfBias)
|
||||
{
|
||||
VCMP->CTRL |= VCMP_CTRL_HALFBIAS;
|
||||
}
|
||||
else
|
||||
{
|
||||
VCMP->CTRL &= ~(VCMP_CTRL_HALFBIAS);
|
||||
}
|
||||
|
||||
/* Configure bias prog */
|
||||
VCMP->CTRL &= ~(_VCMP_CTRL_BIASPROG_MASK);
|
||||
VCMP->CTRL |= (vcmpInit->biasProg << _VCMP_CTRL_BIASPROG_SHIFT);
|
||||
|
||||
/* Configure sense for falling edge */
|
||||
if (vcmpInit->irqFalling)
|
||||
{
|
||||
VCMP->CTRL |= VCMP_CTRL_IFALL;
|
||||
}
|
||||
else
|
||||
{
|
||||
VCMP->CTRL &= ~(VCMP_CTRL_IFALL);
|
||||
}
|
||||
|
||||
/* Configure sense for rising edge */
|
||||
if (vcmpInit->irqRising)
|
||||
{
|
||||
VCMP->CTRL |= VCMP_CTRL_IRISE;
|
||||
}
|
||||
else
|
||||
{
|
||||
VCMP->CTRL &= ~(VCMP_CTRL_IRISE);
|
||||
}
|
||||
|
||||
/* Configure warm-up time */
|
||||
VCMP->CTRL &= ~(_VCMP_CTRL_WARMTIME_MASK);
|
||||
VCMP->CTRL |= (vcmpInit->warmup << _VCMP_CTRL_WARMTIME_SHIFT);
|
||||
|
||||
/* Configure hysteresis */
|
||||
switch (vcmpInit->hyst)
|
||||
{
|
||||
case vcmpHyst20mV:
|
||||
VCMP->CTRL |= VCMP_CTRL_HYSTEN;
|
||||
break;
|
||||
case vcmpHystNone:
|
||||
VCMP->CTRL &= ~(VCMP_CTRL_HYSTEN);
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
|
||||
/* Configure inactive output value */
|
||||
VCMP->CTRL |= (vcmpInit->inactive << _VCMP_CTRL_INACTVAL_SHIFT);
|
||||
|
||||
/* Configure trigger level */
|
||||
VCMP_TriggerSet(vcmpInit->triggerLevel);
|
||||
|
||||
/* Enable or disable VCMP */
|
||||
if (vcmpInit->enable)
|
||||
{
|
||||
VCMP->CTRL |= VCMP_CTRL_EN;
|
||||
}
|
||||
else
|
||||
{
|
||||
VCMP->CTRL &= ~(VCMP_CTRL_EN);
|
||||
}
|
||||
|
||||
/* If Low Power Reference is enabled, wait until VCMP is ready */
|
||||
/* before enabling it, see reference manual for deatils */
|
||||
/* Configuring Low Power Ref without enable has no effect */
|
||||
if(vcmpInit->lowPowerRef && vcmpInit->enable)
|
||||
{
|
||||
/* Poll for VCMP ready */
|
||||
while(!VCMP_Ready());
|
||||
VCMP_LowPowerRefSet(vcmpInit->lowPowerRef);
|
||||
}
|
||||
|
||||
/* Clear edge interrupt */
|
||||
VCMP_IntClear(VCMP_IF_EDGE);
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Enable or disable Low Power Reference setting
|
||||
*
|
||||
* @param[in] enable
|
||||
* If true, enables low power reference, if false disable low power reference
|
||||
******************************************************************************/
|
||||
void VCMP_LowPowerRefSet(bool enable)
|
||||
{
|
||||
if (enable)
|
||||
{
|
||||
VCMP->INPUTSEL |= VCMP_INPUTSEL_LPREF;
|
||||
}
|
||||
else
|
||||
{
|
||||
VCMP->INPUTSEL &= ~(VCMP_INPUTSEL_LPREF);
|
||||
}
|
||||
}
|
||||
|
||||
|
||||
/***************************************************************************//**
|
||||
* @brief
|
||||
* Configure trigger level of voltage comparator
|
||||
*
|
||||
* @param[in] level
|
||||
* Trigger value, in range 0-63
|
||||
******************************************************************************/
|
||||
void VCMP_TriggerSet(int level)
|
||||
{
|
||||
/* Trigger range is 6 bits, value from 0-63 */
|
||||
EFM_ASSERT((level > 0) && (level < 64));
|
||||
|
||||
/* Set trigger level */
|
||||
VCMP->INPUTSEL = (VCMP->INPUTSEL & ~(_VCMP_INPUTSEL_TRIGLEVEL_MASK)) |
|
||||
(level << _VCMP_INPUTSEL_TRIGLEVEL_SHIFT);
|
||||
}
|
||||
|
||||
|
||||
/** @} (end addtogroup VCMP) */
|
||||
/** @} (end addtogroup EFM32_Library) */
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue