Mercurial > ecos
changeset 2580:07fc475e1c28
Add Cortex-M architecture HAL, STM32 variant and STM3210E platform HALs.
Add STM32 serial driver and on-chip flash driver.
Fix some compile problems with dlmalloc.
See the various ChangeLogs for details.
line wrap: on
line diff
--- a/packages/ChangeLog +++ b/packages/ChangeLog @@ -1,3 +1,7 @@ +2008-10-31 Nick Garnett <nickg@ecoscentric.com> + + * NEWS, ecos.db: Add Cortex-M HAL and drivers. + 2008-10-07 Bart Veer <bartv@ecoscentric.com> * NEWS, ecos.db: add generic framebuffer support and a synthetic
--- a/packages/NEWS +++ b/packages/NEWS @@ -1,3 +1,6 @@ +* Cortex-M Architecture HAL contributed by eCosCentric Ltd. +* STM32 Variant HAL, STM3210E platform HAL, serial device driver, + on-chip flash driver contributed by eCosCentric Ltd. * Synthetic target framebuffer device driver contributed by eCosCentric Ltd * Generic framebuffer support contributed by eCosCentric Ltd.
new file mode 100644 --- /dev/null +++ b/packages/devs/flash/cortexm/stm32/current/ChangeLog @@ -0,0 +1,39 @@ +2008-10-07 Nick Garnett <nickg@ecoscentric.com> + + * cdl/flash_stm32.cdl: + * include/stm32_flash.h: + * src/stm32_flash.c: + New package -- support for STM32 on-chip flash. + +//=========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//===========================================================================
new file mode 100644 --- /dev/null +++ b/packages/devs/flash/cortexm/stm32/current/cdl/flash_stm32.cdl @@ -0,0 +1,116 @@ +## ==================================================================== +## +## flash_stm32.cdl +## +## FLASH memory - Hardware support for STM32 on-chip flash +## +## ==================================================================== +######ECOSGPLCOPYRIGHTBEGIN#### +## ------------------------------------------- +## This file is part of eCos, the Embedded Configurable Operating System. +## Copyright (C) 2008 eCosCentric Limited. +## +## eCos 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 2 or (at your option) any later version. +## +## eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +## +## As a special exception, if other files instantiate templates or use macros +## or inline functions from this file, or you compile this file and link it +## with other works to produce a work based on this file, this file does not +## by itself cause the resulting work to be covered by the GNU General Public +## License. However the source code for this file must still be made available +## in accordance with section (3) of the GNU General Public License. +## +## This exception does not invalidate any other reasons why a work based on +## this file might be covered by the GNU General Public License. +## ------------------------------------------- +######ECOSGPLCOPYRIGHTEND#### +## ==================================================================== +######DESCRIPTIONBEGIN#### +## +## Author(s): nickg +## Date: 2008-09-22 +## +#####DESCRIPTIONEND#### +## +## ==================================================================== + +cdl_package CYGPKG_DEVS_FLASH_STM32 { + display "STM32 FLASH memory support" + parent CYGPKG_IO_FLASH + active_if CYGPKG_IO_FLASH + implements CYGHWR_IO_FLASH_DEVICE + + include_dir cyg/io + + compile stm32_flash.c + + description " + Flash memory support for on-chip flash on STM32 devices and compatibles. + This driver implements the V2 flash driver API." + + cdl_option CYGNUM_DEVS_FLASH_STM32_V2_PROGRAM_BURST_SIZE { + display "Number of words to write per burst" + flavor data + default_value 256 + legal_values 4 to 4096 + description " + On typical hardware programming the flash requires disabling + interrupts for an extended period of time. + Some or all of the flash hardware will be unusable while each word + is programmed, and disabling interrupts is the only reliable + way of ensuring that no interrupt handler or other thread will + try to access the flash in the middle of an operation. This + can have a major impact on the real-time responsiveness of + typical applications. To ameliorate this the driver will + perform writes in small bursts, briefly re-enabling the cache + and interrupts between each burst. The number of write operations + per burst is determined by this option: reducing the number of + writes per burst will improve real-time response, but will add + overhead so the actual flash program operation will take + longer; conversely more writes per burst will worsen response + times but reduce overhead." + } + + cdl_component CYGPKG_DEVS_FLASH_STM32_OPTIONS { + display "STM32 driver build options" + flavor none + description " + Package specific build options including control over + compiler flags used only in building the STM32 + flash driver, and details of which tests are built." + + cdl_option CYGPKG_DEVS_FLASH_STM32_CFLAGS_ADD { + display "Additional compiler flags" + flavor data + no_define + default_value { "" } + description " + This option modifies the set of compiler flags for + building the STM32 flash driver. These flags + are used in addition to the set of global flags." + } + + cdl_option CYGPKG_DEVS_FLASH_STM32_CFLAGS_REMOVE { + display "Suppressed compiler flags" + flavor data + no_define + default_value { "" } + description " + This option modifies the set of compiler flags for + building the STM32 flash driver. These flags + are removed from the set of global flags if present." + } + } +} + +# End of flash_stm32.cdl
new file mode 100644 --- /dev/null +++ b/packages/devs/flash/cortexm/stm32/current/include/stm32_flash.h @@ -0,0 +1,66 @@ +#ifndef CYGONCE_DEVS_FLASH_STM32_H +#define CYGONCE_DEVS_FLASH_STM32_H +//========================================================================== +// +// stm32_flash.h +// +// STM32 internal flash driver definitions +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-09-22 +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +// The driver-specific data, pointed at by the priv field in a +// a cyg_flash_dev structure. + +typedef struct cyg_stm32_dev +{ + cyg_flash_block_info_t block_info[1]; + +} cyg_stm32_flash_dev; + +//========================================================================*/ +// Exported function pointers. + +__externC const struct cyg_flash_dev_funs cyg_stm32_flash_funs; + + +//========================================================================*/ +#endif // CYGONCE_DEVS_FLASH_STM32_H +// End
new file mode 100644 --- /dev/null +++ b/packages/devs/flash/cortexm/stm32/current/src/stm32_flash.c @@ -0,0 +1,363 @@ +//========================================================================== +// +// stm32_flash.c +// +// STM32 internal flash driver +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-09-22 +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/devs_flash_stm32.h> + +#include <cyg/infra/cyg_type.h> +#include <cyg/infra/cyg_ass.h> +#include <cyg/infra/diag.h> + +#include <cyg/io/flash.h> +#include <cyg/io/flash_dev.h> + +#include <cyg/hal/hal_arch.h> +#include <cyg/hal/hal_intr.h> +#include <cyg/hal/hal_cache.h> +#include <cyg/hal/hal_io.h> +#include <cyg/hal/hal_if.h> + +#include <string.h> + +#include <cyg/io/stm32_flash.h> + +#include CYGHWR_MEMORY_LAYOUT_H + +// ---------------------------------------------------------------------------- + +typedef cyg_uint16 STM32_TYPE; + +# define STM32_INTSCACHE_STATE int _saved_ints_ +# define STM32_INTSCACHE_BEGIN() HAL_DISABLE_INTERRUPTS(_saved_ints_) +# define STM32_INTSCACHE_SUSPEND() HAL_RESTORE_INTERRUPTS(_saved_ints_) +# define STM32_INTSCACHE_RESUME() HAL_DISABLE_INTERRUPTS(_saved_ints_) +# define STM32_INTSCACHE_END() HAL_RESTORE_INTERRUPTS(_saved_ints_) + +#define STM32_UNCACHED_ADDRESS(__x) ((STM32_TYPE *)(__x)) + +// ---------------------------------------------------------------------------- +// Forward declarations for functions that need to be placed in RAM: + +static int stm32_flash_hw_erase(cyg_flashaddr_t addr) __attribute__((section (".2ram.stm32_flash_hw_erase"))); +static int stm32_flash_hw_program( volatile STM32_TYPE* addr, const cyg_uint16* buf, cyg_uint32 count) __attribute__((section (".2ram.stm32_flash_hw_program"))); + +// ---------------------------------------------------------------------------- +// Diagnostic routines. + +#if 0 +#define stf_diag( __fmt, ... ) diag_printf("STF: %20s[%3d]: " __fmt, __FUNCTION__, __LINE__, ## __VA_ARGS__ ); +#define stf_dump_buf( __addr, __size ) diag_dump_buf( __addr, __size ) +#else +#define stf_diag( __fmt, ... ) +#define stf_dump_buf( __addr, __size ) +#endif + +// ---------------------------------------------------------------------------- +// Initialize the flash. + + +static int +stm32_flash_init(struct cyg_flash_dev* dev) +{ + cyg_stm32_flash_dev *stm32_dev = (cyg_stm32_flash_dev *)dev->priv; + CYG_ADDRESS base = CYGHWR_HAL_STM32_FLASH; + cyg_uint32 sig, id; + cyg_uint32 flash_size, block_size = 0; + + // Set up the block info entries. + + dev->block_info = &stm32_dev->block_info[0]; + dev->num_block_infos = 1; + + // Get flash size from device signature and MCU ID + + HAL_READ_UINT32( CYGHWR_HAL_STM32_DEV_SIG, sig ); + HAL_READ_UINT32( CYGHWR_HAL_STM32_MCU_ID, id ); + + stf_diag("sig %08x id %08x\n", sig, id ); + + flash_size = 1024*CYGHWR_HAL_STM32_DEV_SIG_FSIZE(sig); + + if( CYGHWR_HAL_STM32_MCU_ID_DEV(id) == CYGHWR_HAL_STM32_MCU_ID_DEV_MEDIUM ) + { + block_size = 1024; + if( flash_size == 0xFFFF ) flash_size = 128*1024; + } + else if( CYGHWR_HAL_STM32_MCU_ID_DEV(id) == CYGHWR_HAL_STM32_MCU_ID_DEV_HIGH ) + { + block_size = 2048; + if( flash_size == 0xFFFF ) flash_size = 512*1024; + } + + stm32_dev->block_info[0].blocks = flash_size/block_size; + stm32_dev->block_info[0].block_size = block_size; + + // Set end address + dev->end = dev->start+flash_size-1; + + stf_diag("block_size %d size %08x end %08x\n", block_size, flash_size, dev->end ); + + // Unlock the flash control registers + + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FLASH_KEYR, CYGHWR_HAL_STM32_FLASH_KEYR_KEY1 ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FLASH_KEYR, CYGHWR_HAL_STM32_FLASH_KEYR_KEY2 ); + + return CYG_FLASH_ERR_OK; +} + +// ---------------------------------------------------------------------------- + +static size_t +stm32_flash_query(struct cyg_flash_dev* dev, void* data, size_t len) +{ + static char query[] = "STM32 Internal Flash"; + memcpy( data, query, sizeof(query)); + return sizeof(query); +} + +// ---------------------------------------------------------------------------- +// Get info about the current block, i.e. base and size. + +static void +stm32_flash_get_block_info(struct cyg_flash_dev* dev, const cyg_flashaddr_t addr, cyg_flashaddr_t* block_start, size_t* block_size) +{ + size_t offset = addr - dev->start; + + *block_start = dev->start + (offset & (dev->block_info[0].block_size-1)); + *block_size = dev->block_info[0].block_size; +} + +// ---------------------------------------------------------------------------- + +static int stm32_flash_decode_error( int sr ) +{ + int result = CYG_FLASH_ERR_OK; + + if( sr & CYGHWR_HAL_STM32_FLASH_SR_PGERR ) + result = CYG_FLASH_ERR_PROGRAM; + + if( sr & CYGHWR_HAL_STM32_FLASH_SR_WRPRTERR ) + result = CYG_FLASH_ERR_PROTECT; + + return result; +} + +// ---------------------------------------------------------------------------- +// Erase a single sector. There is no API support for chip-erase. The +// generic code operates one sector at a time, invoking the driver for +// each sector, so there is no opportunity inside the driver for +// erasing multiple sectors in a single call. The address argument +// points at the start of the sector. + +static int +stm32_flash_hw_erase(cyg_flashaddr_t addr) +{ + cyg_uint32 base = CYGHWR_HAL_STM32_FLASH; + cyg_uint32 sr, cr = 0; + cyg_uint32 timeout = 100000; + + cr |= CYGHWR_HAL_STM32_FLASH_CR_PER; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FLASH_CR, cr ); + + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FLASH_AR, addr ); + + cr |= CYGHWR_HAL_STM32_FLASH_CR_STRT; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FLASH_CR, cr ); + + do + { + HAL_READ_UINT32( base+CYGHWR_HAL_STM32_FLASH_SR, sr ); + } while( (sr & CYGHWR_HAL_STM32_FLASH_SR_BSY) && timeout-- > 0); + + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FLASH_CR, 0 ); + + return sr; +} + +// ---------------------------------------------------------------------------- +// Write data to flash, using individual word writes. The destination +// address will be aligned in a way suitable for the bus. The source +// address need not be aligned. The count is in STM32_TYPE's, not in +// bytes. + +static int +stm32_flash_hw_program( volatile STM32_TYPE* addr, const cyg_uint16* buf, cyg_uint32 count) +{ + cyg_uint32 base = CYGHWR_HAL_STM32_FLASH; + cyg_uint32 sr = 0, cr = 0; + + cr |= CYGHWR_HAL_STM32_FLASH_CR_PG; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FLASH_CR, cr ); + + stf_diag("cr %08x\n", cr ); + + while( count-- ) + { + cyg_uint32 timeout = 100000; + + HAL_WRITE_UINT16( addr, *buf ); + + addr++; + buf++; + + do + { + HAL_READ_UINT32( base+CYGHWR_HAL_STM32_FLASH_SR, sr ); +// stf_diag("sr %08x\n", sr ); + } while( (sr & CYGHWR_HAL_STM32_FLASH_SR_BSY) && timeout-- > 0 ); + } + + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FLASH_CR, 0 ); + + stf_diag("cr %08x sr %08x\n", cr, sr ); + + return sr; +} + +// ---------------------------------------------------------------------------- +// Erase a single block. The calling code will have supplied a pointer +// aligned to a block boundary. + +static int +stm32_flash_erase(struct cyg_flash_dev* dev, cyg_flashaddr_t dest) +{ + int (*erase_fn)(cyg_uint32); + volatile STM32_TYPE* uncached; + cyg_flashaddr_t block_start; + size_t block_size; + int result; + STM32_INTSCACHE_STATE; + + stf_diag("dest %p\n", dest); + CYG_CHECK_DATA_PTR(dev, "valid flash device pointer required"); + CYG_ASSERT((dest >= dev->start) && (dest <= dev->end), "flash address out of device range"); + + stm32_flash_get_block_info(dev, dest, &block_start, &block_size); + CYG_ASSERT(dest == block_start, "erase address should be the start of a flash block"); + + uncached = STM32_UNCACHED_ADDRESS(dest); + erase_fn = (int (*)(cyg_uint32)) cyg_flash_anonymizer( & stm32_flash_hw_erase ); + + STM32_INTSCACHE_BEGIN(); + + result = (*erase_fn)(block_start); + result = stm32_flash_decode_error( result ); + + STM32_INTSCACHE_END(); + + return result; +} + +// ---------------------------------------------------------------------------- +// Write some data to the flash. The destination must be aligned to a +// 16 bit boundary. Higher level code guarantees that the data will +// not straddle a block boundary. + +int +stm32_flash_program(struct cyg_flash_dev* dev, cyg_flashaddr_t dest, const void* src, size_t len) +{ + int (*program_fn)(volatile STM32_TYPE*, const cyg_uint16*, cyg_uint32); + volatile STM32_TYPE* uncached; + const cyg_uint16* data; + size_t to_write; + int result = CYG_FLASH_ERR_OK; + + STM32_INTSCACHE_STATE; + + stf_diag("dest %p src %p len %p(%d)\n", dest, src, len, len); + CYG_CHECK_DATA_PTR(dev, "valid flash device pointer required"); + CYG_ASSERT((dest >= dev->start) && ((CYG_ADDRESS)dest <= dev->end), "flash address out of device range"); + + // Source and destination must be 16-bit aligned. + if( (0 != ((CYG_ADDRESS)dest & 1)) || + (0 != ((CYG_ADDRESS)src & 1)) ) + return CYG_FLASH_ERR_INVALID; + + uncached = STM32_UNCACHED_ADDRESS(dest); + data = (const cyg_uint16*) src; + to_write = len / sizeof(STM32_TYPE); // Number of words, not bytes + program_fn = (int (*)(volatile STM32_TYPE*, const cyg_uint16*, cyg_uint32)) cyg_flash_anonymizer( & stm32_flash_hw_program ); + + STM32_INTSCACHE_BEGIN(); + while (to_write > 0) + { + size_t this_write = (to_write < CYGNUM_DEVS_FLASH_STM32_V2_PROGRAM_BURST_SIZE) ? + to_write : CYGNUM_DEVS_FLASH_STM32_V2_PROGRAM_BURST_SIZE; + + + result = (*program_fn)(uncached, data, this_write); + result = stm32_flash_decode_error( result ); + if (result != CYG_FLASH_ERR_OK) + { + break; + } + to_write -= this_write; + if (to_write > 0) + { + // There is still more to be written. The last write must have been a burst size + uncached += this_write; + data += this_write; + STM32_INTSCACHE_SUSPEND(); + STM32_INTSCACHE_RESUME(); + } + } + STM32_INTSCACHE_END(); + return result; +} + +// ---------------------------------------------------------------------------- +// Function table + +const CYG_FLASH_FUNS(cyg_stm32_flash_funs, + &stm32_flash_init, + &stm32_flash_query, + &stm32_flash_erase, + &stm32_flash_program, + (int (*)(struct cyg_flash_dev*, const cyg_flashaddr_t, void*, size_t))0, + cyg_flash_devfn_lock_nop, + cyg_flash_devfn_unlock_nop); + +// ---------------------------------------------------------------------------- +// End of stm32_flash.c
new file mode 100644 --- /dev/null +++ b/packages/devs/serial/cortexm/stm32/current/ChangeLog @@ -0,0 +1,40 @@ +2008-10-07 Nick Garnett <nickg@ecoscentric.com> + + * cdl/ser_cortexm_stm32.cdl: + * src/stm32_serial.h: + * src/stm32_serial.c: + New package: serial driver support for ST STM32 + microcontrollers. + +//=========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//===========================================================================
new file mode 100644 --- /dev/null +++ b/packages/devs/serial/cortexm/stm32/current/cdl/ser_cortexm_stm32.cdl @@ -0,0 +1,329 @@ +# ==================================================================== +# +# ser_cortexm_stm32.cdl +# +# eCos serial ST STM32 configuration data +# +# ==================================================================== +#####ECOSGPLCOPYRIGHTBEGIN#### +## ------------------------------------------- +## This file is part of eCos, the Embedded Configurable Operating System. +## Copyright (C) 2008 eCosCentric Limited +## +## eCos 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 2 or (at your option) any later version. +## +## eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +## +## As a special exception, if other files instantiate templates or use macros +## or inline functions from this file, or you compile this file and link it +## with other works to produce a work based on this file, this file does not +## by itself cause the resulting work to be covered by the GNU General Public +## License. However the source code for this file must still be made available +## in accordance with section (3) of the GNU General Public License. +## +## This exception does not invalidate any other reasons why a work based on +## this file might be covered by the GNU General Public License. +## +## ------------------------------------------- +#####ECOSGPLCOPYRIGHTEND#### +# ==================================================================== +######DESCRIPTIONBEGIN#### +# +# Author(s): nickg +# Date: 2008-09-10 +# +#####DESCRIPTIONEND#### +# +# ==================================================================== + + +cdl_package CYGPKG_IO_SERIAL_CORTEXM_STM32 { + display "ST STM32 serial device drivers" + + parent CYGPKG_IO_SERIAL_DEVICES + active_if CYGPKG_IO_SERIAL + active_if CYGPKG_HAL_CORTEXM_STM32 + + requires CYGPKG_ERROR + include_dir cyg/io + description " + This option enables the serial device drivers for the + ST STM32." + + compile -library=libextras.a stm32_serial.c + + define_proc { + puts $::cdl_system_header "/***** serial driver proc output start *****/" + puts $::cdl_system_header "#define CYGDAT_IO_SERIAL_DEVICE_HEADER <pkgconf/io_serial_cortexm_stm32.h>" + puts $::cdl_system_header "/***** serial driver proc output end *****/" + } + +cdl_component CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL0 { + display "ST STM32 serial port 0 driver" + flavor bool + default_value CYGINT_HAL_STM32_UART0>0 + description " + This option includes the serial device driver for the ST STM32 + port 0." + + cdl_option CYGDAT_IO_SERIAL_CORTEXM_STM32_SERIAL0_NAME { + display "Device name for ST STM32 serial port 0 driver" + flavor data + default_value {"\"/dev/ser0\""} + description " + This option specifies the name of the serial device for the + ST STM32 port 0." + } + + cdl_option CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BAUD { + display "Baud rate for the ST STM32 serial port 0 driver" + flavor data + legal_values { 50 75 110 "134_5" 150 200 300 600 1200 1800 2400 3600 + 4800 7200 9600 14400 19200 38400 57600 115200 230400 + } + default_value { 38400 } + description " + This option specifies the default baud rate (speed) for the + ST STM32 port 0." + } + + cdl_option CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BUFSIZE { + display "Buffer size for the ST STM32 serial port 0 driver" + flavor data + legal_values 0 to 8192 + default_value 128 + description " + This option specifies the size of the internal buffers used + for the ST STM32 port 0." + } +} + +cdl_component CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL1 { + display "ST STM32 serial port 1 driver" + flavor bool + default_value CYGINT_HAL_STM32_UART1>0 + description " + This option includes the serial device driver for the ST STM32 + port 1." + + cdl_option CYGDAT_IO_SERIAL_CORTEXM_STM32_SERIAL1_NAME { + display "Device name for ST STM32 serial port 1 driver" + flavor data + default_value {"\"/dev/ser1\""} + description " + This option specifies the name of the serial device for the + ST STM32 port 1." + } + + cdl_option CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BAUD { + display "Baud rate for the ST STM32 serial port 1 driver" + flavor data + legal_values { 50 75 110 "134_5" 150 200 300 600 1200 1800 2400 3600 + 4800 7200 9600 14400 19200 38400 57600 115200 230400 + } + default_value 38400 + description " + This option specifies the default baud rate (speed) for the + ST STM32 port 1." + } + + cdl_option CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BUFSIZE { + display "Buffer size for the ST STM32 serial port 1 driver" + flavor data + legal_values 0 to 8192 + default_value 128 + description " + This option specifies the size of the internal buffers used + for the ST STM32 port 1." + } +} + +cdl_component CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL2 { + display "ST STM32 serial port 2 driver" + flavor bool + default_value CYGINT_HAL_STM32_UART2>0 + description " + This option includes the serial device driver for the ST STM32 + port 2." + + cdl_option CYGDAT_IO_SERIAL_CORTEXM_STM32_SERIAL2_NAME { + display "Device name for ST STM32 serial port 2 driver" + flavor data + default_value {"\"/dev/ser2\""} + description " + This option specifies the name of the serial device for the + ST STM32 port 2." + } + + cdl_option CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BAUD { + display "Baud rate for the ST STM32 serial port 2 driver" + flavor data + legal_values { 50 75 110 "134_5" 150 200 300 600 1200 1800 2400 3600 + 4800 7200 9600 14400 19200 38400 57600 115200 230400 + } + default_value 38400 + description " + This option specifies the default baud rate (speed) for the + ST STM32 port 2." + } + + cdl_option CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BUFSIZE { + display "Buffer size for the ST STM32 serial port 2 driver" + flavor data + legal_values 0 to 8192 + default_value 128 + description " + This option specifies the size of the internal buffers used + for the ST STM32 port 2." + } +} + +cdl_component CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL3 { + display "ST STM32 serial port 3 driver" + flavor bool + default_value CYGINT_HAL_STM32_UART3>0 + description " + This option includes the serial device driver for the ST STM32 + port 3." + + cdl_option CYGDAT_IO_SERIAL_CORTEXM_STM32_SERIAL3_NAME { + display "Device name for ST STM32 serial port 3 driver" + flavor data + default_value {"\"/dev/ser3\""} + description " + This option specifies the name of the serial device for the + ST STM32 port 3." + } + + cdl_option CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BAUD { + display "Baud rate for the ST STM32 serial port 3 driver" + flavor data + legal_values { 50 75 110 "134_5" 150 200 300 600 1200 1800 2400 3600 + 4800 7200 9600 14400 19200 38400 57600 115200 230400 + } + default_value 38400 + description " + This option specifies the default baud rate (speed) for the + ST STM32 port 3." + } + + cdl_option CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BUFSIZE { + display "Buffer size for the ST STM32 serial port 3 driver" + flavor data + legal_values 0 to 8192 + default_value 128 + description " + This option specifies the size of the internal buffers used + for the ST STM32 port 3." + } +} + +cdl_component CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL4 { + display "ST STM32 serial port 4 driver" + flavor bool + default_value CYGINT_HAL_STM32_UART4>0 + description " + This option includes the serial device driver for the ST STM32 + port 4." + + cdl_option CYGDAT_IO_SERIAL_CORTEXM_STM32_SERIAL4_NAME { + display "Device name for ST STM32 serial port 4 driver" + flavor data + default_value {"\"/dev/ser4\""} + description " + This option specifies the name of the serial device for the + ST STM32 port 4." + } + + cdl_option CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BAUD { + display "Baud rate for the ST STM32 serial port 4 driver" + flavor data + legal_values { 50 75 110 "134_5" 150 200 300 600 1200 1800 2400 3600 + 4800 7200 9600 14400 19200 38400 57600 115200 230400 + } + default_value 38400 + description " + This option specifies the default baud rate (speed) for the + ST STM32 port 4." + } + + cdl_option CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BUFSIZE { + display "Buffer size for the ST STM32 serial port 4 driver" + flavor data + legal_values 0 to 8192 + default_value 128 + description " + This option specifies the size of the internal buffers used + for the ST STM32 port 4." + } +} + + + cdl_component CYGPKG_IO_SERIAL_CORTEXM_STM32_OPTIONS { + display "Serial device driver build options" + flavor none + description " + Package specific build options including control over + compiler flags used only in building this package, + and details of which tests are built." + + + cdl_option CYGPKG_IO_SERIAL_CORTEXM_STM32_CFLAGS_ADD { + display "Additional compiler flags" + flavor data + no_define + default_value { "" } + description " + This option modifies the set of compiler flags for + building these serial device drivers. These flags are used in addition + to the set of global flags." + } + + cdl_option CYGPKG_IO_SERIAL_CORTEXM_STM32_CFLAGS_REMOVE { + display "Suppressed compiler flags" + flavor data + no_define + default_value { "" } + description " + This option modifies the set of compiler flags for + building these serial device drivers. These flags are removed from + the set of global flags if present." + } + } + + cdl_component CYGPKG_IO_SERIAL_CORTEXM_STM32_TESTING { + display "Testing parameters" + flavor none + + implements CYGINT_IO_SERIAL_TEST_SKIP_115200 + implements CYGINT_IO_SERIAL_TEST_SKIP_57600 + implements CYGINT_IO_SERIAL_TEST_SKIP_38400 + + cdl_option CYGPRI_SER_TEST_SER_DEV { + display "Serial device used for testing" + flavor data + default_value { "\"/dev/ser1\"" } + } + + cdl_option CYGPRI_SER_TEST_TTY_DEV { + display "TTY-mode serial device used for testing" + flavor data + default_value { "\"/dev/tty1\"" } + } + + define_proc { + puts $::cdl_header "#define CYGPRI_SER_TEST_CRASH_ID \"stm32\"" + } + } +} + +# EOF ser_cortexm_stm32.cdl
new file mode 100644 --- /dev/null +++ b/packages/devs/serial/cortexm/stm32/current/src/stm32_serial.c @@ -0,0 +1,838 @@ +//========================================================================== +// +// devs/serial/cortexm/stm32/stm32_serial.c +// +// ST STM32 Serial I/O Interface Module +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc. +// Copyright (C) 2004, 2005, 2006, 2008 eCosCentric Limited +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-09-10 +// Purpose: ST STM32 Serial I/O module +// Description: +// +//####DESCRIPTIONEND#### +// +//========================================================================== + +#include <pkgconf/hal.h> +#include <pkgconf/infra.h> +#include <pkgconf/system.h> +#include <pkgconf/io_serial.h> +#include <pkgconf/io.h> +#include <pkgconf/kernel.h> + +#include <cyg/io/io.h> +#include <cyg/hal/hal_io.h> +#include <cyg/hal/hal_intr.h> +#include <cyg/hal/hal_cache.h> +#include <cyg/io/devtab.h> +#include <cyg/io/serial.h> +#include <cyg/infra/diag.h> +#include <cyg/infra/cyg_type.h> +#include <cyg/infra/cyg_ass.h> + + +#ifdef CYGPKG_IO_SERIAL_CORTEXM_STM32 + +#include "stm32_serial.h" + +//========================================================================== + +#define STM32_RXBUFSIZE 16 + +typedef struct stm32_serial_info +{ + CYG_WORD uart; + CYG_ADDRWORD base; + CYG_WORD int_num; + cyg_int32 rx_pin; + cyg_int32 tx_pin; + cyg_int32 rts_pin; + cyg_int32 cts_pin; + + cyg_bool tx_active; + + volatile cyg_uint8 buf[STM32_RXBUFSIZE]; + volatile int buf_head; + volatile int buf_tail; + + cyg_interrupt serial_interrupt; + cyg_handle_t serial_interrupt_handle; +} stm32_serial_info; + +//========================================================================== + +static bool stm32_serial_init(struct cyg_devtab_entry *tab); +static bool stm32_serial_putc_interrupt(serial_channel *chan, unsigned char c); +#if (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL0) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL1) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL2) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL3) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL4) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BUFSIZE == 0) +static bool stm32_serial_putc_polled(serial_channel *chan, unsigned char c); +#endif +static Cyg_ErrNo stm32_serial_lookup(struct cyg_devtab_entry **tab, + struct cyg_devtab_entry *sub_tab, + const char *name); +static unsigned char stm32_serial_getc_interrupt(serial_channel *chan); +#if (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL0) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL1) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL2) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL3) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL4) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BUFSIZE == 0) +static unsigned char stm32_serial_getc_polled(serial_channel *chan); +#endif +static Cyg_ErrNo stm32_serial_set_config(serial_channel *chan, cyg_uint32 key, + const void *xbuf, cyg_uint32 *len); +static void stm32_serial_start_xmit(serial_channel *chan); +static void stm32_serial_stop_xmit(serial_channel *chan); + +static cyg_uint32 stm32_serial_ISR(cyg_vector_t vector, cyg_addrword_t data); +static void stm32_serial_DSR(cyg_vector_t vector, cyg_ucount32 count, cyg_addrword_t data); + +//========================================================================== + +#if (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL0) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BUFSIZE > 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL1) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BUFSIZE > 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL2) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BUFSIZE > 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL3) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BUFSIZE > 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL4) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BUFSIZE > 0) +static SERIAL_FUNS(stm32_serial_funs_interrupt, + stm32_serial_putc_interrupt, + stm32_serial_getc_interrupt, + stm32_serial_set_config, + stm32_serial_start_xmit, + stm32_serial_stop_xmit + ); +#endif + +#if (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL0) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL1) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL2) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL3) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BUFSIZE == 0) \ + || (defined(CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL4) && CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BUFSIZE == 0) +static SERIAL_FUNS(stm32_serial_funs_polled, + stm32_serial_putc_polled, + stm32_serial_getc_polled, + stm32_serial_set_config, + stm32_serial_start_xmit, + stm32_serial_stop_xmit + ); +#endif + +//========================================================================== + +#ifdef CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL0 +static stm32_serial_info stm32_serial_info0 = { + uart : 0, + base : (CYG_ADDRWORD) CYGHWR_HAL_STM32_UART1, + int_num : CYGNUM_HAL_INTERRUPT_UART1, + rx_pin : CYGHWR_HAL_STM32_UART1_RX, + tx_pin : CYGHWR_HAL_STM32_UART1_TX, + rts_pin : CYGHWR_HAL_STM32_UART1_RTS, + cts_pin : CYGHWR_HAL_STM32_UART1_CTS, +}; + +#if CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BUFSIZE > 0 +static unsigned char stm32_serial_out_buf0[CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BUFSIZE]; +static unsigned char stm32_serial_in_buf0[CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BUFSIZE]; + +static SERIAL_CHANNEL_USING_INTERRUPTS(stm32_serial_channel0, + stm32_serial_funs_interrupt, + stm32_serial_info0, + CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BAUD), + CYG_SERIAL_STOP_DEFAULT, + CYG_SERIAL_PARITY_DEFAULT, + CYG_SERIAL_WORD_LENGTH_DEFAULT, + CYG_SERIAL_FLAGS_DEFAULT, + &stm32_serial_out_buf0[0], sizeof(stm32_serial_out_buf0), + &stm32_serial_in_buf0[0], sizeof(stm32_serial_in_buf0) + ); +#else +static SERIAL_CHANNEL(stm32_serial_channel0, + stm32_serial_funs_polled, + stm32_serial_info0, + CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL0_BAUD), + CYG_SERIAL_STOP_DEFAULT, + CYG_SERIAL_PARITY_DEFAULT, + CYG_SERIAL_WORD_LENGTH_DEFAULT, + CYG_SERIAL_FLAGS_DEFAULT + ); +#endif + +DEVTAB_ENTRY(stm32_serial_io0, + CYGDAT_IO_SERIAL_CORTEXM_STM32_SERIAL0_NAME, + 0, // Does not depend on a lower level interface + &cyg_io_serial_devio, + stm32_serial_init, + stm32_serial_lookup, // Serial driver may need initializing + &stm32_serial_channel0 + ); +#endif // CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL0 + +//========================================================================== + +#ifdef CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL1 +static stm32_serial_info stm32_serial_info1 = { + uart : 1, + base : (CYG_ADDRWORD) CYGHWR_HAL_STM32_UART2, + int_num : CYGNUM_HAL_INTERRUPT_UART2, + rx_pin : CYGHWR_HAL_STM32_UART2_RX, + tx_pin : CYGHWR_HAL_STM32_UART2_TX, + rts_pin : CYGHWR_HAL_STM32_UART2_RTS, + cts_pin : CYGHWR_HAL_STM32_UART2_CTS, +}; + +#if CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BUFSIZE > 0 +static unsigned char stm32_serial_out_buf1[CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BUFSIZE]; +static unsigned char stm32_serial_in_buf1[CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BUFSIZE]; + +static SERIAL_CHANNEL_USING_INTERRUPTS(stm32_serial_channel1, + stm32_serial_funs_interrupt, + stm32_serial_info1, + CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BAUD), + CYG_SERIAL_STOP_DEFAULT, + CYG_SERIAL_PARITY_DEFAULT, + CYG_SERIAL_WORD_LENGTH_DEFAULT, + CYG_SERIAL_FLAGS_DEFAULT, + &stm32_serial_out_buf1[0], sizeof(stm32_serial_out_buf1), + &stm32_serial_in_buf1[0], sizeof(stm32_serial_in_buf1) + ); +#else +static SERIAL_CHANNEL(stm32_serial_channel1, + stm32_serial_funs_polled, + stm32_serial_info1, + CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL1_BAUD), + CYG_SERIAL_STOP_DEFAULT, + CYG_SERIAL_PARITY_DEFAULT, + CYG_SERIAL_WORD_LENGTH_DEFAULT, + CYG_SERIAL_FLAGS_DEFAULT + ); +#endif + +DEVTAB_ENTRY(stm32_serial_io1, + CYGDAT_IO_SERIAL_CORTEXM_STM32_SERIAL1_NAME, + 0, // Does not depend on a lower level interface + &cyg_io_serial_devio, + stm32_serial_init, + stm32_serial_lookup, // Serial driver may need initializing + &stm32_serial_channel1 + ); +#endif // CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL1 + +//========================================================================== + +#ifdef CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL2 +static stm32_serial_info stm32_serial_info2 = { + uart : 2, + base : (CYG_ADDRWORD) CYGHWR_HAL_STM32_UART3, + int_num : CYGNUM_HAL_INTERRUPT_UART3, + rx_pin : CYGHWR_HAL_STM32_UART3_RX, + tx_pin : CYGHWR_HAL_STM32_UART3_TX, + rts_pin : CYGHWR_HAL_STM32_UART3_RTS, + cts_pin : CYGHWR_HAL_STM32_UART3_CTS, +}; + +#if CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BUFSIZE > 0 +static unsigned char stm32_serial_out_buf2[CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BUFSIZE]; +static unsigned char stm32_serial_in_buf2[CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BUFSIZE]; + +static SERIAL_CHANNEL_USING_INTERRUPTS(stm32_serial_channel2, + stm32_serial_funs_interrupt, + stm32_serial_info2, + CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BAUD), + CYG_SERIAL_STOP_DEFAULT, + CYG_SERIAL_PARITY_DEFAULT, + CYG_SERIAL_WORD_LENGTH_DEFAULT, + CYG_SERIAL_FLAGS_DEFAULT, + &stm32_serial_out_buf2[0], sizeof(stm32_serial_out_buf2), + &stm32_serial_in_buf2[0], sizeof(stm32_serial_in_buf2) + ); +#else +static SERIAL_CHANNEL(stm32_serial_channel2, + stm32_serial_funs_polled, + stm32_serial_info2, + CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL2_BAUD), + CYG_SERIAL_STOP_DEFAULT, + CYG_SERIAL_PARITY_DEFAULT, + CYG_SERIAL_WORD_LENGTH_DEFAULT, + CYG_SERIAL_FLAGS_DEFAULT + ); +#endif + +DEVTAB_ENTRY(stm32_serial_io2, + CYGDAT_IO_SERIAL_CORTEXM_STM32_SERIAL2_NAME, + 0, // Does not depend on a lower level interface + &cyg_io_serial_devio, + stm32_serial_init, + stm32_serial_lookup, // Serial driver may need initializing + &stm32_serial_channel2 + ); +#endif // CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL2 + +//========================================================================== + +#ifdef CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL3 +static stm32_serial_info stm32_serial_info3 = { + uart : 3, + base : (CYG_ADDRWORD) CYGHWR_HAL_STM32_UART4, + int_num : CYGNUM_HAL_INTERRUPT_UART4, + rx_pin : CYGHWR_HAL_STM32_UART4_RX, + tx_pin : CYGHWR_HAL_STM32_UART4_TX, + rts_pin : CYGHWR_HAL_STM32_UART4_RTS, + cts_pin : CYGHWR_HAL_STM32_UART4_CTS, +}; + +#if CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BUFSIZE > 0 +static unsigned char stm32_serial_out_buf3[CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BUFSIZE]; +static unsigned char stm32_serial_in_buf3[CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BUFSIZE]; + +static SERIAL_CHANNEL_USING_INTERRUPTS(stm32_serial_channel3, + stm32_serial_funs_interrupt, + stm32_serial_info3, + CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BAUD), + CYG_SERIAL_STOP_DEFAULT, + CYG_SERIAL_PARITY_DEFAULT, + CYG_SERIAL_WORD_LENGTH_DEFAULT, + CYG_SERIAL_FLAGS_DEFAULT, + &stm32_serial_out_buf3[0], sizeof(stm32_serial_out_buf3), + &stm32_serial_in_buf3[0], sizeof(stm32_serial_in_buf3) + ); +#else +static SERIAL_CHANNEL(stm32_serial_channel3, + stm32_serial_funs_polled, + stm32_serial_info3, + CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL3_BAUD), + CYG_SERIAL_STOP_DEFAULT, + CYG_SERIAL_PARITY_DEFAULT, + CYG_SERIAL_WORD_LENGTH_DEFAULT, + CYG_SERIAL_FLAGS_DEFAULT + ); +#endif + +DEVTAB_ENTRY(stm32_serial_io3, + CYGDAT_IO_SERIAL_CORTEXM_STM32_SERIAL3_NAME, + 0, // Does not depend on a lower level interface + &cyg_io_serial_devio, + stm32_serial_init, + stm32_serial_lookup, // Serial driver may need initializing + &stm32_serial_channel3 + ); +#endif // CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL3 + +//========================================================================== + +#ifdef CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL4 +static stm32_serial_info stm32_serial_info4 = { + uart : 4, + base : (CYG_ADDRWORD) CYGHWR_HAL_STM32_UART5, + int_num : CYGNUM_HAL_INTERRUPT_UART5, + rx_pin : CYGHWR_HAL_STM32_UART5_RX, + tx_pin : CYGHWR_HAL_STM32_UART5_TX, + rts_pin : CYGHWR_HAL_STM32_UART5_RTS, + cts_pin : CYGHWR_HAL_STM32_UART5_CTS, +}; + +#if CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BUFSIZE > 0 +static unsigned char stm32_serial_out_buf4[CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BUFSIZE]; +static unsigned char stm32_serial_in_buf4[CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BUFSIZE]; + +static SERIAL_CHANNEL_USING_INTERRUPTS(stm32_serial_channel4, + stm32_serial_funs_interrupt, + stm32_serial_info4, + CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BAUD), + CYG_SERIAL_STOP_DEFAULT, + CYG_SERIAL_PARITY_DEFAULT, + CYG_SERIAL_WORD_LENGTH_DEFAULT, + CYG_SERIAL_FLAGS_DEFAULT, + &stm32_serial_out_buf4[0], sizeof(stm32_serial_out_buf4), + &stm32_serial_in_buf4[0], sizeof(stm32_serial_in_buf4) + ); +#else +static SERIAL_CHANNEL(stm32_serial_channel4, + stm32_serial_funs_polled, + stm32_serial_info4, + CYG_SERIAL_BAUD_RATE(CYGNUM_IO_SERIAL_CORTEXM_STM32_SERIAL4_BAUD), + CYG_SERIAL_STOP_DEFAULT, + CYG_SERIAL_PARITY_DEFAULT, + CYG_SERIAL_WORD_LENGTH_DEFAULT, + CYG_SERIAL_FLAGS_DEFAULT + ); +#endif + +DEVTAB_ENTRY(stm32_serial_io4, + CYGDAT_IO_SERIAL_CORTEXM_STM32_SERIAL4_NAME, + 0, // Does not depend on a lower level interface + &cyg_io_serial_devio, + stm32_serial_init, + stm32_serial_lookup, // Serial driver may need initializing + &stm32_serial_channel4 + ); +#endif // CYGPKG_IO_SERIAL_CORTEXM_STM32_SERIAL4 + + +//========================================================================== +// Internal function to actually configure the hardware to desired baud +// rate, etc. + +static bool +stm32_serial_config_port(serial_channel *chan, cyg_serial_info_t *new_config, bool init) +{ + stm32_serial_info * const stm32_chan = (stm32_serial_info *)chan->dev_priv; + const CYG_ADDRWORD base = stm32_chan->base; + cyg_uint32 parity = select_parity[new_config->parity]; + cyg_uint32 word_length = select_word_length[new_config->word_length-CYGNUM_SERIAL_WORD_LENGTH_5]; + cyg_uint32 stop_bits = select_stop_bits[new_config->stop]; + cyg_uint32 cr1 = 0; + cyg_uint32 cr2 = 0; + cyg_uint32 cr3 = 0; + + // Set up FIFO buffer + stm32_chan->buf_head = stm32_chan->buf_tail = 0; + + // Set up GPIO pins + CYGHWR_HAL_STM32_GPIO_SET( stm32_chan->rx_pin ); + CYGHWR_HAL_STM32_GPIO_SET( stm32_chan->tx_pin ); + CYGHWR_HAL_STM32_GPIO_SET( stm32_chan->rts_pin ); + CYGHWR_HAL_STM32_GPIO_SET( stm32_chan->cts_pin ); + + // Select line parameters + cr1 |= parity|word_length; + cr2 |= stop_bits; + + cr1 |= CYGHWR_HAL_STM32_UART_CR1_TE | CYGHWR_HAL_STM32_UART_CR1_RE; + + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_UART_CR1, cr1 ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_UART_CR2, cr2 ); + + // Set up baud rate + hal_stm32_uart_setbaud( base, select_baud[new_config->baud] ); + + // Enable the uart + cr1 |= CYGHWR_HAL_STM32_UART_CR1_UE; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_UART_CR1, cr1 ); + + +#ifdef CYGOPT_IO_SERIAL_FLOW_CONTROL_HW + // Handle RTS by hand but leave CTS to be handled by the UART hardware + if ( (new_config->flags & CYGNUM_SERIAL_FLOW_RTSCTS_TX) && stm32_chan->cts_pin != CYGHWR_HAL_STM32_GPIO_NONE ) + { + cr3 |= CYGHWR_HAL_STM32_UART_CR3_CTSE; + } +#endif + + if(1) + { + // Enable receive and error interrupts + + cr1 |= CYGHWR_HAL_STM32_UART_CR1_RXNEIE; + cr3 |= CYGHWR_HAL_STM32_UART_CR3_EIE; + + HAL_WRITE_UINT32( base + CYGHWR_HAL_STM32_UART_CR1, cr1 ); + } + + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_UART_CR3, cr3 ); + + stm32_chan->tx_active = false; + + if (new_config != &chan->config) + chan->config = *new_config; + + return true; +} + +//========================================================================== +// Function to initialize the device. Called at bootstrap time. + +static bool +stm32_serial_init(struct cyg_devtab_entry *tab) +{ + serial_channel * const chan = (serial_channel *) tab->priv; + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + int res; + + (chan->callbacks->serial_init)(chan); // Really only required for interrupt driven devices + if (chan->out_cbuf.len != 0) { + cyg_drv_interrupt_create(stm32_chan->int_num, + 0x80, + (cyg_addrword_t)chan, + stm32_serial_ISR, + stm32_serial_DSR, + &stm32_chan->serial_interrupt_handle, + &stm32_chan->serial_interrupt); + cyg_drv_interrupt_attach(stm32_chan->serial_interrupt_handle); + cyg_drv_interrupt_unmask(stm32_chan->int_num); + + } + + res = stm32_serial_config_port(chan, &chan->config, true); + return res; +} + +//========================================================================== +// This routine is called when the device is "looked" up (i.e. attached) + +static Cyg_ErrNo +stm32_serial_lookup(struct cyg_devtab_entry **tab, + struct cyg_devtab_entry *sub_tab, + const char *name) +{ + serial_channel * const chan = (serial_channel *) (*tab)->priv; + + (chan->callbacks->serial_init)(chan); // Really only required for interrupt driven devices + return ENOERR; +} + +//========================================================================== +// Send a character to the device output buffer. +// Return 'true' if character is sent to device + +static bool +stm32_serial_putc_interrupt(serial_channel *chan, unsigned char c) +{ + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + const CYG_ADDRWORD base = stm32_chan->base; + cyg_uint32 status; + + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_SR, status ); + + if (status & CYGHWR_HAL_STM32_UART_SR_TXE) + { + HAL_WRITE_UINT32( base + CYGHWR_HAL_STM32_UART_DR, c ); + return true; + } + + return false; +} + +//========================================================================== + +static bool +stm32_serial_putc_polled(serial_channel *chan, unsigned char c) +{ + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + const CYG_ADDRWORD base = stm32_chan->base; + cyg_uint32 status; + + do { + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_SR, status ); + } while ((status & CYGHWR_HAL_STM32_UART_SR_TXE) == 0); + + HAL_WRITE_UINT32( base + CYGHWR_HAL_STM32_UART_DR, c ); + + return true; +} + +//========================================================================== +// Fetch a character from the device input buffer + +static unsigned char +stm32_serial_getc_interrupt(serial_channel *chan) +{ + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + const CYG_ADDRWORD base = stm32_chan->base; + CYG_WORD32 c; + + // Read data + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_DR, c); + return (unsigned char) (c&0xFF); +} + +//========================================================================== + +static unsigned char +stm32_serial_getc_polled(serial_channel *chan) +{ + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + const CYG_ADDRWORD base = stm32_chan->base; + cyg_uint32 stat; + cyg_uint32 c; + + do { + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_SR, stat ); + } while ((stat & CYGHWR_HAL_STM32_UART_SR_RXNE) == 0); + + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_DR, c); + + return (unsigned char) (c&0xFF); +} + +//========================================================================== +// Set up the device characteristics; baud rate, etc. + +static Cyg_ErrNo +stm32_serial_set_config(serial_channel *chan, cyg_uint32 key, + const void *xbuf, cyg_uint32 *len) +{ + switch (key) { + case CYG_IO_SET_CONFIG_SERIAL_INFO: + { + cyg_serial_info_t *config = (cyg_serial_info_t *)xbuf; + if ( *len < sizeof(cyg_serial_info_t) ) { + return -EINVAL; + } + *len = sizeof(cyg_serial_info_t); + if ( true != stm32_serial_config_port(chan, config, false) ) + return -EINVAL; + } + break; + +#ifdef CYGOPT_IO_SERIAL_FLOW_CONTROL_HW + + case CYG_IO_SET_CONFIG_SERIAL_HW_RX_FLOW_THROTTLE: + { + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + cyg_uint32 *f = (cyg_uint32 *)xbuf; + + if ( *len < sizeof(*f) ) + return -EINVAL; + + if ( chan->config.flags & CYGNUM_SERIAL_FLOW_RTSCTS_RX ) + { + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + + // Note that the RTS line is active-low, so set it to 1 + // to throttle and 0 to allow the data to flow. + if( *f ) + CYGHWR_HAL_STM32_GPIO_OUT( stm32_chan->rts_pin, 1 ); + else + CYGHWR_HAL_STM32_GPIO_OUT( stm32_chan->rts_pin, 0 ); + } + } + break; + + case CYG_IO_SET_CONFIG_SERIAL_HW_FLOW_CONFIG: + { + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + Cyg_ErrNo result = ENOERR; + + // If the client is asking for DSR/DTR, refuse to do it. + if (0 != (chan->config.flags & (CYGNUM_SERIAL_FLOW_DSRDTR_RX | CYGNUM_SERIAL_FLOW_DSRDTR_TX))) + { + chan->config.flags &= ~(CYGNUM_SERIAL_FLOW_DSRDTR_RX | CYGNUM_SERIAL_FLOW_DSRDTR_TX); + result = -ENOSUPP; + } + + // If the client is asking for RTS/CTS then only allow it if + // the port has RTS/CTS lines attached to it. + if (0 != (chan->config.flags & (CYGNUM_SERIAL_FLOW_RTSCTS_RX | CYGNUM_SERIAL_FLOW_RTSCTS_TX))) + { + if( stm32_chan->rts_pin != CYGHWR_HAL_STM32_GPIO_NONE && + stm32_chan->cts_pin != CYGHWR_HAL_STM32_GPIO_NONE ) + { + chan->config.flags &= (CYGNUM_SERIAL_FLOW_RTSCTS_RX | CYGNUM_SERIAL_FLOW_RTSCTS_TX); + } + else + { + chan->config.flags &= ~(CYGNUM_SERIAL_FLOW_RTSCTS_RX | CYGNUM_SERIAL_FLOW_RTSCTS_TX); + result = -ENOSUPP; + } + } + return result; + } + +#endif + + default: + return -EINVAL; + } + return ENOERR; +} + +//========================================================================== +// Enable the transmitter on the device + +static void +stm32_serial_start_xmit(serial_channel *chan) +{ + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + const CYG_ADDRWORD base = stm32_chan->base; + cyg_uint32 cr1; + + if( !stm32_chan->tx_active ) + { + stm32_chan->tx_active = true; + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_CR1, cr1 ); + cr1 |= CYGHWR_HAL_STM32_UART_CR1_TXEIE; + HAL_WRITE_UINT32( base + CYGHWR_HAL_STM32_UART_CR1, cr1 ); + } + +} + +//========================================================================== +// Disable the transmitter on the device + +static void +stm32_serial_stop_xmit(serial_channel *chan) +{ + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + const CYG_ADDRWORD base = stm32_chan->base; + cyg_uint32 cr1; + + if( stm32_chan->tx_active ) + { + stm32_chan->tx_active = false; + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_CR1, cr1 ); + cr1 &= ~CYGHWR_HAL_STM32_UART_CR1_TXEIE; + HAL_WRITE_UINT32( base + CYGHWR_HAL_STM32_UART_CR1, cr1 ); + } + +} + +//========================================================================== +// Serial I/O - low level interrupt handler (ISR) +// +// This ISR does rather more than other serial driver ISRs. Normally, +// the ISR just masks the interrupt vector and schedules the DSR, +// which then handles all IO. However, if the processor is running out +// of external RAM it is too slow to handle higher baud rates using +// that technique. Something that is exacerbated by the lack of FIFOs +// in the USART hardware. +// +// Instead, this ISR receives any incoming data into a circular +// buffer, essentially providing the FIFO lacking in the +// hardware. Transmission is still offloaded to the DSR. Only TX +// interrupts are masked while this is done to prevent an interrupt +// loop, and to avoid blocking RX interrupts. + +static cyg_uint32 +stm32_serial_ISR(cyg_vector_t vector, cyg_addrword_t data) +{ + serial_channel * const chan = (serial_channel *) data; + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + const CYG_ADDRWORD base = stm32_chan->base; + cyg_uint32 stat; + cyg_uint32 ret = CYG_ISR_HANDLED; + cyg_drv_interrupt_acknowledge(vector); + + HAL_READ_UINT32(base + CYGHWR_HAL_STM32_UART_SR, stat); + + if( stat & CYGHWR_HAL_STM32_UART_SR_RXNE ) + { + cyg_uint32 c; + + while( stat & CYGHWR_HAL_STM32_UART_SR_RXNE ) + { + int next = stm32_chan->buf_head+1; + + if( next == STM32_RXBUFSIZE ) next = 0; + + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_DR, c); + + if( next != stm32_chan->buf_tail ) + { + stm32_chan->buf[stm32_chan->buf_head] = c&0xFF; + stm32_chan->buf_head = next; + ret |= CYG_ISR_CALL_DSR; + } + else + { + // TODO: deal with buffer overflow + } + + HAL_READ_UINT32(base + CYGHWR_HAL_STM32_UART_SR, stat); + } + } + else if( stat & CYGHWR_HAL_STM32_UART_SR_TXE ) + { + cyg_uint32 cr1; + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_CR1, cr1 ); + cr1 &= ~CYGHWR_HAL_STM32_UART_CR1_TXEIE; + HAL_WRITE_UINT32( base + CYGHWR_HAL_STM32_UART_CR1, cr1 ); + + ret |= CYG_ISR_CALL_DSR; + } + + + if( stat & CYGHWR_HAL_STM32_UART_SR_CTS ) + { + // Clear CTS status if we see it. + stat &= ~CYGHWR_HAL_STM32_UART_SR_CTS; + HAL_WRITE_UINT32( base + CYGHWR_HAL_STM32_UART_SR, stat ); + } + + if( stat & (CYGHWR_HAL_STM32_UART_SR_FE|CYGHWR_HAL_STM32_UART_SR_NE|CYGHWR_HAL_STM32_UART_SR_ORE) ) + { + // TODO: Handle hardware errors + } + + return ret; +} + +//========================================================================== +// Serial I/O - high level interrupt handler (DSR) + +static void +stm32_serial_DSR(cyg_vector_t vector, cyg_ucount32 count, cyg_addrword_t data) +{ + serial_channel * const chan = (serial_channel *) data; + stm32_serial_info * const stm32_chan = (stm32_serial_info *) chan->dev_priv; + const CYG_ADDRWORD base = stm32_chan->base; + CYG_WORD32 stat; + + while( stm32_chan->buf_head != stm32_chan->buf_tail ) + { + int next = stm32_chan->buf_tail+1; + cyg_uint8 c; + + if( next == STM32_RXBUFSIZE ) next = 0; + c = stm32_chan->buf[stm32_chan->buf_tail]; + stm32_chan->buf_tail = next; + + (chan->callbacks->rcv_char)(chan, c); + } + + HAL_READ_UINT32(base + CYGHWR_HAL_STM32_UART_SR, stat); + + if( stm32_chan->tx_active && stat & CYGHWR_HAL_STM32_UART_SR_TXE ) + { + cyg_uint32 cr1; + + (chan->callbacks->xmt_char)(chan); + + if( stm32_chan->tx_active ) + { + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_CR1, cr1 ); + cr1 |= CYGHWR_HAL_STM32_UART_CR1_TXEIE; + HAL_WRITE_UINT32( base + CYGHWR_HAL_STM32_UART_CR1, cr1 ); + } + } +} + +//========================================================================== +#endif // CYGPKG_IO_SERIAL_CORTEXM_STM32 +// end of stm32_serial.c
new file mode 100644 --- /dev/null +++ b/packages/devs/serial/cortexm/stm32/current/src/stm32_serial.h @@ -0,0 +1,114 @@ +#ifndef CYGONCE_CORTEXM_STM32_SERIAL_H +#define CYGONCE_CORTEXM_STM32_SERIAL_H + +// ==================================================================== +// +// stm32_serial.h +// +// Device I/O - Description of ST STM32 serial hardware +// +// ==================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +// ==================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-09-10 +// Purpose: Internal interfaces for serial I/O drivers +// Description: +// +//####DESCRIPTIONEND#### +// +// ==================================================================== + +#include <cyg/hal/hal_io.h> // Register definitions + +// ==================================================================== +// Translate system word length selector into local values. + +static cyg_uint32 select_word_length[] = { + 0, + 0, + 0, + CYGHWR_HAL_STM32_UART_CR1_M_8 +}; + +// ==================================================================== +// Translate system stop bit selector into control register bits. + +static cyg_uint32 select_stop_bits[] = { + CYGHWR_HAL_STM32_UART_CR2_STOP_0_5, // 0.5 stop bits + CYGHWR_HAL_STM32_UART_CR2_STOP_1, // 1 stop bit + CYGHWR_HAL_STM32_UART_CR2_STOP_1_5, // 1.5 stop bit + CYGHWR_HAL_STM32_UART_CR2_STOP_2 // 2 stop bit +}; + +// Translate system parity selector into local values. +static cyg_uint32 select_parity[] = { + 0, // No parity + CYGHWR_HAL_STM32_UART_CR1_PCE|CYGHWR_HAL_STM32_UART_CR1_PS_EVEN, // Even parity + CYGHWR_HAL_STM32_UART_CR1_PCE|CYGHWR_HAL_STM32_UART_CR1_PS_ODD, // Odd parity + 0, // Mark (1) parity -- not supported + 0 // Space (0) parity -- not supported +}; + +// ==================================================================== +// Translate system baud selector into direct baud rate value. This is +// then used to calculate the clock divisor from the PCLK clock. + +static cyg_int32 select_baud[] = { + 0, // Unused + 50, // 50 + 75, // 75 + 110, // 110 + 0, // 134.5 + 150, // 150 + 200, // 200 + 300, // 300 + 600, // 600 + 1200, // 1200 + 1800, // 1800 + 2400, // 2400 + 3600, // 3600 + 4800, // 4800 + 7200, // 7200 + 9600, // 9600 + 14400, // 14400 + 19200, // 19200 + 38400, // 38400 + 57600, // 57600 + 115200, // 115200 + 230400, // 230400 +}; + +// ==================================================================== +#endif // CYGONCE_CORTEXM_STM32_SERIAL_H
--- a/packages/ecos.db +++ b/packages/ecos.db @@ -6693,3 +6693,72 @@ package CYGPKG_ATHTTPD { } +# ========================================================================== +# Cortex-M architecture support + +package CYGPKG_HAL_CORTEXM { + alias { "Cortex-M common HAL" hal_cortexm cortexm_hal cortexm_arch_hal } + directory hal/cortexm/arch + script hal_cortexm.cdl + hardware + description " + The CortexM architecture HAL package provides generic support for the ARM + Cortex-M processor architecture. It is also necessary to select + variant and platform HAL packages." +} + +package CYGPKG_HAL_CORTEXM_STM32 { + alias { "ST STM32 variant HAL" hal_cortexm_stm32 } + directory hal/cortexm/stm32/var + script hal_cortexm_stm32.cdl + hardware + description " + The STM32 HAL package provides the support needed to run + eCos and RedBoot on targets based on the ST STM32 + family of microcontrollers." +} + +package CYGPKG_HAL_CORTEXM_STM32_STM3210E_EVAL { + alias { "ST STM3210E EVAL HAL" hal_cortexm_stm3210e_eval } + directory hal/cortexm/stm32/stm3210e_eval + script hal_cortexm_stm32_stm3210e_eval.cdl + hardware + description " + The stm3210e_eval HAL package provides the support needed to run + eCos on the ST STM3210E EVAL board." +} + +package CYGPKG_IO_SERIAL_CORTEXM_STM32 { + alias { "ST STM32 serial device drivers" + devs_serial_cortexm_stm32 stm32_serial_driver } + hardware + directory devs/serial/cortexm/stm32 + script ser_cortexm_stm32.cdl + description "ST STM32 serial device driver" +} + +package CYGPKG_DEVS_FLASH_STM32 { + alias { "Internal FLASH memory support for ST STM32" flash_stm32 } + directory devs/flash/cortexm/stm32 + script flash_stm32.cdl + hardware + description " + This package contains hardware support for the internal FLASH memory + on the ST STM32 devices." +} + +target stm3210e_eval { + alias { "ST STM3210E EVAL board" stm3210e } + packages { CYGPKG_HAL_CORTEXM + CYGPKG_HAL_CORTEXM_STM32 + CYGPKG_HAL_CORTEXM_STM32_STM3210E_EVAL + CYGPKG_DEVS_FLASH_AMD_AM29XXXXX_V2 + CYGPKG_DEVS_FLASH_STM32 + CYGPKG_IO_SERIAL_CORTEXM_STM32 + } + description "The stm3210e_eval target provides the packages needed + to run eCos on the STM3210E EVAL board." +} + +# ========================================================================== +# End of ecos.db
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/ChangeLog @@ -0,0 +1,62 @@ +2008-10-16 Nick Garnett <nickg@ecoscentric.com> + + * src/vectors.S: + * src/hal_misc.c: Tidy some comments and code. + +2008-10-10 Nick Garnett <nickg@ecoscentric.com> + + * src/hal_misc.c (hal_deliver_interrupt): Add support for chained + interrupts. + (hal_interrupt_end): Only increment scheduler lock when the kernel + is present. + + * include/hal_arch.h (HAL_THREAD_INIT_CONTEXT): Add end-stop to + new thread states to terminate GDB backtraces. + +2008-10-06 Nick Garnett <nickg@ecoscentric.com> + + * hal_cortexm.cdl: + * include/basetype.h: + * include/hal_arch.h: + * include/hal_intr.h: + * include/hal_io.h: + * include/cortex_stub.h: + * src/vectors.S: + * src/context.S: + * src/cortexm.ld: + * src/cortexm_stub.c: + * src/hal_misc.c: + New package -- Cortex-M architecture HAL. + +//=========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//===========================================================================
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/cdl/hal_cortexm.cdl @@ -0,0 +1,134 @@ +##========================================================================== +## +## hal_cortexm.cdl +## +## Cortex-M architectural HAL configuration data +## +##========================================================================== +######ECOSGPLCOPYRIGHTBEGIN#### +## ------------------------------------------- +## This file is part of eCos, the Embedded Configurable Operating System. +## Copyright (C) 2008 eCosCentric Limited. +## +## eCos 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 2 or (at your option) any later version. +## +## eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +## +## As a special exception, if other files instantiate templates or use macros +## or inline functions from this file, or you compile this file and link it +## with other works to produce a work based on this file, this file does not +## by itself cause the resulting work to be covered by the GNU General Public +## License. However the source code for this file must still be made available +## in accordance with section (3) of the GNU General Public License. +## +## This exception does not invalidate any other reasons why a work based on +## this file might be covered by the GNU General Public License. +## ------------------------------------------- +######ECOSGPLCOPYRIGHTEND#### +##========================================================================== +#######DESCRIPTIONBEGIN#### +## +## Author(s): nickg +## Date: 2008-07-30 +## +######DESCRIPTIONEND#### +## +##========================================================================== + +cdl_package CYGPKG_HAL_CORTEXM { + display "Cortex-M Architecture" + parent CYGPKG_HAL + hardware + include_dir cyg/hal + define_header hal_cortexm.h + description " + This package provides generic support for the ARM Cortex-M architecture. + It is also necessary to select a variant and platform HAL package." + + compile hal_misc.c context.S cortexm_stub.c + + requires { CYGHWR_HAL_CORTEXM_BIGENDIAN implies + is_substr(CYGBLD_GLOBAL_CFLAGS, " -mbig-endian ") && + is_substr(CYGBLD_GLOBAL_LDFLAGS, " -mbig-endian ") } + requires { !CYGHWR_HAL_CORTEXM_BIGENDIAN implies + !is_substr(CYGBLD_GLOBAL_CFLAGS, " -mbig-endian ") && + !is_substr(CYGBLD_GLOBAL_LDFLAGS, " -mbig-endian ") } + + make { + <PREFIX>/lib/vectors.o : <PACKAGE>/src/vectors.S + $(CC) -Wp,-MD,vectors.tmp $(INCLUDE_PATH) $(CFLAGS) -c -o $@ $< + @echo $@ ": \\" > $(notdir $@).deps + @tail -n +2 vectors.tmp >> $(notdir $@).deps + @echo >> $(notdir $@).deps + @rm vectors.tmp + } + + make { + <PREFIX>/lib/target.ld: <PACKAGE>/src/cortexm.ld + $(CC) -E -P -Wp,-MD,target.tmp -xc $(INCLUDE_PATH) $(CFLAGS) -o $@ $< + @echo $@ ": \\" > $(notdir $@).deps + @tail -n +2 target.tmp >> $(notdir $@).deps + @echo >> $(notdir $@).deps + @rm target.tmp + } + + cdl_interface CYGINT_HAL_CORTEXM_BIGENDIAN { + display "The platform and architecture supports Big Endian operation" + } + + cdl_option CYGHWR_HAL_CORTEXM_BIGENDIAN { + display "Use big-endian mode" + active_if { CYGINT_HAL_CORTEXM_BIGENDIAN != 0 } + default_value 0 + description " + Use the CPU in big-endian mode." + } + + cdl_option CYGHWR_HAL_CORTEXM { + display "Cortex-M CPU family" + flavor data + legal_values { "M1" "M3" } + default_value { "M3" } + description " + The Cortex-M architecture has two variants at present. The M1 is + base on the ARMV6 architecture specification and executes an extended + variant of the Thumb instruction set and has some differences in + the interrupt controller. The M3 is based on the ARMV7 architecture + specification and executes the Thumb2 instruction set." + } + + cdl_option CYGNUM_HAL_CORTEXM_PRIORITY_MAX { + display "Maximum usable priority" + flavor data + calculated 1<<(8-CYGNUM_HAL_CORTEXM_PRIORITY_LEVEL_BITS) + description " + Calculate the maximum exception priority that can be set by interrupts. + Higher priorities are reserved for the DEBUG and SVC traps." + } + + cdl_option CYGBLD_LINKER_SCRIPT { + display "Linker script" + flavor data + no_define + calculated { "src/cortexm.ld" } + } + + cdl_option CYGNUM_HAL_BREAKPOINT_LIST_SIZE { + display "Number of breakpoints supported by the HAL." + flavor data + default_value 8 + description " + This option determines the number of breakpoints supported by the HAL." + } +} + +# EOF hal_cortexm.cdl
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/include/basetype.h @@ -0,0 +1,69 @@ +#ifndef CYGONCE_HAL_BASETYPE_H +#define CYGONCE_HAL_BASETYPE_H +/*========================================================================== +// +// hal_intr.h +// +// Cortex-M standard types +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Description: Define architecture base types +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#define CYG_BYTEORDER CYG_LSBFIRST // Little endian +#define CYG_DOUBLE_BYTEORDER CYG_LSBFIRST + +//----------------------------------------------------------------------------- +// Cortex-M does not usually use labels with underscores. + +#define CYG_LABEL_NAME(_name_) _name_ +#define CYG_LABEL_DEFN(_name_) _name_ + +//----------------------------------------------------------------------------- +// Define the standard variable sizes + +// The ARM architecture uses the default definitions of the base +// types, so we do not need to define any here. + + +//========================================================================== +#endif // CYGONCE_HAL_BASETYPE_H +// End of basetype.h +
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/include/cortexm_stub.h @@ -0,0 +1,152 @@ +#ifndef CYGONCE_HAL_CORTEXM_STUB_H +#define CYGONCE_HAL_CORTEXM_STUB_H +/*========================================================================== +// +// cortexm_stub.h +// +// Cortex-M GDB stub support +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + + +#ifdef __cplusplus +extern "C" { +#endif + +// The ARM has float (and possibly other coprocessor) registers that are +// larger than it can hold in a target_register_t. +#define TARGET_HAS_LARGE_REGISTERS + +// ARM stub has special needs for register handling (not all regs are the +// the same size), so special put_register and get_register are provided. +#define CYGARC_STUB_REGISTER_ACCESS_DEFINED 1 + +#define NUMREGS (16+8+2) // 16 GPR, 8 FPR (unused), 2 PS + +#define REGSIZE( _x_ ) (((_x_) < F0 || (_x_) >= FPS) ? 4 : 12) + +// Comment out to allow for default gdb stub packet buffer which is larger. +// #define NUMREGBYTES ((16*4)+(8*12)+(2*4)) + +#ifndef TARGET_REGISTER_T_DEFINED +#define TARGET_REGISTER_T_DEFINED +typedef unsigned long target_register_t; +#endif + +enum regnames { + R0, R1, R2, R3, R4, R5, R6, R7, + R8, R9, R10, FP, IP, SP, LR, PC, + F0, F1, F2, F3, F4, F5, F6, F7, + FPS, PS +}; + +#define HAL_STUB_REGISTERS_SIZE \ + ((sizeof(HAL_CORTEXM_GDB_Registers) + sizeof(target_register_t) - 1) / sizeof(target_register_t)) + +#define PS_N 0x80000000 +#define PS_Z 0x40000000 +#define PS_C 0x20000000 +#define PS_V 0x10000000 + +typedef enum regnames regnames_t; + +//------------------------------------------------------------------------ + +/* Given a trap value TRAP, return the corresponding signal. */ +extern int __computeSignal (unsigned int trap_number); + +/* Return the trap number corresponding to the last-taken trap. */ +extern int __get_trap_number (void); + +/* Return the currently-saved value corresponding to register REG. */ +extern target_register_t get_register (regnames_t reg); + +/* Store VALUE in the register corresponding to WHICH. */ +extern void put_register (regnames_t which, target_register_t value); + +/* Set the currently-saved pc register value to PC. This also updates NPC + as needed. */ +extern void set_pc (target_register_t pc); + +/* Set things up so that the next user resume will execute one instruction. + This may be done by setting breakpoints or setting a single step flag + in the saved user registers, for example. */ +void __single_step (void); + +/* Clear the single-step state. */ +void __clear_single_step (void); + +/* If the breakpoint we hit is in the breakpoint() instruction, return a + non-zero value. */ +extern int __is_breakpoint_function (void); + +/* Skip the current instruction. */ +extern void __skipinst (void); + +extern void __install_breakpoints (void); + +extern void __clear_breakpoints (void); + +extern int __is_bsp_syscall(void); + +//------------------------------------------------------------------------ +// Special definition of CYG_HAL_GDB_ENTER_CRITICAL_IO_REGION + +#ifdef CYGDBG_HAL_DEBUG_GDB_BREAK_SUPPORT +// we can only do this at all if break support is enabled: + +// If this macro is used from Thumb code, we need to pass this information +// along to the place_break function so it can do the right thing. +#define CYG_HAL_GDB_ENTER_CRITICAL_IO_REGION( _old_ ) \ +do { \ + HAL_DISABLE_INTERRUPTS(_old_); \ + cyg_hal_gdb_place_break((target_register_t)((unsigned long)&&cyg_hal_gdb_break_place));\ +} while ( 0 ) + +#endif // CYGDBG_HAL_DEBUG_GDB_BREAK_SUPPORT + + +#ifdef __cplusplus +} /* extern "C" */ +#endif + +//========================================================================== +#endif // ifndef CYGONCE_HAL_CORTEXM_STUB_H
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/include/hal_arch.h @@ -0,0 +1,343 @@ +#ifndef CYGONCE_HAL_ARCH_H +#define CYGONCE_HAL_ARCH_H +/*========================================================================== +// +// hal_arch.h +// +// Cortex-M architecture abstractions +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Description: Define architecture abstractions +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/system.h> +#include <pkgconf/hal.h> +#include <cyg/infra/cyg_type.h> + +//========================================================================== +// CPU save state +// +// This is a discriminated union of different save states for threads, +// exceptions and interrupts. State is saved in the most efficient way +// for each context. This makes the GDB state get/put slightly more +// complex, but that is a suitable compromise. + +typedef struct +{ + union + { + cyg_uint32 type; // State type + + struct + { + cyg_uint32 type; // State type + cyg_uint32 basepri; // BASEPRI + cyg_uint32 sp; // SP (R13) + cyg_uint32 r[13]; // R0..R12 + cyg_uint32 pc; // PC/LR + } thread; + + struct + { + cyg_uint32 type; // State type + cyg_uint32 vector; // Exception vector number + cyg_uint32 basepri; // BASEPRI + + cyg_uint32 r4_11[8]; // Remaining CPU registers + cyg_uint32 xlr; // Exception return LR + + // The following are saved and restored automatically by the CPU + // for exceptions or interrupts. + + cyg_uint32 r0; + cyg_uint32 r1; + cyg_uint32 r2; + cyg_uint32 r3; + cyg_uint32 r12; + cyg_uint32 lr; + cyg_uint32 pc; + cyg_uint32 psr; + } exception; + + struct + { + cyg_uint32 type; // State type + + // The following are saved and restored automatically by the CPU + // for exceptions or interrupts. + + cyg_uint32 r0; + cyg_uint32 r1; + cyg_uint32 r2; + cyg_uint32 r3; + cyg_uint32 r12; + cyg_uint32 lr; + cyg_uint32 pc; + cyg_uint32 psr; + + } interrupt; + } u; + +} HAL_SavedRegisters; + +#define HAL_SAVEDREGISTERS_EXCEPTION 1 +#define HAL_SAVEDREGISTERS_THREAD 2 +#define HAL_SAVEDREGISTERS_INTERRUPT 3 + +//========================================================================== +// Thread context initialization + +#define HAL_THREAD_INIT_CONTEXT( __sparg, __thread, __entry, __id ) \ +{ \ + register CYG_WORD __sp = ((CYG_WORD)__sparg) & ~7; \ + register CYG_WORD *__ep = (CYG_WORD *)(__sp -= sizeof(CYG_WORD)); \ + register HAL_SavedRegisters *__regs; \ + int __i; \ + __sp = ((CYG_WORD)__sp) &~15; \ + __regs = (HAL_SavedRegisters *)((__sp) - sizeof(__regs->u.thread)); \ + __regs->u.type = HAL_SAVEDREGISTERS_THREAD; \ + for( __i = 1; __i < 13; __i++ ) \ + __regs->u.thread.r[__i] = 0; \ + *__ep = (CYG_WORD)(__entry); \ + __regs->u.thread.sp = (CYG_WORD)(__sp); \ + __regs->u.thread.r[0] = (CYG_WORD)(__thread); \ + __regs->u.thread.r[1] = (CYG_WORD)(__id); \ + __regs->u.thread.r[11] = (CYG_WORD)(__ep); \ + __regs->u.thread.pc = (CYG_WORD)__entry; \ + __regs->u.thread.basepri = 0; \ + __sparg = (CYG_ADDRESS)__regs; \ +} + +//========================================================================== +// Context switch macros. +// The arguments are pointers to locations where the stack pointer +// of the current thread is to be stored, and from where the SP of the +// next thread is to be fetched. + +__externC void hal_thread_switch_context( CYG_ADDRESS to, CYG_ADDRESS from ); +__externC void hal_thread_load_context( CYG_ADDRESS to ) __attribute__ ((noreturn)); + +#define HAL_THREAD_SWITCH_CONTEXT(__fspptr,__tspptr) \ + hal_thread_switch_context((CYG_ADDRESS)__tspptr, \ + (CYG_ADDRESS)__fspptr); + +#define HAL_THREAD_LOAD_CONTEXT(__tspptr) \ + hal_thread_load_context( (CYG_ADDRESS)__tspptr ); + + +//========================================================================== +// Fetch PC from saved state + +#define CYGARC_HAL_GET_PC_REG(__regs,__val) \ +{ \ + switch( (__regs)->u.type ) \ + { \ + case HAL_SAVEDREGISTERS_THREAD : (__val) = (__regs)->u.thread.pc; break; \ + case HAL_SAVEDREGISTERS_EXCEPTION: (__val) = (__regs)->u.exception.pc; break; \ + case HAL_SAVEDREGISTERS_INTERRUPT: (__val) = (__regs)->u.interrupt.pc; break; \ + } \ +} + +//========================================================================== +// Exception handling function +// This function is defined by the kernel according to this prototype. It is +// invoked from the HAL to deal with any CPU exceptions that the HAL does +// not want to deal with itself. It usually invokes the kernel's exception +// delivery mechanism. + +externC void cyg_hal_deliver_exception( CYG_WORD code, CYG_ADDRWORD data ); + +//========================================================================== +// Bit manipulation macros + +#define HAL_LSBIT_INDEX(__index, __mask) \ +{ \ + register cyg_uint32 __bit = (__mask); \ + register int __count; \ + __bit = __bit & -__bit; \ + __asm__ volatile ("clz %0,%1" : "=r"(__count) : "r"(__bit) ); \ + (__index) = 31-__count; \ +} + +#define HAL_MSBIT_INDEX(__index, __mask) \ +{ \ + register cyg_uint32 __bit = (__mask); \ + register int __count; \ + __asm__ volatile ("clz %0,%1" : "=r"(__count) : "r"(__bit) ); \ + (__index) = 31-__count; \ +} + +//========================================================================== +// Execution reorder barrier. +// When optimizing the compiler can reorder code. In multithreaded systems +// where the order of actions is vital, this can sometimes cause problems. +// This macro may be inserted into places where reordering should not happen. + +#define HAL_REORDER_BARRIER() asm volatile ( "" : : : "memory" ) + +//========================================================================== +// Breakpoint support +// HAL_BREAKPOINT() is a code sequence that will cause a breakpoint to happen +// if executed. +// HAL_BREAKINST is the value of the breakpoint instruction and +// HAL_BREAKINST_SIZE is its size in bytes. + +#define HAL_BREAKINST 0xbebe // BKPT + +# define HAL_BREAKINST_SIZE 2 +# define HAL_BREAKINST_TYPE cyg_uint16 + +#define _stringify1(__arg) #__arg +#define _stringify(__arg) _stringify1(__arg) + +# define HAL_BREAKPOINT(_label_) \ +__asm__ volatile (" .globl " #_label_ ";" \ + #_label_":" \ + " .short " _stringify(HAL_BREAKINST) \ + ); + +//========================================================================== +// GDB support + +// Register layout expected by GDB +typedef struct +{ + cyg_uint32 gpr[16]; + cyg_uint32 f0[3]; + cyg_uint32 f1[3]; + cyg_uint32 f2[3]; + cyg_uint32 f3[3]; + cyg_uint32 f4[3]; + cyg_uint32 f5[3]; + cyg_uint32 f6[3]; + cyg_uint32 f7[3]; + cyg_uint32 fps; + cyg_uint32 ps; +} HAL_CORTEXM_GDB_Registers; + +// Translate a stack pointer as saved by the thread context macros +// into a pointer to a HAL_SavedRegisters structure. On the Cortex-M +// these are equivalent. + +#define HAL_THREAD_GET_SAVED_REGISTERS(__stack, __regs) \ + CYG_MACRO_START \ + (__regs) = (HAL_SavedRegisters*)(__stack); \ + CYG_MACRO_END + + +__externC void hal_get_gdb_registers( HAL_CORTEXM_GDB_Registers *gdbreg, HAL_SavedRegisters *regs ); +__externC void hal_set_gdb_registers( HAL_CORTEXM_GDB_Registers *gdbreg, HAL_SavedRegisters *regs ); + +#define HAL_GET_GDB_REGISTERS(__regval, __regs) hal_get_gdb_registers( (HAL_CORTEXM_GDB_Registers *)(__regval), (HAL_SavedRegisters *)(__regs) ) +#define HAL_SET_GDB_REGISTERS(__regs, __regval) hal_set_gdb_registers( (HAL_CORTEXM_GDB_Registers *)(__regval), (HAL_SavedRegisters *)(__regs) ) + +//========================================================================== +// HAL setjmp + +#define CYGARC_JMP_BUF_SIZE 16 + +typedef cyg_uint32 hal_jmp_buf[CYGARC_JMP_BUF_SIZE]; + +__externC int hal_setjmp(hal_jmp_buf env); +__externC void hal_longjmp(hal_jmp_buf env, int val); + + +//========================================================================== +// Idle thread code. +// +// This macro is called in the idle thread loop, and gives the HAL the +// chance to insert code. Typical idle thread behaviour might be to halt the +// processor. Here we only supply a default fallback if the variant/platform +// doesn't define anything. + +#if 0 //ndef HAL_IDLE_THREAD_ACTION +#define HAL_IDLE_THREAD_ACTION(__count) __asm__ volatile ( "wfi\n" ) +#else +#define HAL_IDLE_THREAD_ACTION(__count) CYG_EMPTY_STATEMENT +#endif + +//========================================================================== +// Minimal and sensible stack sizes: the intention is that applications +// will use these to provide a stack size in the first instance prior to +// proper analysis. Idle thread stack should be this big. + +// THESE ARE NOT INTENDED TO BE MICROMETRICALLY ACCURATE FIGURES. +// THEY ARE HOWEVER ENOUGH TO START PROGRAMMING. +// YOU MUST MAKE YOUR STACKS LARGER IF YOU HAVE LARGE "AUTO" VARIABLES! + +// This is not a config option because it should not be adjusted except +// under "enough rope" sort of disclaimers. + +// A minimal, optimized stack frame - space for return link plus four +// arguments or local variables. +#define CYGNUM_HAL_STACK_FRAME_SIZE (4 * 20) + +// Stack needed for a context switch +#define CYGNUM_HAL_STACK_CONTEXT_SIZE (4 * 20) + +// Interrupt + call to ISR, interrupt_end() and the DSR +#define CYGNUM_HAL_STACK_INTERRUPT_SIZE \ + (CYGNUM_HAL_STACK_CONTEXT_SIZE + 2 * CYGNUM_HAL_STACK_FRAME_SIZE) + +// Space for the maximum number of nested interrupts, plus room to call functions +#define CYGNUM_HAL_MAX_INTERRUPT_NESTING 4 + +// Minimum stack size. Space for the given number of nested +// interrupts, plus a thread context switch plus a couple of function +// calls. +#define CYGNUM_HAL_STACK_SIZE_MINIMUM \ + ((CYGNUM_HAL_MAX_INTERRUPT_NESTING+1) * CYGNUM_HAL_STACK_INTERRUPT_SIZE + \ + 2 * CYGNUM_HAL_STACK_FRAME_SIZE) + +// Typical stack size -- used mainly for test programs. The minimum +// stack size plus enough space for some function calls. +#define CYGNUM_HAL_STACK_SIZE_TYPICAL \ + (CYGNUM_HAL_STACK_SIZE_MINIMUM + 32 * CYGNUM_HAL_STACK_FRAME_SIZE) + +//========================================================================== +// Macros for switching context between two eCos instances (jump from +// code in ROM to code in RAM or vice versa). + +#define CYGARC_HAL_SAVE_GP() +#define CYGARC_HAL_RESTORE_GP() + +//========================================================================== +#endif //CYGONCE_HAL_ARCH_H +
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/include/hal_intr.h @@ -0,0 +1,380 @@ +#ifndef CYGONCE_HAL_INTR_H +#define CYGONCE_HAL_INTR_H +/*========================================================================== +// +// hal_intr.h +// +// Cortex-M interrupt and clock abstractions +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Description: Define interrupt and clock abstractions +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/system.h> +#include <pkgconf/hal.h> + +#include <cyg/infra/cyg_type.h> + +#include <cyg/hal/hal_io.h> + +//========================================================================== +// Exception vectors +// +// These are the common vectors defined by all Cortex-M CPUs. The +// exact number of vectors is variant specific, so the limits will be +// defined in var_intr.h. + + +#define CYGNUM_HAL_VECTOR_STACK 0 // Reset stack pointer +#define CYGNUM_HAL_VECTOR_RESET 1 // Reset entry point +#define CYGNUM_HAL_VECTOR_NMI 2 // Non-Maskable Interrupt +#define CYGNUM_HAL_VECTOR_HARD_FAULT 3 // Hard fault +#define CYGNUM_HAL_VECTOR_MEMORY_MAN 4 // Memory management (M3) +#define CYGNUM_HAL_VECTOR_BUS_FAULT 5 // Bus Fault +#define CYGNUM_HAL_VECTOR_USAGE_FAULT 6 // Usage Fault +#define CYGNUM_HAL_VECTOR_RESERVED_07 7 +#define CYGNUM_HAL_VECTOR_RESERVED_08 8 +#define CYGNUM_HAL_VECTOR_RESERVED_09 9 +#define CYGNUM_HAL_VECTOR_RESERVED_10 10 +#define CYGNUM_HAL_VECTOR_SERVICE 11 // System service call +#define CYGNUM_HAL_VECTOR_DEBUG 12 // Debug monitor (M3) +#define CYGNUM_HAL_VECTOR_RESERVED_13 13 +#define CYGNUM_HAL_VECTOR_PENDSV 14 // Pendable svc request +#define CYGNUM_HAL_VECTOR_SYS_TICK 15 // System timer tick +#define CYGNUM_HAL_VECTOR_EXTERNAL 16 // Base of external interrupts + + +//========================================================================== +// Interrupt vectors +// +// The system tick interrupt is mapped to vector 0 and all external +// interrupts are mapped from vector 1 up. + +#define CYGNUM_HAL_INTERRUPT_SYS_TICK 0 +#define CYGNUM_HAL_INTERRUPT_EXTERNAL 1 + +#define CYGNUM_HAL_INTERRUPT_RTC CYGNUM_HAL_INTERRUPT_SYS_TICK + +//========================================================================== +// Include variant definitions here. + +#include <cyg/hal/var_intr.h> + +//========================================================================== +// Exception vectors. +// +// These are the values used when passed out to an external exception +// handler using cyg_hal_deliver_exception() + +#define CYGNUM_HAL_EXCEPTION_DATA_TLBMISS_ACCESS CYGNUM_HAL_VECTOR_MEMORY_MAN +#define CYGNUM_HAL_EXCEPTION_CODE_TLBMISS_ACCESS CYGNUM_HAL_VECTOR_MEMORY_MAN +#define CYGNUM_HAL_EXCEPTION_DATA_ACCESS CYGNUM_HAL_VECTOR_BUS_FAULT +#define CYGNUM_HAL_EXCEPTION_CODE_ACCESS CYGNUM_HAL_VECTOR_BUS_FAULT +#define CYGNUM_HAL_EXCEPTION_ILLEGAL_INSTRUCTION CYGNUM_HAL_VECTOR_USAGE_FAULT +#define CYGNUM_HAL_EXCEPTION_DATA_UNALIGNED_ACCESS CYGNUM_HAL_VECTOR_USAGE_FAULT +#define CYGNUM_HAL_EXCEPTION_INTERRUPT CYGNUM_HAL_VECTOR_SERVICE + + +#define CYGNUM_HAL_EXCEPTION_MIN CYGNUM_HAL_EXCEPTION_DATA_UNALIGNED_ACCESS +#define CYGNUM_HAL_EXCEPTION_MAX CYGNUM_HAL_EXCEPTION_INTERRUPT +#define CYGNUM_HAL_EXCEPTION_COUNT (CYGNUM_HAL_EXCEPTION_MAX - \ + CYGNUM_HAL_EXCEPTION_MIN + 1) + + +//========================================================================== +// VSR handling + +__externC volatile CYG_ADDRESS hal_vsr_table[CYGNUM_HAL_VSR_COUNT]; + +#ifndef HAL_VSR_GET +#define HAL_VSR_GET( __vector, __pvsr ) \ + *(CYG_ADDRESS *)(__pvsr) = hal_vsr_table[__vector]; +#endif + +#ifndef HAL_VSR_SET +#define HAL_VSR_SET( __vector, __vsr, __poldvsr ) \ +CYG_MACRO_START \ + if( __poldvsr != NULL ) \ + *(CYG_ADDRESS *)__poldvsr = hal_vsr_table[__vector]; \ + hal_vsr_table[__vector] = (CYG_ADDRESS)__vsr; \ +CYG_MACRO_END +#endif + +#ifndef HAL_VSR_SET_TO_ECOS_HANDLER +__externC void hal_default_interrupt_vsr( void ); +__externC void hal_default_exception_vsr( void ); +# define HAL_VSR_SET_TO_ECOS_HANDLER( __vector, __poldvsr ) \ +CYG_MACRO_START \ + cyg_uint32 __vector2 = (cyg_uint32) (__vector); \ + CYG_ADDRESS* __poldvsr2 = (CYG_ADDRESS*)(__poldvsr); \ + if( __vector2 < CYGNUM_HAL_VECTOR_SYS_TICK ) \ + HAL_VSR_SET(__vector2, &hal_default_exception_vsr, __poldvsr2); \ + else \ + HAL_VSR_SET(__vector2, &hal_default_interrupt_vsr, __poldvsr2); \ +CYG_MACRO_END +#endif + +// Default definition of HAL_TRANSLATE_VECTOR(), a no-op +#ifndef HAL_TRANSLATE_VECTOR +# define HAL_TRANSLATE_VECTOR(__vector, __index) ((__index) = (__vector)) +#endif + +//========================================================================== +// ISR handling +// +// Interrupt handler/data/object tables plus functions and macros to +// manipulate them. + +__externC volatile CYG_ADDRESS hal_interrupt_handlers[CYGNUM_HAL_ISR_COUNT]; +__externC volatile CYG_ADDRWORD hal_interrupt_data [CYGNUM_HAL_ISR_COUNT]; +__externC volatile CYG_ADDRESS hal_interrupt_objects [CYGNUM_HAL_ISR_COUNT]; + +//-------------------------------------------------------------------------- +// Interrupt delivery +// +// This function is used by the HAL to deliver an interrupt, and post +// a DSR if required. It may also be used to deliver secondary +// interrupts from springboard ISRs. + +__externC void hal_deliver_interrupt( cyg_uint32 vector ); + +//-------------------------------------------------------------------------- +// Default ISR The #define is used to test whether this routine +// exists, and to allow code outside the HAL to call it. + +externC cyg_uint32 hal_default_isr(CYG_ADDRWORD vector, CYG_ADDRWORD data); +#define HAL_DEFAULT_ISR hal_default_isr + +//-------------------------------------------------------------------------- + +#define HAL_INTERRUPT_IN_USE( _vector_, _state_) \ +{ \ + cyg_uint32 _index_; \ + HAL_TRANSLATE_VECTOR ((_vector_), _index_); \ + \ + if( hal_interrupt_handlers[_index_] == (CYG_ADDRESS)hal_default_isr ) \ + (_state_) = 0; \ + else \ + (_state_) = 1; \ +} + +#define HAL_INTERRUPT_ATTACH( _vector_, _isr_, _data_, _object_ ) \ +{ \ + if( hal_interrupt_handlers[_vector_] == (CYG_ADDRESS)hal_default_isr ) \ + { \ + hal_interrupt_handlers[_vector_] = (CYG_ADDRESS)_isr_; \ + hal_interrupt_data[_vector_] = (CYG_ADDRWORD) _data_; \ + hal_interrupt_objects[_vector_] = (CYG_ADDRESS)_object_; \ + } \ +} + +#define HAL_INTERRUPT_DETACH( _vector_, _isr_ ) \ +{ \ + if( hal_interrupt_handlers[_vector_] == (CYG_ADDRESS)_isr_ ) \ + { \ + hal_interrupt_handlers[_vector_] = (CYG_ADDRESS)hal_default_isr; \ + hal_interrupt_data[_vector_] = 0; \ + hal_interrupt_objects[_vector_] = 0; \ + } \ +} + +//-------------------------------------------------------------------------- +// CPU interrupt control. +// +// We use the BASEPRI register to control delivery of interrupts. The +// register is set to the second highest implemented priority for this +// Cortex-M implementation to mask interrupts. It is set to zero to +// enable interrupts, which will disable the BASEPRI mechanism. + +#ifndef __ASSEMBLER__ +typedef cyg_uint32 CYG_INTERRUPT_STATE; +#endif + +#ifndef HAL_DISABLE_INTERRUPTS +# define HAL_DISABLE_INTERRUPTS(__old) \ + __asm__ volatile ( \ + "mrs %0, basepri \n" \ + "mov r1,%1 \n" \ + "msr basepri,r1 \n" \ + : "=r" (__old) \ + : "r" (CYGNUM_HAL_CORTEXM_PRIORITY_MAX)\ + : "r1" \ + ); +#endif + +#ifndef HAL_RESTORE_INTERRUPTS +# define HAL_RESTORE_INTERRUPTS(__old) \ + __asm__ volatile ( \ + "msr basepri, %0 \n" \ + : \ + : "r" (__old) \ + ); +#endif + +#ifndef HAL_ENABLE_INTERRUPTS +# define HAL_ENABLE_INTERRUPTS() \ + __asm__ volatile ( \ + "mov r1,#0 \n" \ + "msr basepri,r1 \n" \ + : \ + : \ + : "r1" \ + ); +#endif + +#ifndef HAL_QUERY_INTERRUPTS +#define HAL_QUERY_INTERRUPTS(__state) \ + __asm__ volatile ( \ + "mrs %0, basepri \n" \ + : "=r" (__state) \ + ); +#endif + +//-------------------------------------------------------------------------- +// Interrupt masking and unmasking +// +// This is mostly done via the architecture defined NVIC. The +// HAL_VAR_*() macros allow the variant HAL to provide extended +// support for additional interrupt sources supported by supplementary +// interrupt controllers. + +__externC void hal_interrupt_mask( cyg_uint32 vector ); +__externC void hal_interrupt_unmask( cyg_uint32 vector ); +__externC void hal_interrupt_set_level( cyg_uint32 vector, cyg_uint32 level ); +__externC void hal_interrupt_acknowledge( cyg_uint32 vector ); +__externC void hal_interrupt_configure( cyg_uint32 vector, cyg_uint32 level, cyg_uint32 up ); + + +#define HAL_INTERRUPT_MASK( __vector ) hal_interrupt_mask( __vector ) +#define HAL_INTERRUPT_UNMASK( __vector ) hal_interrupt_unmask( __vector ) +#define HAL_INTERRUPT_SET_LEVEL( __vector, __level ) hal_interrupt_set_level( __vector, __level ) +#define HAL_INTERRUPT_ACKNOWLEDGE( __vector ) hal_interrupt_acknowledge( __vector ) +#define HAL_INTERRUPT_CONFIGURE( __vector, __level, __up ) hal_interrupt_configure( __vector, __level, __up ) + +//-------------------------------------------------------------------------- +// Routine to execute DSRs using separate interrupt stack + +__externC void hal_call_dsrs_vsr(void); +#define HAL_INTERRUPT_STACK_CALL_PENDING_DSRS() \ +{ \ + __asm__ volatile ( \ + "ldr r3,=hal_call_dsrs_vsr \n" \ + "swi \n" \ + : \ + : \ + : "r3" \ + ); \ +} + +//-------------------------------------------------------------------------- + +#if 0 +// these are offered solely for stack usage testing +// if they are not defined, then there is no interrupt stack. +#define HAL_INTERRUPT_STACK_BASE cyg_interrupt_stack_base +#define HAL_INTERRUPT_STACK_TOP cyg_interrupt_stack +// use them to declare these extern however you want: +// extern char HAL_INTERRUPT_STACK_BASE[]; +// extern char HAL_INTERRUPT_STACK_TOP[]; +// is recommended +#endif + +//========================================================================== +// Clock control +// +// This uses the CPU SysTick timer. + +__externC cyg_uint32 hal_cortexm_systick_clock; + +#define HAL_CLOCK_INITIALIZE( __period ) \ +{ \ + cyg_uint32 __p = __period; \ + __p = hal_cortexm_systick_clock / ( 1000000 / __p ); \ + HAL_WRITE_UINT32(CYGARC_REG_SYSTICK_BASE+CYGARC_REG_SYSTICK_RELOAD, \ + __p ); \ + HAL_WRITE_UINT32(CYGARC_REG_SYSTICK_BASE+CYGARC_REG_SYSTICK_CSR, \ + CYGARC_REG_SYSTICK_CSR_ENABLE | \ + CYGARC_REG_SYSTICK_CSR_CLK_EXT ); \ +} + +#define HAL_CLOCK_RESET( __vector, __period ) \ +{ \ + cyg_uint32 __csr; \ + HAL_READ_UINT32(CYGARC_REG_SYSTICK_BASE+CYGARC_REG_SYSTICK_CSR, __csr ); \ +} + +#define HAL_CLOCK_READ( __pvalue ) \ +{ \ + cyg_uint32 __period, __value; \ + HAL_READ_UINT32(CYGARC_REG_SYSTICK_BASE+CYGARC_REG_SYSTICK_RELOAD, __period ); \ + HAL_READ_UINT32(CYGARC_REG_SYSTICK_BASE+CYGARC_REG_SYSTICK_VALUE, __value ); \ + __value = __period - __value; \ + __value /= (hal_cortexm_systick_clock/ 1000000 ); \ + *(__pvalue) = __value; \ +} + +#define HAL_CLOCK_LATENCY( __pvalue ) HAL_CLOCK_READ( __pvalue ) + +//========================================================================== +// HAL_DELAY_US(). +// + +__externC void hal_delay_us( cyg_int32 us ); +#define HAL_DELAY_US( __us ) hal_delay_us( __us ) + +//========================================================================== +// Reset. +// +// This uses the SYSRESETREQ bit in the Cortex-M3 NVIC. + +#define HAL_PLATFORM_RESET() \ +{ \ + HAL_WRITE_UINT32(CYGARC_REG_SYSTICK_BASE+CYGARC_REG_NVIC_AIRCR, \ + CYGARC_REG_NVIC_AIRCR_KEY| \ + CYGARC_REG_NVIC_AIRCR_SYSRESETREQ ); \ + for(;;); \ +} + +__externC void hal_reset_vsr( void ); +#define HAL_PLATFORM_RESET_ENTRY &hal_reset_vsr + +//========================================================================== +#endif //CYGONCE_HAL_INTR_H +
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/include/hal_io.h @@ -0,0 +1,396 @@ +#ifndef CYGONCE_HAL_IO_H +#define CYGONCE_HAL_IO_H +/*========================================================================== +// +// hal_io.h +// +// Cortex-M architecture IO register definitions +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Description: Define IO registers +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/system.h> +#include <pkgconf/hal.h> + +#include <cyg/infra/cyg_type.h> + +#include <cyg/hal/var_io.h> + +//========================================================================== +// Handy macros for defining register bits and fields: +// + +#define BIT_(__n) (1<<(__n)) +#define MASK_(__n,__s) (((1<<((__s)+1))-1)<<(__n)) +#define VALUE_(__n,__v) ((__v)<<(__n)) + +//========================================================================== +// SysTick timer +// +// This is really part of the NVIC, but we break it out into a +// separate definition for convenience. + +#define CYGARC_REG_SYSTICK_BASE 0xE000E010 + +#define CYGARC_REG_SYSTICK_CSR 0 +#define CYGARC_REG_SYSTICK_RELOAD 4 +#define CYGARC_REG_SYSTICK_VALUE 8 +#define CYGARC_REG_SYSTICK_CAL 12 + +#define CYGARC_REG_SYSTICK_CSR_COUNTFLAG BIT_(16) +#define CYGARC_REG_SYSTICK_CSR_CLK_EXT VALUE_(2,0) +#define CYGARC_REG_SYSTICK_CSR_CLK_INT VALUE_(2,1) +#define CYGARC_REG_SYSTICK_CSR_TICKINT BIT_(1) +#define CYGARC_REG_SYSTICK_CSR_ENABLE BIT_(0) + +#define CYGARC_REG_SYSTICK_CAL_NOREF BIT_(31) +#define CYGARC_REG_SYSTICK_CAL_SKEW BIT_(30) +#define CYGARC_REG_SYSTICK_CAL_TENMS MASK_(0,23) + +//========================================================================== +// NVIC registers + +#define CYGARC_REG_NVIC_BASE 0xE000E000 + +#if defined(CYGHWR_HAL_CORTEXM_M3) +#define CYGARC_REG_NVIC_TYPE 0x004 +#endif + +#define CYGARC_REG_NVIC_SER0 0x100 +#define CYGARC_REG_NVIC_CER0 0x180 +#define CYGARC_REG_NVIC_SPR0 0x200 +#define CYGARC_REG_NVIC_CPR0 0x280 +#define CYGARC_REG_NVIC_ABR0 0x300 +#define CYGARC_REG_NVIC_PR0 0x400 + +// Generate address of 32 bit control register for interrupt +#define CYGARC_REG_NVIC_SER(__intr) (CYGARC_REG_NVIC_SER0+4*((__intr)>>5)) +#define CYGARC_REG_NVIC_CER(__intr) (CYGARC_REG_NVIC_CER0+4*((__intr)>>5)) +#define CYGARC_REG_NVIC_SPR(__intr) (CYGARC_REG_NVIC_SPR0+4*((__intr)>>5)) +#define CYGARC_REG_NVIC_CPR(__intr) (CYGARC_REG_NVIC_CPR0+4*((__intr)>>5)) +#define CYGARC_REG_NVIC_ABR(__intr) (CYGARC_REG_NVIC_ABR0+4*((__intr)>>5)) + +// Generate bit in register for interrupt +#define CYGARC_REG_NVIC_IBIT(__intr) BIT_((__intr)&0x1F) + +// Generate byte address of interrupt's priority register. +#define CYGARC_REG_NVIC_PR(__intr) (CYGARC_REG_NVIC_PR0+(__intr)) + + +#if defined(CYGHWR_HAL_CORTEXM_M3) + +#define CYGARC_REG_NVIC_CPUID 0xD00 +#define CYGARC_REG_NVIC_ICSR 0xD04 +#define CYGARC_REG_NVIC_VTOR 0xD08 +#define CYGARC_REG_NVIC_AIRCR 0xD0C +#define CYGARC_REG_NVIC_SCR 0xD10 +#define CYGARC_REG_NVIC_CCR 0xD14 +#define CYGARC_REG_NVIC_SHPR0 0xD18 +#define CYGARC_REG_NVIC_SHPR1 0xD1C +#define CYGARC_REG_NVIC_SHPR2 0xD20 +#define CYGARC_REG_NVIC_SHCSR 0xD24 +#define CYGARC_REG_NVIC_CFSR 0xD28 +#define CYGARC_REG_NVIC_HFSR 0xD2C +#define CYGARC_REG_NVIC_DFSR 0xD30 +#define CYGARC_REG_NVIC_MMAR 0xD34 +#define CYGARC_REG_NVIC_BFAR 0xD38 +#define CYGARC_REG_NVIC_AFSR 0xD3C +#define CYGARC_REG_NVIC_PFR0 0xD40 +#define CYGARC_REG_NVIC_PFR1 0xD44 +#define CYGARC_REG_NVIC_DFR0 0xD48 +#define CYGARC_REG_NVIC_AFR0 0xD4C +#define CYGARC_REG_NVIC_MMFR0 0xD50 +#define CYGARC_REG_NVIC_MMFR1 0xD54 +#define CYGARC_REG_NVIC_MMFR2 0xD58 +#define CYGARC_REG_NVIC_MMFR3 0xD5C +#define CYGARC_REG_NVIC_ISAR0 0xD60 +#define CYGARC_REG_NVIC_ISAR1 0xD64 +#define CYGARC_REG_NVIC_ISAR2 0xD68 +#define CYGARC_REG_NVIC_ISAR3 0xD6C +#define CYGARC_REG_NVIC_ISAR4 0xD70 +#define CYGARC_REG_NVIC_STIR 0xF00 +#define CYGARC_REG_NVIC_PID4 0xFD0 +#define CYGARC_REG_NVIC_PID5 0xFD4 +#define CYGARC_REG_NVIC_PID6 0xFD8 +#define CYGARC_REG_NVIC_PID7 0xFDC +#define CYGARC_REG_NVIC_PID0 0xFE0 +#define CYGARC_REG_NVIC_PID1 0xFE4 +#define CYGARC_REG_NVIC_PID2 0xFE8 +#define CYGARC_REG_NVIC_PID3 0xFEC +#define CYGARC_REG_NVIC_CID0 0xFF0 +#define CYGARC_REG_NVIC_CID1 0xFF4 +#define CYGARC_REG_NVIC_CID2 0xFF8 +#define CYGARC_REG_NVIC_CID3 0xFFC + +// ICSR + +#define CYGARC_REG_NVIC_ICSR_NMIPENDSET BIT_(31) +#define CYGARC_REG_NVIC_ICSR_PENDSVSET BIT_(28) +#define CYGARC_REG_NVIC_ICSR_PENDSVCLR BIT_(27) +#define CYGARC_REG_NVIC_ICSR_PENDSTSET BIT_(26) +#define CYGARC_REG_NVIC_ICSR_PENDSTCLR BIT_(25) +#define CYGARC_REG_NVIC_ICSR_ISRPREEMPT BIT_(23) +#define CYGARC_REG_NVIC_ICSR_ISRPENDING BIT_(22) +#define CYGARC_REG_NVIC_ICSR_VECTPENDING MASK_(12,9) +#define CYGARC_REG_NVIC_ICSR_RETTOBASE BIT_(11) +#define CYGARC_REG_NVIC_ICSR_VECTACTIVE MASK_(0,9) + +// VTOR + +#define CYGARC_REG_NVIC_VTOR_TBLOFF(__o) VALUE_(7,__o) +#define CYGARC_REG_NVIC_VTOR_TBLBASE_CODE 0 +#define CYGARC_REG_NVIC_VTOR_TBLBASE_SRAM BIT_(29) + +// AI/RCR + +#define CYGARC_REG_NVIC_AIRCR_KEY VALUE_(16,0x5FA) +#define CYGARC_REG_NVIC_AIRCR_BIGENDIAN BIT_(15) +#define CYGARC_REG_NVIC_AIRCR_PRIGROUP(__p) VALUE_(8,__p) +#define CYGARC_REG_NVIC_AIRCR_SYSRESETREQ BIT_(2) +#define CYGARC_REG_NVIC_AIRCR_VECTCLRACTIVE BIT_(1) +#define CYGARC_REG_NVIC_AIRCR_VECTRESET BIT_(0) + +// SHCSR + +#define CYGARC_REG_NVIC_SHCSR_USGFAULTENA BIT_(18) +#define CYGARC_REG_NVIC_SHCSR_BUSFAULTENA BIT_(17) +#define CYGARC_REG_NVIC_SHCSR_MEMFAULTENA BIT_(16) +#define CYGARC_REG_NVIC_SHCSR_SVCALLPENDED BIT_(15) +#define CYGARC_REG_NVIC_SHCSR_BUSFAULTPENDED BIT_(14) +#define CYGARC_REG_NVIC_SHCSR_MEMFAULTPENDED BIT_(13) +#define CYGARC_REG_NVIC_SHCSR_USGFAULTPENDED BIT_(12) +#define CYGARC_REG_NVIC_SHCSR_SYSTICKACT BIT_(11) +#define CYGARC_REG_NVIC_SHCSR_PENDSVACT BIT_(10) +#define CYGARC_REG_NVIC_SHCSR_MONITORACT BIT_(8) +#define CYGARC_REG_NVIC_SHCSR_SVCALLACT BIT_(7) +#define CYGARC_REG_NVIC_SHCSR_USGFAULTACT BIT_(3) +#define CYGARC_REG_NVIC_SHCSR_BUSFAULTACT BIT_(1) +#define CYGARC_REG_NVIC_SHCSR_MEMFAULTACT BIT_(0) + +#endif + +//========================================================================== +// Debug registers + +#if defined(CYGHWR_HAL_CORTEXM_M3) + +#define CYGARC_REG_DEBUG_BASE 0xE000EDF0 + +#define CYGARC_REG_DEBUG_DHSR 0x00 +#define CYGARC_REG_DEBUG_DCRSR 0x04 +#define CYGARC_REG_DEBUG_DCRDR 0x08 +#define CYGARC_REG_DEBUG_DEMCR 0x0C + + +#define CYGARC_REG_DEBUG_DHSR_DBGKEY VALUE_(16,0xA05F) +#define CYGARC_REG_DEBUG_DHSR_S_RESET BIT_(25) +#define CYGARC_REG_DEBUG_DHSR_S_RETIRE BIT_(24) +#define CYGARC_REG_DEBUG_DHSR_S_LOCKUP BIT_(19) +#define CYGARC_REG_DEBUG_DHSR_S_SLEEP BIT_(18) +#define CYGARC_REG_DEBUG_DHSR_S_HALT BIT_(17) +#define CYGARC_REG_DEBUG_DHSR_S_REGRDY BIT_(16) +#define CYGARC_REG_DEBUG_DHSR_C_SNAPSTALL BIT_(5) +#define CYGARC_REG_DEBUG_DHSR_C_MASKINTS BIT_(3) +#define CYGARC_REG_DEBUG_DHSR_C_STEP BIT_(2) +#define CYGARC_REG_DEBUG_DHSR_C_HALT BIT_(1) +#define CYGARC_REG_DEBUG_DHSR_C_DEBUGEN BIT_(0) + + +#define CYGARC_REG_DEBUG_DCRSR_REG_WRITE BIT_(16) +#define CYGARC_REG_DEBUG_DCRSR_REG_READ 0 +#define CYGARC_REG_DEBUG_DCRSR_REG(__x) VALUE_(0,__x) + + +#define CYGARC_REG_DEBUG_DEMCR_TRCENA BIT_(24) +#define CYGARC_REG_DEBUG_DEMCR_MON_REQ BIT_(19) +#define CYGARC_REG_DEBUG_DEMCR_MON_STEP BIT_(18) +#define CYGARC_REG_DEBUG_DEMCR_MON_PEND BIT_(17) +#define CYGARC_REG_DEBUG_DEMCR_MON_EN BIT_(16) +#define CYGARC_REG_DEBUG_DEMCR_VC_HARDERR BIT_(10) +#define CYGARC_REG_DEBUG_DEMCR_VC_INTERR BIT_(9) +#define CYGARC_REG_DEBUG_DEMCR_VC_BUSERR BIT_(8) +#define CYGARC_REG_DEBUG_DEMCR_VC_STATERR BIT_(7) +#define CYGARC_REG_DEBUG_DEMCR_VC_CHKERR BIT_(6) +#define CYGARC_REG_DEBUG_DEMCR_VC_NOCPERR BIT_(5) +#define CYGARC_REG_DEBUG_DEMCR_VC_MMERR BIT_(4) +#define CYGARC_REG_DEBUG_DEMCR_VC_CORERESET BIT_(0) + +#endif + +//========================================================================== +// IO Register address. +// This type is for recording the address of an IO register. + +typedef volatile CYG_ADDRWORD HAL_IO_REGISTER; + +//----------------------------------------------------------------------------- +// HAL IO macros. + +#ifndef HAL_IO_MACROS_DEFINED + +//----------------------------------------------------------------------------- +// BYTE Register access. +// Individual and vectorized access to 8 bit registers. + + +#define HAL_READ_UINT8( _register_, _value_ ) \ + ((_value_) = *((volatile CYG_BYTE *)(_register_))) + +#define HAL_WRITE_UINT8( _register_, _value_ ) \ + (*((volatile CYG_BYTE *)(_register_)) = (_value_)) + +#define HAL_READ_UINT8_VECTOR( _register_, _buf_, _count_, _step_ ) \ + CYG_MACRO_START \ + cyg_count32 _i_,_j_; \ + for( _i_ = 0, _j_ = 0; _i_ < (_count_); _i_++, _j_ += (_step_)) \ + (_buf_)[_i_] = ((volatile CYG_BYTE *)(_register_))[_j_]; \ + CYG_MACRO_END + +#define HAL_WRITE_UINT8_VECTOR( _register_, _buf_, _count_, _step_ ) \ + CYG_MACRO_START \ + cyg_count32 _i_,_j_; \ + for( _i_ = 0, _j_ = 0; _i_ < (_count_); _i_++, _j_ += (_step_)) \ + ((volatile CYG_BYTE *)(_register_))[_j_] = (_buf_)[_i_]; \ + CYG_MACRO_END + +#define HAL_READ_UINT8_STRING( _register_, _buf_, _count_ ) \ + CYG_MACRO_START \ + cyg_count32 _i_; \ + for( _i_ = 0; _i_ < (_count_); _i_++) \ + (_buf_)[_i_] = ((volatile CYG_BYTE *)(_register_))[_i_]; \ + CYG_MACRO_END + +#define HAL_WRITE_UINT8_STRING( _register_, _buf_, _count_ ) \ + CYG_MACRO_START \ + cyg_count32 _i_; \ + for( _i_ = 0; _i_ < (_count_); _i_++) \ + ((volatile CYG_BYTE *)(_register_)) = (_buf_)[_i_]; \ + CYG_MACRO_END + +//----------------------------------------------------------------------------- +// 16 bit access. +// Individual and vectorized access to 16 bit registers. + + +#define HAL_READ_UINT16( _register_, _value_ ) \ + ((_value_) = *((volatile CYG_WORD16 *)(_register_))) + +#define HAL_WRITE_UINT16( _register_, _value_ ) \ + (*((volatile CYG_WORD16 *)(_register_)) = (_value_)) + +#define HAL_READ_UINT16_VECTOR( _register_, _buf_, _count_, _step_ ) \ + CYG_MACRO_START \ + cyg_count32 _i_,_j_; \ + for( _i_ = 0, _j_ = 0; _i_ < (_count_); _i_++, _j_ += (_step_)) \ + (_buf_)[_i_] = ((volatile CYG_WORD16 *)(_register_))[_j_]; \ + CYG_MACRO_END + +#define HAL_WRITE_UINT16_VECTOR( _register_, _buf_, _count_, _step_ ) \ + CYG_MACRO_START \ + cyg_count32 _i_,_j_; \ + for( _i_ = 0, _j_ = 0; _i_ < (_count_); _i_++, _j_ += (_step_)) \ + ((volatile CYG_WORD16 *)(_register_))[_j_] = (_buf_)[_i_]; \ + CYG_MACRO_END + +#define HAL_READ_UINT16_STRING( _register_, _buf_, _count_) \ + CYG_MACRO_START \ + cyg_count32 _i_; \ + for( _i_ = 0; _i_ < (_count_); _i_++) \ + (_buf_)[_i_] = ((volatile CYG_WORD16 *)(_register_))[_i_]; \ + CYG_MACRO_END + +#define HAL_WRITE_UINT16_STRING( _register_, _buf_, _count_) \ + CYG_MACRO_START \ + cyg_count32 _i_; \ + for( _i_ = 0; _i_ < (_count_); _i_++) \ + ((volatile CYG_WORD16 *)(_register_))[_i_] = (_buf_)[_i_]; \ + CYG_MACRO_END + +//----------------------------------------------------------------------------- +// 32 bit access. +// Individual and vectorized access to 32 bit registers. + +#define HAL_READ_UINT32( _register_, _value_ ) \ + ((_value_) = *((volatile CYG_WORD32 *)(_register_))) + +#define HAL_WRITE_UINT32( _register_, _value_ ) \ + (*((volatile CYG_WORD32 *)(_register_)) = (_value_)) + +#define HAL_READ_UINT32_VECTOR( _register_, _buf_, _count_, _step_ ) \ + CYG_MACRO_START \ + cyg_count32 _i_,_j_; \ + for( _i_ = 0, _j_ = 0; _i_ < (_count_); _i_++, _j_ += (_step_)) \ + (_buf_)[_i_] = ((volatile CYG_WORD32 *)(_register_))[_j_]; \ + CYG_MACRO_END + +#define HAL_WRITE_UINT32_VECTOR( _register_, _buf_, _count_, _step_ ) \ + CYG_MACRO_START \ + cyg_count32 _i_,_j_; \ + for( _i_ = 0, _j_ = 0; _i_ < (_count_); _i_++, _j_ += (_step_)) \ + ((volatile CYG_WORD32 *)(_register_))[_j_] = (_buf_)[_i_]; \ + CYG_MACRO_END + +#define HAL_READ_UINT32_STRING( _register_, _buf_, _count_) \ + CYG_MACRO_START \ + cyg_count32 _i_; \ + for( _i_ = 0; _i_ < (_count_); _i_++) \ + (_buf_)[_i_] = ((volatile CYG_WORD32 *)(_register_))[_i_]; \ + CYG_MACRO_END + +#define HAL_WRITE_UINT32_STRING( _register_, _buf_, _count_) \ + CYG_MACRO_START \ + cyg_count32 _i_; \ + for( _i_ = 0; _i_ < (_count_); _i_++) \ + ((volatile CYG_WORD32 *)(_register_))[_i_] = (_buf_)[_i_]; \ + CYG_MACRO_END + + +#define HAL_IO_MACROS_DEFINED + +#endif // !HAL_IO_MACROS_DEFINED + +// Enforce a flow "barrier" to prevent optimizing compiler from reordering +// operations. +#define HAL_IO_BARRIER() + + +//========================================================================== +#endif //CYGONCE_HAL_IO_H
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/src/context.S @@ -0,0 +1,129 @@ +/*========================================================================== +// +// context.S +// +// Cortex-M context switch code +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Description: This file contains thread context switch code. +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/system.h> +#include <pkgconf/hal.h> +#include <pkgconf/hal_cortexm.h> +#ifdef CYGPKG_KERNEL +#include <pkgconf/kernel.h> +#endif + +//========================================================================== + + .syntax unified + .thumb + .text + +//========================================================================== +// Context switch +// +// R0 contains a pointer to the SP of the thread to load, R1 contains +// a pointer to the SP of the current thread. + + .globl hal_thread_switch_context + .thumb + .thumb_func + .type hal_thread_switch_context, %function +hal_thread_switch_context: + + push {r0-r12,lr} // Push all savable register + mov r2,#2 // Set state type == thread + mrs r3,basepri // Get priority base register + mov r4,sp // Get SP (for info only) + push {r2-r4} // Push them + + str sp,[r1] // Save SP + + // Fall through + +//-------------------------------------------------------------------------- +// Load context +// +// This is used to load a thread context, abandoning the current one. This +// function is also the second half of hal_thread_switch_context. + + .globl hal_thread_load_context + .thumb + .thumb_func + .type hal_thread_load_context, %function +hal_thread_load_context: + + ldr sp,[r0] // Load SP + pop {r2-r4} // Pop type, basepri and SP (discarded) + msr basepri,r3 // Set BASEPRI + pop {r0-r12,pc} // Pop all register and return + +//========================================================================== +// HAL longjmp, setjmp implementations +// +// hal_setjmp saves only to callee save registers R4-14 +// and LR into buffer supplied in r0[arg0]. + + .globl hal_setjmp + .thumb + .thumb_func + .type hal_setjmp, %function +hal_setjmp: + mov r3,sp + stmea r0,{r3-r12,r14} + mov r0,#0 + bx lr + +// hal_longjmp loads state from r0[arg0] and returns + + .globl hal_longjmp + .thumb + .thumb_func + .type hal_longjmp, %function +hal_longjmp: + ldmfd r0,{r3-r12,r14} + mov sp,r3 + mov r0,r1 // return [arg1] + bx lr + +//========================================================================== +// EOF context.S
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/src/cortexm.ld @@ -0,0 +1,266 @@ +//============================================================================= +// +// MLT linker script for Cortex-M +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= + +#include <pkgconf/system.h> +#include <pkgconf/hal.h> + +STARTUP(vectors.o) +ENTRY(reset_vector) +INPUT(extras.o) +GROUP(libtarget.a libgcc.a libsupc++.a) + +#if defined(__ARMEB__) +OUTPUT_FORMAT(elf32-bigarm) +#endif + +// ALIGN_LMA is 4, but the AAPCS now requires that double word types +// be aligned to 8, which means some input sections can be marked as needing +// 8-byte alignment, even text ones (consider literal data). + +#define ALIGN_LMA 4 +#define AAPCS_ALIGN 8 +#define FOLLOWING_ALIGNED(_section_, _align_) AT ((LOADADDR (_section_) + SIZEOF (_section_) + (_align_) - 1) & ~ ((_align_) - 1)) +#define FOLLOWING(_section_) FOLLOWING_ALIGNED(_section_, ALIGN_LMA) + +#define LMA_EQ_VMA +#define FORCE_OUTPUT . = . + +// Some versions of gcc define "arm" which causes problems with .note.arm.ident +#undef arm +#define SECTIONS_BEGIN \ + /* Debug information */ \ + .debug_aranges 0 : { *(.debug_aranges) } \ + .debug_pubnames 0 : { *(.debug_pubnames) } \ + .debug_info 0 : { *(.debug_info) } \ + .debug_abbrev 0 : { *(.debug_abbrev) } \ + .debug_line 0 : { *(.debug_line) } \ + .debug_frame 0 : { *(.debug_frame) } \ + .debug_str 0 : { *(.debug_str) } \ + .debug_loc 0 : { *(.debug_loc) } \ + .debug_macinfo 0 : { *(.debug_macinfo) } \ + .note.arm.ident 0 : { KEEP (*(.note.arm.ident)) } \ + /DISCARD/ 0 : { *(.fini_array*) } + + +// Following not used unless CYGHWR_HAL_ARM_SEPARATE_VSR_TABLE +// defined in hal_platform_setup.h. Otherwise vsr table +// goes in .fixed_vectors. +#define SECTION_hal_vsr_table(_region_, _vma_, _lma_) \ + .hal_vsr_table _vma_ : _lma_ \ + { FORCE_OUTPUT; KEEP (*(.hal_vsr_table)) } \ + > _region_ + +#define SECTION_fixed_vectors(_region_, _vma_, _lma_) \ + .fixed_vectors _vma_ : _lma_ \ + { FORCE_OUTPUT; KEEP (*(.fixed_vectors)) } \ + > _region_ + +#define SECTION_rom_vectors(_region_, _vma_, _lma_) \ + .rom_vectors _vma_ : _lma_ \ + { __rom_vectors_vma = ABSOLUTE(.); \ + FORCE_OUTPUT; KEEP (*(.vectors)) } \ + > _region_ \ + __rom_vectors_lma = LOADADDR(.rom_vectors); + +// We slot in the .ARM.extab and .ARM.exidx sections first. They +// need to be close to .text due to their relocations which may +// want small offsets - .rodata may be somewhere very different. +// This approach also allows forward compatibility with targets +// which haven't used the EABI before (no new SECTION_xxx definition +// to use). +// One glitch is that the AAPCS can require up to 8-byte alignment +// for double word types. For sections after the first (for which we +// "trust" the MLT files (probably a mistake)), we need to +// ensure the subsequent sections' VMA and LMA move in sync, which +// means keeping the same alignment, and thus since for example literal +// data in .text can require up to 8 byte alignment, the LMA must also +// be 8 byte aligned. +#define SECTION_text(_region_, _vma_, _lma_) \ + .ARM.extab _vma_ : _lma_ \ + { PROVIDE (__stext = ABSOLUTE(.));_stext = ABSOLUTE(.) ; \ + FORCE_OUTPUT; \ + *(.ARM.extab* .gnu.linkonce.armextab.*) } > _region_ \ + . = ALIGN(AAPCS_ALIGN); \ + __exidx_start = ABSOLUTE(.); \ + .ARM.exidx ALIGN(AAPCS_ALIGN) : FOLLOWING_ALIGNED(.ARM.extab, AAPCS_ALIGN) { \ + *(.ARM.exidx* .gnu.linkonce.armexidx.*) \ + FORCE_OUTPUT; \ + } > _region_ \ + __exidx_end = ABSOLUTE(.);\ + .text ALIGN(AAPCS_ALIGN) : FOLLOWING_ALIGNED(.ARM.exidx, AAPCS_ALIGN) \ + { \ + *(.text*) *(.gnu.warning) *(.gnu.linkonce.t.*) *(.init) \ + *(.glue_7) *(.glue_7t) \ + __CTOR_LIST__ = ABSOLUTE (.); KEEP (*(SORT (.ctors*))) __CTOR_END__ = ABSOLUTE (.); \ + __DTOR_LIST__ = ABSOLUTE (.); KEEP (*(SORT (.dtors*))) __DTOR_END__ = ABSOLUTE (.); \ + } > _region_ \ + _etext = .; PROVIDE (__etext = .); + +#define SECTION_fini(_region_, _vma_, _lma_) \ + .fini _vma_ : _lma_ \ + { FORCE_OUTPUT; *(.fini) } \ + > _region_ + +#define SECTION_rodata(_region_, _vma_, _lma_) \ + .rodata _vma_ : _lma_ \ + { FORCE_OUTPUT; *(.rodata*) *(.gnu.linkonce.r.*) } \ + > _region_ + +#define SECTION_rodata1(_region_, _vma_, _lma_) \ + .rodata1 _vma_ : _lma_ \ + { FORCE_OUTPUT; *(.rodata1) } \ + > _region_ + +#define SECTION_fixup(_region_, _vma_, _lma_) \ + .fixup _vma_ : _lma_ \ + { FORCE_OUTPUT; *(.fixup) } \ + > _region_ + +#define SECTION_gcc_except_table(_region_, _vma_, _lma_) \ + .gcc_except_table _vma_ : _lma_ \ + { FORCE_OUTPUT; \ + KEEP(*(.gcc_except_table)) \ + *(.gcc_except_table.*) \ + } > _region_ + +#define SECTION_eh_frame(_region_, _vma_, _lma_) \ + .eh_frame _vma_ : _lma_ \ + { \ + FORCE_OUTPUT; __EH_FRAME_BEGIN__ = .; \ + KEEP(*(.eh_frame)) \ + __FRAME_END__ = .; \ + . = . + 8; \ + } > _region_ = 0 + +#define SECTION_RELOCS(_region_, _vma_, _lma_) \ + .rel.text : \ + { \ + *(.rel.text) \ + *(.rel.text.*) \ + *(.rel.gnu.linkonce.t*) \ + } > _region_ \ + .rela.text : \ + { \ + *(.rela.text) \ + *(.rela.text.*) \ + *(.rela.gnu.linkonce.t*) \ + } > _region_ \ + .rel.data : \ + { \ + *(.rel.data) \ + *(.rel.data.*) \ + *(.rel.gnu.linkonce.d*) \ + } > _region_ \ + .rela.data : \ + { \ + *(.rela.data) \ + *(.rela.data.*) \ + *(.rela.gnu.linkonce.d*) \ + } > _region_ \ + .rel.rodata : \ + { \ + *(.rel.rodata) \ + *(.rel.rodata.*) \ + *(.rel.gnu.linkonce.r*) \ + } > _region_ \ + .rela.rodata : \ + { \ + *(.rela.rodata) \ + *(.rela.rodata.*) \ + *(.rela.gnu.linkonce.r*) \ + } > _region_ \ + .rel.got : { *(.rel.got) } > _region_ \ + .rela.got : { *(.rela.got) } > _region_ \ + .rel.ctors : { *(.rel.ctors) } > _region_ \ + .rela.ctors : { *(.rela.ctors) } > _region_ \ + .rel.dtors : { *(.rel.dtors) } > _region_ \ + .rela.dtors : { *(.rela.dtors) } > _region_ \ + .rel.init : { *(.rel.init) } > _region_ \ + .rela.init : { *(.rela.init) } > _region_ \ + .rel.fini : { *(.rel.fini) } > _region_ \ + .rela.fini : { *(.rela.fini) } > _region_ \ + .rel.bss : { *(.rel.bss) } > _region_ \ + .rela.bss : { *(.rela.bss) } > _region_ \ + .rel.plt : { *(.rel.plt) } > _region_ \ + .rela.plt : { *(.rela.plt) } > _region_ \ + .rel.dyn : { *(.rel.dyn) } > _region_ + +#define SECTION_got(_region_, _vma_, _lma_) \ + .got _vma_ : _lma_ \ + { \ + FORCE_OUTPUT; *(.got.plt) *(.got) \ + _GOT1_START_ = ABSOLUTE (.); *(.got1) _GOT1_END_ = ABSOLUTE (.); \ + _GOT2_START_ = ABSOLUTE (.); *(.got2) _GOT2_END_ = ABSOLUTE (.); \ + } > _region_ + +#define SECTION_mmu_tables(_region_, _vma_, _lma_) \ + .mmu_tables _vma_ : _lma_ \ + { FORCE_OUTPUT; *(.mmu_tables) } \ + > _region_ + +#define SECTION_sram(_region_, _vma_, _lma_) \ + .sram _vma_ : _lma_ \ + { FORCE_OUTPUT; *(.sram*) } \ + > _region_ + +#define SECTION_data(_region_, _vma_, _lma_) \ + .data _vma_ : _lma_ \ + { __ram_data_start = ABSOLUTE (.); \ + *(.data*) *(.data1) *(.gnu.linkonce.d.*) \ + . = ALIGN (4); \ + KEEP(*( SORT (.ecos.table.*))) ; \ + . = ALIGN (4); \ + __init_array_start__ = ABSOLUTE (.); KEEP (*(SORT (.init_array.*))) \ + KEEP (*(SORT (.init_array))) __init_array_end__ = ABSOLUTE (.); \ + *(.dynamic) *(.sdata*) *(.gnu.linkonce.s.*) \ + . = ALIGN (4); *(.2ram.*) } \ + > _region_ \ + __rom_data_start = LOADADDR (.data); \ + __ram_data_end = .; PROVIDE (__ram_data_end = .); _edata = .; PROVIDE (edata = .); \ + PROVIDE (__rom_data_end = LOADADDR (.data) + SIZEOF(.data)); + +#define SECTION_bss(_region_, _vma_, _lma_) \ + .bss _vma_ : _lma_ \ + { __bss_start = ABSOLUTE (.); \ + *(.scommon) *(.dynsbss) *(.sbss*) *(.gnu.linkonce.sb.*) \ + *(.dynbss) *(.bss*) *(.gnu.linkonce.b.*) *(COMMON) \ + __bss_end = ABSOLUTE (.); } \ + > _region_ + +#define SECTIONS_END . = ALIGN(4); _end = .; PROVIDE (end = .); + +#include <pkgconf/hal_cortexm.h> +#include CYGHWR_MEMORY_LAYOUT_LDI
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/src/cortexm_stub.c @@ -0,0 +1,295 @@ +/*========================================================================== +// +// cortexm_stub.c +// +// Cortex-M GDB stub support +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <stddef.h> + +#include <pkgconf/hal.h> + +#ifdef CYGPKG_REDBOOT +#include <pkgconf/redboot.h> +#endif + +#ifdef CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS + +#include <cyg/hal/hal_arch.h> +#include <cyg/hal/hal_intr.h> +#include <cyg/hal/hal_stub.h> + +//========================================================================== + +#ifndef FALSE +#define FALSE 0 +#define TRUE 1 +#endif + +#ifdef CYGDBG_HAL_DEBUG_GDB_THREAD_SUPPORT +#include <cyg/hal/dbg-threads-api.h> // dbg_currthread_id +#endif + +//========================================================================== +/* Given a trap value TRAP, return the corresponding signal. */ + +int __computeSignal (unsigned int trap_number) +{ + switch (trap_number) + { + case CYGNUM_HAL_VECTOR_BUS_FAULT: // Fall through + case CYGNUM_HAL_VECTOR_MEMORY_MAN: // Fall through + return SIGBUS; + case CYGNUM_HAL_VECTOR_NMI: + case CYGNUM_HAL_VECTOR_SYS_TICK: + return SIGINT; + default: + return SIGTRAP; + } +} + + +//========================================================================== +/* Return the trap number corresponding to the last-taken trap. */ + +int __get_trap_number (void) +{ + // The vector is not not part of the GDB register set so get it + // directly from the save context. + return _hal_registers->u.exception.vector; +} + + +//========================================================================== +/* Set the currently-saved pc register value to PC. */ + +void set_pc (target_register_t pc) +{ + put_register (PC, pc); +} + +//========================================================================== +// Calculate byte offset a given register from start of register save area. + +static int +reg_offset(regnames_t reg) +{ + int base_offset; + + if (reg < F0) + return reg * 4; + + base_offset = 16 * 4; + + if (reg < FPS) + return base_offset + ((reg - F0) * 12); + + base_offset += (8 * 12); + + if (reg <= PS) + return base_offset + ((reg - FPS) * 4); + + return -1; // Should never happen! +} + + +//========================================================================== +// Return the currently-saved value corresponding to register REG of +// the exception context. + +target_register_t +get_register (regnames_t reg) +{ + target_register_t val; + int offset = reg_offset(reg); + + if (REGSIZE(reg) > sizeof(target_register_t) || offset == -1) + return -1; + + val = _registers[offset/sizeof(target_register_t)]; + + return val; +} + +//========================================================================== +// Store VALUE in the register corresponding to WHICH in the exception +// context. + +void +put_register (regnames_t which, target_register_t value) +{ + int offset = reg_offset(which); + + if (REGSIZE(which) > sizeof(target_register_t) || offset == -1) + return; + + _registers[offset/sizeof(target_register_t)] = value; +} + +//========================================================================== +// Write the contents of register WHICH into VALUE as raw bytes. This +// is only used for registers larger than sizeof(target_register_t). +// Return non-zero if it is a valid register. + +int +get_register_as_bytes (regnames_t which, char *value) +{ + int offset = reg_offset(which); + + if (offset != -1) { + memcpy (value, (char *)_registers + offset, REGSIZE(which)); + return 1; + } + return 0; +} + +//========================================================================== +// Alter the contents of saved register WHICH to contain VALUE. This +// is only used for registers larger than sizeof(target_register_t). +// Return non-zero if it is a valid register. + +int +put_register_as_bytes (regnames_t which, char *value) +{ + int offset = reg_offset(which); + + if (offset != -1) { + memcpy ((char *)_registers + offset, value, REGSIZE(which)); + return 1; + } + return 0; +} + +//========================================================================== +// Single step the processor. +// +// We do this by setting the MON_STEP bit in the DEMCR. So long as we +// are in a DebugMonitor exception this will single step the CPU on +// return. +// We also need to block all pending interrupts by setting basepri +// before doing the step. Otherwise an interrupt may be delivered +// before the step happens, and may cause unpleasant things to happen. + +cyg_uint32 __single_step_basepri = 0; + +void __single_step (void) +{ + CYG_ADDRESS base = CYGARC_REG_DEBUG_BASE; + cyg_uint32 demcr; + + // Save basepri and set it to mask all interrupts. + __single_step_basepri = _hal_registers->u.exception.basepri; + _hal_registers->u.exception.basepri = CYGNUM_HAL_CORTEXM_PRIORITY_MAX; + + // Set MON_STEP + HAL_READ_UINT32( base+CYGARC_REG_DEBUG_DEMCR, demcr ); + demcr |= CYGARC_REG_DEBUG_DEMCR_MON_STEP; + HAL_WRITE_UINT32( base+CYGARC_REG_DEBUG_DEMCR, demcr ); + + // Clear any bits set in DFSR + base = CYGARC_REG_NVIC_BASE; + HAL_WRITE_UINT32( base+CYGARC_REG_NVIC_DFSR, 0xFFFFFFFF ); + +} + +//========================================================================== +// Clear the single-step state. + +void __clear_single_step (void) +{ + CYG_ADDRESS base = CYGARC_REG_DEBUG_BASE; + cyg_uint32 demcr; + + // Restore basepri + _hal_registers->u.exception.basepri = __single_step_basepri; + + // Clear MON_STEP + HAL_READ_UINT32( base+CYGARC_REG_DEBUG_DEMCR, demcr ); + demcr &= ~CYGARC_REG_DEBUG_DEMCR_MON_STEP; + HAL_WRITE_UINT32( base+CYGARC_REG_DEBUG_DEMCR, demcr ); + + // Clear any bits set in DFSR + base = CYGARC_REG_NVIC_BASE; + HAL_WRITE_UINT32( base+CYGARC_REG_NVIC_DFSR, 0xFFFFFFFF ); +} + +//========================================================================== + +void __install_breakpoints (void) +{ + __install_breakpoint_list(); +} + +//-------------------------------------------------------------------------- + +void __clear_breakpoints (void) +{ + __clear_breakpoint_list(); +} + +//-------------------------------------------------------------------------- +/* If the breakpoint we hit is in the breakpoint() instruction, return a + non-zero value. */ + +int +__is_breakpoint_function () +{ + return get_register (PC) == (target_register_t)&_breakinst; +} + + +//-------------------------------------------------------------------------- +/* Skip the current instruction. Since this is only called by the + stub when the PC points to a breakpoint or trap instruction, + we can safely just skip 2. */ + +void __skipinst (void) +{ + unsigned long pc = get_register(PC); + + pc += 2; + + put_register(PC, pc); +} + +//========================================================================== +#endif // CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/src/hal_misc.c @@ -0,0 +1,672 @@ +/*========================================================================== +// +// hal_misc.c +// +// Cortex-M exception vectors +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/hal.h> +#include <pkgconf/hal_cortexm.h> +#ifdef CYGPKG_KERNEL +#include <pkgconf/kernel.h> +#endif + +#include <cyg/infra/diag.h> +#include <cyg/infra/cyg_type.h> +#include <cyg/infra/cyg_trac.h> // tracing macros +#include <cyg/infra/cyg_ass.h> // assertion macros + +#include <cyg/hal/hal_arch.h> // HAL header +#include <cyg/hal/hal_intr.h> // HAL header + +#include <cyg/hal/drv_api.h> + +//========================================================================== + +typedef cyg_uint32 cyg_isr(cyg_uint32 vector, CYG_ADDRWORD data); + +//========================================================================== +// External references + +// VSRs in vectors.S +__externC void hal_default_exception_vsr( void ); +__externC void hal_default_interrupt_vsr( void ); +__externC void hal_default_svc_vsr( void ); +__externC void hal_pendable_svc_vsr( void ); +__externC void hal_switch_state_vsr( void ); + +// HAL and eCos functions +__externC void hal_system_init( void ); +__externC void hal_variant_init( void ); +__externC void hal_platform_init( void ); +__externC void hal_ctrlc_isr_init( void ); +__externC void initialize_stub( void ); +__externC void cyg_hal_invoke_constructors( void ); +__externC void cyg_start( void ); +__externC void cyg_interrupt_post_dsr( CYG_ADDRWORD intr_obj ); +__externC void interrupt_end(cyg_uint32 isr_ret, CYG_ADDRWORD intr, HAL_SavedRegisters *regs ); + +// DATA and BSS locations +__externC cyg_uint32 __ram_data_start; +__externC cyg_uint32 __ram_data_end; +__externC cyg_uint32 __rom_data_start; +__externC cyg_uint32 __bss_start; +__externC cyg_uint32 __bss_end; + +// Scheduler lock +__externC volatile cyg_uint32 cyg_scheduler_sched_lock; + +//========================================================================== +// Interrupt tables + +volatile CYG_ADDRESS hal_interrupt_handlers[CYGNUM_HAL_ISR_COUNT]; +volatile CYG_ADDRWORD hal_interrupt_data [CYGNUM_HAL_ISR_COUNT]; +volatile CYG_ADDRESS hal_interrupt_objects [CYGNUM_HAL_ISR_COUNT]; + +//========================================================================== +// Main entry point +// +// Enter here from reset via slot 1 of VSR table. The stack pointer is +// already set to the value in VSR slot 0, usually the top of internal +// SRAM. + +void hal_reset_vsr( void ) +{ + // Call system init routine. This should do the minimum necessary + // for the rest of the initialization to complete. For example set + // up GPIO, the SRAM, power management etc. This routine is + // usually supplied by the platform HAL. Calls to + // hal_variant_init() and hal_platform_init() later will perform + // the main initialization. + + hal_system_init(); + + // Initialize vector table in base of SRAM. + { + register int i; + +#if !defined(CYG_HAL_STARTUP_RAM) + + // Only install the exception vectors for non-RAM startup. For + // RAM startup we want these to continue to point to the original + // VSRs, which will belong to RedBoot or GDB stubs. + + for( i = 2; i < 15; i++ ) + hal_vsr_table[i] = (CYG_ADDRESS)hal_default_exception_vsr; + +#endif + // Always point SVC and PENDSVC vectors to our local versions + + hal_vsr_table[CYGNUM_HAL_VECTOR_SERVICE] = (CYG_ADDRESS)hal_default_svc_vsr; + hal_vsr_table[CYGNUM_HAL_VECTOR_PENDSV] = (CYG_ADDRESS)hal_pendable_svc_vsr; + + // For all startup type, redirect interrupt vectors to our VSR. + for( i = CYGNUM_HAL_VECTOR_SYS_TICK ; + i < CYGNUM_HAL_VECTOR_SYS_TICK + CYGNUM_HAL_VSR_MAX; + i++ ) + hal_vsr_table[i] = (CYG_ADDRESS)hal_default_interrupt_vsr; + } + + +#if !defined(CYG_HAL_STARTUP_RAM) + + // Ensure that the CPU will use the vector table we have just set + // up. + +# if defined(CYGHWR_HAL_CORTEXM_M3) + + // On M3 parts, the NVIC contains a vector table base register. We + // program this to relocate the vector table base to the base of + // SRAM. + + HAL_WRITE_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_VTOR, + CYGARC_REG_NVIC_VTOR_TBLOFF(0)| + CYGARC_REG_NVIC_VTOR_TBLBASE_SRAM ); + +# else + +# error Unknown SRAM/VECTAB remap mechanism + +# endif + + // Use SVC to switch our state to thread mode running on the PSP. + // We don't need to do this for RAM startup since the ROM code + // will have already done it. + + hal_vsr_table[CYGNUM_HAL_VECTOR_SERVICE] = (CYG_ADDRESS)hal_switch_state_vsr; + + __asm__ volatile( "swi" ); + + hal_vsr_table[CYGNUM_HAL_VECTOR_SERVICE] = (CYG_ADDRESS)hal_default_svc_vsr; + +#endif // !defined(CYG_HAL_STARTUP_RAM) + +#if defined(CYG_HAL_STARTUP_ROM) + // Relocate data from ROM to RAM + { + register cyg_uint32 *p, *q; + for( p = &__ram_data_start, q = &__rom_data_start; + p < &__ram_data_end; + p++, q++ ) + *p = *q; + } +#endif + + // Clear BSS + { + register cyg_uint32 *p; + for( p = &__bss_start; p < &__bss_end; p++ ) + *p = 0; + } + + // Initialize interrupt vectors. Set the levels for all interrupts + // to default values. Also set the default priorities of the + // system handlers: all exceptions maximum priority except SVC and + // PendSVC which are lowest priority. + { + register int i; + + HAL_WRITE_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_SHPR0, 0x00000000 ); + HAL_WRITE_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_SHPR1, 0xFF000000 ); + HAL_WRITE_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_SHPR2, 0x00FF0000 ); + + hal_interrupt_handlers[CYGNUM_HAL_INTERRUPT_SYS_TICK] = (CYG_ADDRESS)hal_default_isr; + + for( i = 1; i < CYGNUM_HAL_ISR_COUNT; i++ ) + { + hal_interrupt_handlers[i] = (CYG_ADDRESS)hal_default_isr; + HAL_WRITE_UINT8( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_PR(i-CYGNUM_HAL_INTERRUPT_EXTERNAL), 0x80 ); + } + } + +#if defined(CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS) + // Enable DebugMonitor exceptions. This is needed to enable single + // step. This only has an effect if no external JTAG device is + // attached. + { + CYG_ADDRESS base = CYGARC_REG_DEBUG_BASE; + cyg_uint32 demcr; + + HAL_READ_UINT32( base+CYGARC_REG_DEBUG_DEMCR, demcr ); + demcr |= CYGARC_REG_DEBUG_DEMCR_MON_EN; + HAL_WRITE_UINT32( base+CYGARC_REG_DEBUG_DEMCR, demcr ); + } +#endif + +#if !defined(CYG_HAL_STARTUP_RAM) + // Enable Usage, Bus and Mem fault handlers. Do this for ROM and + // JTAG startups. For RAM startups, this will have already been + // done by the ROM monitor. + { + CYG_ADDRESS base = CYGARC_REG_NVIC_BASE; + cyg_uint32 shcsr; + + HAL_READ_UINT32( base+CYGARC_REG_NVIC_SHCSR, shcsr ); + shcsr |= CYGARC_REG_NVIC_SHCSR_USGFAULTENA; + shcsr |= CYGARC_REG_NVIC_SHCSR_BUSFAULTENA; + shcsr |= CYGARC_REG_NVIC_SHCSR_MEMFAULTENA; + HAL_WRITE_UINT32( base+CYGARC_REG_NVIC_SHCSR, shcsr ); + } +#endif + + // Call variant and platform init routines + hal_variant_init(); + hal_platform_init(); + + // Start up the system clock + HAL_CLOCK_INITIALIZE( CYGNUM_HAL_RTC_PERIOD ); + +#ifdef CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS + + initialize_stub(); + +#endif + +#if defined(CYGDBG_HAL_DEBUG_GDB_CTRLC_SUPPORT) || \ + defined(CYGDBG_HAL_DEBUG_GDB_BREAK_SUPPORT) + + hal_ctrlc_isr_init(); + +#endif + + // Run through static constructors + cyg_hal_invoke_constructors(); + + // Finally call into application + cyg_start(); + for(;;); +} + +//========================================================================== +// Handle Exceptions +// +// Exceptions are passed here from the initial VSR. We pass the +// exception on to GDB stubs or the kernel as appropriate. + +__externC void __handle_exception (void); + +__externC HAL_SavedRegisters *_hal_registers; +#ifdef CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS +__externC void* volatile __mem_fault_handler; +#endif + +void hal_deliver_exception( HAL_SavedRegisters *regs ) +{ + // Special case handler for code which has chosen to take care + // of data exceptions (i.e. code which expects them to happen) + // This is common in discovery code, e.g. checking for a particular + // device which may generate an exception when probing if the + // device is not present +#ifdef CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS + if (__mem_fault_handler ) + { + regs->u.exception.pc = (unsigned long)__mem_fault_handler; + return; // Caught an exception inside stubs + } +#endif + +#if defined(CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS) + + _hal_registers = regs; + __handle_exception(); + +#elif defined(CYGPKG_KERNEL_EXCEPTIONS) + + cyg_hal_deliver_exception( regs->u.exception.vector, (CYG_ADDRWORD)regs ); + +#else + + CYG_FAIL("Exception!!!"); + +#endif +} + +//========================================================================== +// Handle Interrupts +// +// Interrupts are passed here from the low-level VSR in vectors.S. We +// look up the ISR in the interrupt table, call it and if it requests +// it, post a DSR. If necessary we also then cause the pendable SVC to +// be requested. +// +// This function is also callable from ISR springboards that decode +// additional interrupts via external controllers to deliver an +// interrupt to a secondary vector. + +void hal_deliver_interrupt( cyg_uint32 vector ) +{ + register cyg_uint32 isr_result; + register cyg_isr *isr; + cyg_bool pendsvc = false; + +#if defined(CYGPKG_KERNEL_INSTRUMENT) && \ + defined(CYGDBG_KERNEL_INSTRUMENT_INTR) + cyg_instrument(RAISE_INTR, vector, 0 ); +#endif + + isr = (cyg_isr *)hal_interrupt_handlers[vector]; + + // Call the ISR + isr_result = isr( vector, hal_interrupt_data[vector] ); + + +#if !defined(CYGIMP_HAL_COMMON_INTERRUPTS_CHAIN) + // If the ISR has returned the CALL_DSR bit, post the DSR and set + // the pendable SVC exception pending. + if( isr_result & CYG_ISR_CALL_DSR ) + { + cyg_interrupt_post_dsr( hal_interrupt_objects[vector] ); + + // Post the pendable SVC to call interrupt_end(). But only if + // the scheduler lock is currently zero. If it is non zero + // then interrupt_end will do nothing useful, so avoid calling + // it. + if( cyg_scheduler_sched_lock == 0 ) + pendsvc = true; + } +#else + // When chaining we don't know here whether the nested interrupt + // has posted a DSR, so we have to run interrupt_end() regardless. + // However, the same considerations as above regarding the + // scheduler lock still apply. + if( cyg_scheduler_sched_lock == 0 ) + pendsvc = true; +#endif + + // Post the pendable SVC if required. + if( pendsvc ) + { + cyg_uint32 icsr; + HAL_READ_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_ICSR, icsr ); + icsr |= CYGARC_REG_NVIC_ICSR_PENDSVSET; + HAL_WRITE_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_ICSR, icsr ); + } +} + +//========================================================================== +// Call interrupt_end() +// +// This is called on the thread stack as a result of the pendable +// SVC. interrupt_end() decrements the scheduler lock, calls DSRs and +// optionally switches thread context. So before calling, we must +// increment the lock. The actual interrupt end processing has already +// been done above in hal_default_interrupt_vsr1(), so the arguments +// are zero. + +__externC void hal_interrupt_end( void ) +{ +#ifdef CYGFUN_HAL_COMMON_KERNEL_SUPPORT + cyg_scheduler_sched_lock++; +#endif + + interrupt_end(0,0,0); +} + +//========================================================================== +// Interrupt masking and configuration + +#ifndef HAL_VAR_INTERRUPT_MASK +#define HAL_VAR_INTERRUPT_MASK( __vector ) CYG_EMPTY_STATEMENT +#define HAL_VAR_INTERRUPT_UNMASK( __vector ) CYG_EMPTY_STATEMENT +#define HAL_VAR_INTERRUPT_SET_LEVEL( __vector, __level ) CYG_EMPTY_STATEMENT +#define HAL_VAR_INTERRUPT_ACKNOWLEDGE( __vector ) CYG_EMPTY_STATEMENT +#define HAL_VAR_INTERRUPT_CONFIGURE( __vector, __level, __up ) CYG_EMPTY_STATEMENT +#endif + +//-------------------------------------------------------------------------- + +__externC void hal_interrupt_mask( cyg_uint32 vector ) +{ + if( vector >= CYGNUM_HAL_INTERRUPT_EXTERNAL && + vector <= CYGNUM_HAL_INTERRUPT_NVIC_MAX ) + HAL_WRITE_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_CER(vector-CYGNUM_HAL_INTERRUPT_EXTERNAL), + CYGARC_REG_NVIC_IBIT(vector-CYGNUM_HAL_INTERRUPT_EXTERNAL) ); + else if( vector == CYGNUM_HAL_INTERRUPT_SYS_TICK ) + { + cyg_uint32 csr; + HAL_READ_UINT32(CYGARC_REG_SYSTICK_BASE+CYGARC_REG_SYSTICK_CSR, csr ); + csr &= ~CYGARC_REG_SYSTICK_CSR_TICKINT; + HAL_WRITE_UINT32(CYGARC_REG_SYSTICK_BASE+CYGARC_REG_SYSTICK_CSR, csr ); + } + HAL_VAR_INTERRUPT_MASK( vector ); +} + +//-------------------------------------------------------------------------- + +__externC void hal_interrupt_unmask( cyg_uint32 vector ) +{ + if( vector >= CYGNUM_HAL_INTERRUPT_EXTERNAL && + vector <= CYGNUM_HAL_INTERRUPT_NVIC_MAX ) + HAL_WRITE_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_SER(vector-CYGNUM_HAL_INTERRUPT_EXTERNAL), + CYGARC_REG_NVIC_IBIT(vector-CYGNUM_HAL_INTERRUPT_EXTERNAL) ); + else if( vector == CYGNUM_HAL_INTERRUPT_SYS_TICK ) + { + cyg_uint32 csr; + HAL_READ_UINT32(CYGARC_REG_SYSTICK_BASE+CYGARC_REG_SYSTICK_CSR, csr ); + csr |= CYGARC_REG_SYSTICK_CSR_TICKINT; + HAL_WRITE_UINT32(CYGARC_REG_SYSTICK_BASE+CYGARC_REG_SYSTICK_CSR, csr ); + } + HAL_VAR_INTERRUPT_UNMASK( vector ); +} + +//-------------------------------------------------------------------------- + +__externC void hal_interrupt_acknowledge( cyg_uint32 vector ) +{ + HAL_VAR_INTERRUPT_ACKNOWLEDGE( vector ); +} + +//-------------------------------------------------------------------------- + +__externC void hal_interrupt_configure( cyg_uint32 vector, cyg_uint32 level, cyg_uint32 up ) +{ + HAL_VAR_INTERRUPT_CONFIGURE( vector, level, up ); +} + +//-------------------------------------------------------------------------- + +__externC void hal_interrupt_set_level( cyg_uint32 vector, cyg_uint32 level ) +{ + cyg_uint32 l = (level)+CYGNUM_HAL_CORTEXM_PRIORITY_MAX; + if( l > 0xFF ) l = 0xFF; /* clamp to 0xFF */ + if( vector >= CYGNUM_HAL_INTERRUPT_EXTERNAL && + vector <= CYGNUM_HAL_INTERRUPT_NVIC_MAX ) + { + HAL_WRITE_UINT8( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_PR(vector-CYGNUM_HAL_INTERRUPT_EXTERNAL), + l ); + } + else if ( vector == CYGNUM_HAL_INTERRUPT_SYS_TICK ) + { + cyg_uint32 shpr2; + HAL_READ_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_SHPR2, shpr2 ); + shpr2 &= ~0xFF000000; + shpr2 |= (l)<<24; + HAL_WRITE_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_SHPR2, shpr2 ); + } + HAL_VAR_INTERRUPT_SET_LEVEL( vector, level ); +} + +//========================================================================== +// Microsecond delay +// +// The system RTC is set up to tick at 1MHz so all we need to do here +// is count ticks. + +__externC void hal_delay_us( cyg_int32 us ) +{ + cyg_uint32 t0, t1; + + HAL_CLOCK_READ( &t0 ); + while ( us > 0 ) + { + HAL_CLOCK_READ( &t1 ); + if( t1 < t0 ) + t1 += CYGNUM_HAL_RTC_PERIOD; + us -= t1-t0; + t0 = t1; + } +} + +//========================================================================== +// C++ support - run initial constructors + +#ifdef CYGSEM_HAL_STOP_CONSTRUCTORS_ON_FLAG +cyg_bool cyg_hal_stop_constructors; +#endif + +typedef void (*pfunc) (void); + +extern pfunc __init_array_start__[]; +extern pfunc __init_array_end__[]; +#define CONSTRUCTORS_START (__init_array_start__[0]) +#define CONSTRUCTORS_END (__init_array_end__) +#define NEXT_CONSTRUCTOR(c) ((c)++) + +void +cyg_hal_invoke_constructors (void) +{ +#ifdef CYGSEM_HAL_STOP_CONSTRUCTORS_ON_FLAG + static pfunc *p = &CONSTRUCTORS_START; + + cyg_hal_stop_constructors = 0; + for (; p != CONSTRUCTORS_END; NEXT_CONSTRUCTOR(p)) { + (*p)(); + if (cyg_hal_stop_constructors) { + NEXT_CONSTRUCTOR(p); + break; + } + } +#else + pfunc *p; + + for (p = &CONSTRUCTORS_START; p != CONSTRUCTORS_END; NEXT_CONSTRUCTOR(p)) + (*p)(); +#endif +} + +//========================================================================== +// Architecture default ISR + +__externC cyg_uint32 +hal_arch_default_isr(CYG_ADDRWORD vector, CYG_ADDRWORD data) +{ + CYG_TRACE1(true, "Interrupt: %d", vector); + + CYG_FAIL("Spurious Interrupt!!!"); + + return 0; +} + +//========================================================================== +// GDB support +// +// These functions translate between HAL saved contexts and GDB +// register dumps. + +__externC void hal_get_gdb_registers( HAL_CORTEXM_GDB_Registers *gdbreg, HAL_SavedRegisters *regs ) +{ + int i; + cyg_uint32 *p = gdbreg->f0; + + switch( regs->u.type ) + { + case HAL_SAVEDREGISTERS_THREAD: + for( i = 0; i < 13; i++ ) + gdbreg->gpr[i] = regs->u.thread.r[i]; + gdbreg->gpr[13] = regs->u.thread.sp; + gdbreg->gpr[14] = regs->u.thread.pc; + gdbreg->gpr[15] = regs->u.thread.pc; + gdbreg->ps = 0x01000000; + break; + + case HAL_SAVEDREGISTERS_EXCEPTION: + gdbreg->gpr[0] = regs->u.exception.r0; + gdbreg->gpr[1] = regs->u.exception.r1; + gdbreg->gpr[2] = regs->u.exception.r2; + gdbreg->gpr[3] = regs->u.exception.r3; + for( i = 0; i < 8; i++ ) + gdbreg->gpr[i+4] = regs->u.exception.r4_11[i]; + gdbreg->gpr[12] = regs->u.exception.r12; + gdbreg->gpr[13] = ((cyg_uint32)regs)+sizeof(regs->u.exception); + gdbreg->gpr[14] = regs->u.exception.lr; + gdbreg->gpr[15] = regs->u.exception.pc; + gdbreg->ps = regs->u.exception.psr; + break; + + case HAL_SAVEDREGISTERS_INTERRUPT: + gdbreg->gpr[0] = regs->u.interrupt.r0; + gdbreg->gpr[1] = regs->u.interrupt.r1; + gdbreg->gpr[2] = regs->u.interrupt.r2; + gdbreg->gpr[3] = regs->u.interrupt.r3; + gdbreg->gpr[12] = regs->u.interrupt.r12; + gdbreg->gpr[13] = ((cyg_uint32)regs)+sizeof(regs->u.interrupt); + gdbreg->gpr[14] = regs->u.interrupt.lr; + gdbreg->gpr[15] = regs->u.interrupt.pc; + gdbreg->ps = regs->u.interrupt.psr; + break; + } + + // Clear FP state, which we don't use + for( i = 0; i < (8*3+1); i++ ) + p[i] = 0; + +} + +__externC void hal_set_gdb_registers( HAL_CORTEXM_GDB_Registers *gdbreg, HAL_SavedRegisters *regs ) +{ + int i; + + switch( regs->u.type ) + { + case HAL_SAVEDREGISTERS_THREAD: + for( i = 0; i < 13; i++ ) + regs->u.thread.r[i] = gdbreg->gpr[i]; + regs->u.thread.sp = gdbreg->gpr[13]; + regs->u.thread.pc = gdbreg->gpr[14]; + regs->u.thread.pc = gdbreg->gpr[15]; + break; + + case HAL_SAVEDREGISTERS_EXCEPTION: + regs->u.exception.r0 = gdbreg->gpr[0]; + regs->u.exception.r1 = gdbreg->gpr[1]; + regs->u.exception.r2 = gdbreg->gpr[2]; + regs->u.exception.r3 = gdbreg->gpr[3]; + for( i = 0; i < 8; i++ ) + regs->u.exception.r4_11[i] = gdbreg->gpr[i+4]; + regs->u.exception.r12 = gdbreg->gpr[12]; + regs->u.exception.lr = gdbreg->gpr[14]; + regs->u.exception.pc = gdbreg->gpr[15]; + regs->u.exception.psr = gdbreg->ps; + break; + + case HAL_SAVEDREGISTERS_INTERRUPT: + regs->u.interrupt.r0 = gdbreg->gpr[0]; + regs->u.interrupt.r1 = gdbreg->gpr[1]; + regs->u.interrupt.r2 = gdbreg->gpr[2]; + regs->u.interrupt.r3 = gdbreg->gpr[3]; + regs->u.interrupt.r12 = gdbreg->gpr[12]; + regs->u.interrupt.lr = gdbreg->gpr[14]; + regs->u.interrupt.pc = gdbreg->gpr[15]; + regs->u.interrupt.psr = gdbreg->ps; + break; + } +} + +//========================================================================== +// When compiling C++ code with static objects the compiler +// inserts a call to __cxa_atexit() with __dso_handle as one of the +// arguments. __cxa_atexit() would normally be provided by glibc, and +// __dso_handle is part of crtstuff.c. eCos applications +// are linked rather differently, so either a differently-configured +// compiler is needed or dummy versions of these symbols should be +// provided. If these symbols are not actually used then providing +// them is still harmless, linker garbage collection will remove them. + +void +__cxa_atexit(void (*arg1)(void*), void* arg2, void* arg3) +{ +} + +void* __dso_handle = (void*) &__dso_handle; + +//========================================================================== +// EOF hal_misc.c
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/arch/current/src/vectors.S @@ -0,0 +1,340 @@ +/*========================================================================== +// +// vectors.S +// +// Cortex-M exception vectors +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Description: This file defines the code placed into the exception +// vectors. It also contains the first level default VSRs +// that save and restore state for both exceptions and +// interrupts. +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/hal.h> +#include <pkgconf/hal_cortexm.h> +#ifdef CYGPKG_KERNEL +#include <pkgconf/kernel.h> +#endif + +#include <cyg/hal/variant.inc> + +//========================================================================== + + .syntax unified + .thumb + +//========================================================================== +// Initial exception vector table +// +// This only contains the stack and entry point for reset. The table +// to be used at runtime is constructed by code in hal_reset_vsr(). + + .section ".vectors","ax" + + .global hal_vsr_table +hal_vsr_table_init: + + .long hal_startup_stack // 0 Reset stack + .long hal_reset_vsr // 1 Reset entry + +//========================================================================== + + .text + .thumb + +//========================================================================== +// Fake entry point. +// +// The ELF file entry point points here. When loading an executable +// via RedBoot/Stubs or via JTAG the PC will be set to this address. +// The code here sets up the SP and branches to the reset VSR in +// emulation of the hardware reset behaviour. + + .align 2 + .global reset_vector + .thumb + .thumb_func + .type reset_vector, %function +reset_vector: + + ldr sp,=hal_startup_stack + b hal_reset_vsr + + .pool + +#if !defined(CYG_HAL_STARTUP_RAM) +//========================================================================== +// State switch VSR +// +// This is called from the init code to switch execution from the main +// stack to the process stack. We also take the opportunity to do some +// other things that are best done in asm code such as disabling interrupts +// and setting the control register. +// +// The adjustment to MSP by 1/2 interrupt stack size allows code to +// throw exceptions without corrupting the execution stack. This is +// only necessary for non-kernel configurations (e.g. RedBoot, Stubs) +// since kernel configurations will switch to a thread stack before +// they should throw an exception. + + .global hal_switch_state_vsr + .thumb + .thumb_func + .type hal_switch_state_vsr, %function +hal_switch_state_vsr: + + mov r0,#CYGNUM_HAL_CORTEXM_PRIORITY_MAX + msr basepri,r0 + + mov r0,#2 // Set CONTROL register to 2 + msr control,r0 + isb // Insert a barrier + + msr psp,sp // Copy SP to PSP + +#if !defined(CYGPKG_KERNEL) + sub sp,#(CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE/2) +#endif + + orr lr,#0xD // Adjust return link + bx lr // Return to init code on PSP now + +#endif + +//========================================================================== +// Default exception VSR +// +// This is attached to all exception vectors. It saves the entire +// machine state and calls into the eCos exception handling code. +// +// NOTE: At present this implementation does not permit an exception +// handler to suspend the faulting thread and enter the scheduler to +// switch elsewhere. However, I know of no code that does anything +// like this. If there is then this may need treating in the same way +// as the interrupt end code. + + .global hal_default_exception_vsr + .thumb + .thumb_func + .type hal_default_exception_vsr, %function +hal_default_exception_vsr: + + mrs r0,psp // Get process stack + sub r1,r0,#(4*12) // Make space for saved state + msr psp,r1 // Ensure PSP is up to date + + mov r1,#1 // R1 = exception state type + mrs r2,ipsr // R2 = vector number + mrs r3,basepri // R3 = basepri + stmfd r0!,{r1-r11,lr} // Push type, vector, basepri, r4-11 + + mov r4,r0 // R4 = saved state pointer + + bl hal_deliver_exception + + mov r0,r4 // R0 = state saved across call + ldmfd r0!,{r1-r11,lr} // Pop type, vec, basepri, registers and LR + msr psp,r0 // Restore PSP + msr basepri,r3 // Restore basepri + + bx lr // Return + + .pool + +//========================================================================== +// Default interrupt VSR +// +// This is a trampoline that translates from the hardware defined entry point +// to the ISR defined by eCos. The CPU will switch automatically to the main +// (interrupt) stack with the process state saved on the process stack. Apart +// from saving a pointer to the interrupt state for Ctrl-C support, and fetching +// the vector number, most of the work is actually done in hal_deliver_interrupt(). + + + .global hal_default_interrupt_vsr + .thumb + .thumb_func + .type hal_default_interrupt_vsr, %function +hal_default_interrupt_vsr: + + push {lr} // Save return link + sub sp,#4 // Realign SP to 8 bytes + +#if defined(CYGDBG_HAL_DEBUG_GDB_CTRLC_SUPPORT) || \ + defined(CYGDBG_HAL_DEBUG_GDB_BREAK_SUPPORT) + // If we are supporting Ctrl-C interrupts from GDB, we must squirrel + // away a pointer to the saved interrupt state here so that we can + // plant a breakpoint at some later time. We only need to make a + // full interrupt saved state in that case. + + .extern hal_saved_interrupt_state + mrs r1,psp // Get PSP + mov r0,#3 // Interrupt state type + stmfd r1!,{r0} // Push interrupt type + ldr r12,=hal_saved_interrupt_state + str r1,[r12] +#endif + + mrs r0,ipsr // R0 = arg0 = vector number + sub r0,#15 // Adjust to interrupt range + + bl hal_deliver_interrupt + + add sp,#4 // pop alignment padding + pop {pc} // Pop LR and return + + .pool + +//========================================================================== +// Pendable SVC VSR +// +// This is invoked if an interrupt posts a DSR. It calls the DSR +// and finalizes interrupt processing by calling interrupt_end(). We want +// to run interrupt_end() on the PSP of the current thread. So we push +// a fake exception frame onto the PSP which will take us to hal_interrupt_end(), +// which will make the call. The return link loaded by that frame takes us +// back to hal_interrupt_end_done which will unwind the real exception +// frame that is still on the PSP. + + + .global hal_pendable_svc_vsr + .thumb + .thumb_func + .type hal_pendable_svc_vsr, %function +hal_pendable_svc_vsr: + + mrs r12,psp // R12 = thread's PSP + sub r0,r12,#0x20 // Make space for frame + msr psp,r0 // Put it back + + ldr r3,=0x01000000 // R3 = PSR = thumb bit set + ldr r2,=hal_interrupt_end // R2 = PC = interrupt end entry point + ldr r1,=hal_interrupt_end_done // R1 = LR = restore code + stmfd r12!,{r0-r3} // Save fake R12, LR, PC, PSR + stmfd r12!,{r0-r3} // Save fake R0-R3 + + bx lr // Return to hal_interrupt_end + + .pool + +//========================================================================== +// Interrupt end done +// +// After calling interrupt end a thread returns here to unstack the +// exception frame used to enter hal_pendable_svc_vsr. We can only +// successfully unstack a frame by doing a proper exception return +// from handler mode, so we use a SWI which will discard its own +// frame and restore the saved one. + + + .global hal_interrupt_end_done + .thumb + .thumb_func + .type hal_interrupt_end_done, %function +hal_interrupt_end_done: + + ldr r3,=hal_interrupt_end_vsr + swi + +//========================================================================== +// Interrupt end VSR +// +// This is the SVC VSR invoked by hal_interrupt_end_done to restore the +// original exception frame from a pendable SVC entry. It does this +// by discarding its own frame and using the one below it on the +// stack to return. + + .global hal_interrupt_end_vsr + .thumb + .thumb_func + .type hal_interrupt_end_vsr, %function +hal_interrupt_end_vsr: + + mrs r12,psp // R12 = thread's PSP + add r12,#32 // Skip our saved state + msr psp,r12 // Restore thread's PSP + + bx lr // And return + +//========================================================================== +// Run DSRs VSR +// +// This is invoked from the kernel via a SWI to run DSRs on the +// interrupt/main stack. It merely branches to +// cyg_interrupt_call_pending_DSRs() which will then directly return +// from the SVC exception. + + .global hal_call_dsrs_vsr + .thumb + .thumb_func + .type hal_call_dsrs_vsr, %function + +hal_call_dsrs_vsr: + + .extern cyg_interrupt_call_pending_DSRs + b cyg_interrupt_call_pending_DSRs + +//========================================================================== +// SVC VSR +// +// The SVC VSR is used as a general-purpose mechanism for running code +// in handler mode. R3 contains the address of a piece of code to run, +// R0-R2 contain any arguments. Once entered the code is responsible for +// handling the system state and returning to thread mode. +// +// Note that R0-R3 must be explicitly restored from their stacked +// copies since a late arriving interrupt can preempt the SVC entry +// and corrupt these registers before we get here. + + .global hal_default_svc_vsr + .thumb + .thumb_func + .type hal_default_svc_vsr, %function +hal_default_svc_vsr: + + mrs r12,psp + ldmfd r12,{r0-r3} + bx r3 // Jump to routine in R3 + + .pool + +//========================================================================== +// end of vectors.S
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/ChangeLog @@ -0,0 +1,68 @@ +2008-10-10 Nick Garnett <nickg@ecoscentric.com> + + * include/pkgconf/mlt_cortexm_stm3210e_eval_rom.ldi: + * include/pkgconf/mlt_cortexm_stm3210e_eval_rom.h: + * include/pkgconf/mlt_cortexm_stm3210e_eval_ram.ldi: + * include/pkgconf/mlt_cortexm_stm3210e_eval_ram.h: + * include/pkgconf/mlt_cortexm_stm3210e_eval_jtag.ldi: + * include/pkgconf/mlt_cortexm_stm3210e_eval_jtag.h: + * include/pkgconf/mlt_cortexm_stm3210e_eval_sram.ldi: + * include/pkgconf/mlt_cortexm_stm3210e_eval_sram.h: + Update RAM/SRAM upper limits to account for interrupt/init + stack. + + * src/stm3210e_eval_flash.c: Use generic null functions for + external flash lock operations. + +2008-10-06 Nick Garnett <nickg@ecoscentric.com> + + * cdl/hal_cortexm_stm32_stm3210e_eval.cdl: + * include/plf_arch.h: + * include/plf_intr.h: + * include/plf_io.h: + * src/stm3210e_eval_misc.c: + * src/stm3210e_eval_flash.c: + * misc/redboot_ROM.ecm: + * misc/redboot_JTAG.ecm: + * include/pkgconf/mlt_cortexm_stm3210e_eval_rom.ldi: + * include/pkgconf/mlt_cortexm_stm3210e_eval_rom.h: + * include/pkgconf/mlt_cortexm_stm3210e_eval_ram.ldi: + * include/pkgconf/mlt_cortexm_stm3210e_eval_ram.h: + * include/pkgconf/mlt_cortexm_stm3210e_eval_jtag.ldi: + * include/pkgconf/mlt_cortexm_stm3210e_eval_jtag.h: + * include/pkgconf/mlt_cortexm_stm3210e_eval_sram.ldi: + * include/pkgconf/mlt_cortexm_stm3210e_eval_sram.h: + New package -- ST STM3210E EVAL board HAL. + +//=========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//===========================================================================
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/cdl/hal_cortexm_stm32_stm3210e_eval.cdl @@ -0,0 +1,330 @@ +##========================================================================== +## +## hal_cortexm_stm32_stm3210e_eval.cdl +## +## Cortex-M STM3210E EVAL platform HAL configuration data +## +##========================================================================== +######ECOSGPLCOPYRIGHTBEGIN#### +## ------------------------------------------- +## This file is part of eCos, the Embedded Configurable Operating System. +## Copyright (C) 2008 eCosCentric Limited. +## +## eCos 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 2 or (at your option) any later version. +## +## eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +## +## As a special exception, if other files instantiate templates or use macros +## or inline functions from this file, or you compile this file and link it +## with other works to produce a work based on this file, this file does not +## by itself cause the resulting work to be covered by the GNU General Public +## License. However the source code for this file must still be made available +## in accordance with section (3) of the GNU General Public License. +## +## This exception does not invalidate any other reasons why a work based on +## this file might be covered by the GNU General Public License. +## ------------------------------------------- +######ECOSGPLCOPYRIGHTEND#### +##========================================================================== +#######DESCRIPTIONBEGIN#### +## +## Author(s): nickg +## Date: 2008-07-30 +## +######DESCRIPTIONEND#### +## +##========================================================================== + +cdl_package CYGPKG_HAL_CORTEXM_STM32_STM3210E_EVAL { + display "ST STM3210E EVAL Development Board HAL" + doc ecospro-ref/hal-cortexm-stm3210e_eval-part.html + parent CYGPKG_HAL_CORTEXM_STM32 + define_header hal_cortexm_stm32_stm3210e_eval.h + include_dir cyg/hal + hardware + description " + The STM3210E EVAL HAL package provides the support needed to run + eCos on the ST STM3210E EVAL board." + + compile stm3210e_eval_misc.c + + define_proc { + puts $::cdl_system_header "#define CYGBLD_HAL_TARGET_H <pkgconf/hal_cortexm.h>" + puts $::cdl_system_header "#define CYGBLD_HAL_VARIANT_H <pkgconf/hal_cortexm_stm32.h>" + puts $::cdl_system_header "#define CYGBLD_HAL_PLATFORM_H <pkgconf/hal_cortexm_stm32_stm3210e_eval.h>" + puts $::cdl_header "#define HAL_PLATFORM_CPU \"Cortex-M3\"" + puts $::cdl_header "#define HAL_PLATFORM_BOARD \"ST STM3210E EVAL\"" + puts $::cdl_header "#define HAL_PLATFORM_EXTRA \"\"" + } + + cdl_component CYG_HAL_STARTUP { + display "Startup type" + flavor data + default_value {"RAM"} + legal_values {"RAM" "SRAM" "ROM" "JTAG"} + no_define + define -file system.h CYG_HAL_STARTUP + description " + When targetting the ST STM3210E EVAL board it is possible to + build the system for either RAM bootstrap or ROM bootstrap. + Select 'RAM' when building programs to load into RAM using onboard + debug software such as RedBoot or eCos GDB stubs. Select 'ROM' + when building a stand-alone application which will be put + into ROM. The 'JTAG' type allows programs to be downloaded using a + JTAG debugger such as a BDI3000 or PEEDI. The 'SRAM' type allows + programs to be downloaded via a JTAG debugger into on-chip SRAM." + } + + cdl_component CYGHWR_MEMORY_LAYOUT { + display "Memory layout" + flavor data + no_define + default_value { (CYG_HAL_STARTUP == "RAM" ) ? "cortexm_stm3210e_eval_ram" : + (CYG_HAL_STARTUP == "SRAM") ? "cortexm_stm3210e_eval_sram" : + (CYG_HAL_STARTUP == "ROM" ) ? "cortexm_stm3210e_eval_rom" : + (CYG_HAL_STARTUP == "JTAG") ? "cortexm_stm3210e_eval_jtag" : + "undefined" } + + cdl_option CYGHWR_MEMORY_LAYOUT_LDI { + display "Memory layout linker script fragment" + flavor data + no_define + define -file system.h CYGHWR_MEMORY_LAYOUT_LDI + calculated { "<pkgconf/mlt_" . CYGHWR_MEMORY_LAYOUT . ".ldi>" } + } + + cdl_option CYGHWR_MEMORY_LAYOUT_H { + display "Memory layout header file" + flavor data + no_define + define -file system.h CYGHWR_MEMORY_LAYOUT_H + calculated { "<pkgconf/mlt_" . CYGHWR_MEMORY_LAYOUT . ".h>" } + } + + } + + cdl_option CYGARC_HAL_CORTEXM_STM32_INPUT_CLOCK { + display "Input Clock frequency" + flavor data + default_value 8000000 + legal_values 0 to 1000000000 + description "Main clock input." + } + + cdl_option CYGHWR_HAL_CORTEXM_STM32_FLASH { + display "External NOR flash support" + parent CYGPKG_IO_FLASH + active_if CYGPKG_IO_FLASH + flavor none + compile -library=libextras.a stm3210e_eval_flash.c + description "This option enables support for the external NOR flash device." + } + + # Both UARTs 0 and 1 are available for diagnostic/debug use. + implements CYGINT_HAL_STM32_UART0 + implements CYGINT_HAL_STM32_UART1 + + implements CYGINT_IO_SERIAL_FLOW_CONTROL_HW + implements CYGINT_IO_SERIAL_LINE_STATUS_HW + + + cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS { + display "Number of communication channels on the board" + flavor data + calculated 2 + } + + cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_DEBUG_CHANNEL { + display "Debug serial port" + active_if CYGPRI_HAL_VIRTUAL_VECTOR_DEBUG_CHANNEL_CONFIGURABLE + flavor data + legal_values 0 to CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS-1 + default_value 0 + description " + The ST STM3210E EVAL board has two serial ports. This option + chooses which port will be used to connect to a host + running GDB." + } + + cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL { + display "Diagnostic serial port" + active_if CYGPRI_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL_CONFIGURABLE + flavor data + legal_values 0 to CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS-1 + default_value 0 + description " + The ST STM3210E EVAL has two serial ports. This option + chooses which port will be used for diagnostic output." + } + + cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL_BAUD { + display "Console serial port baud rate" + flavor data + legal_values 9600 19200 38400 57600 115200 + default_value 38400 + description " + This option controls the default baud rate used for the + console connection. + Note: this should match the value chosen for the GDB port if the + diagnostic and GDB port are the same." + } + + cdl_option CYGNUM_HAL_VIRTUAL_VECTOR_DEBUG_CHANNEL_BAUD { + display "GDB serial port baud rate" + flavor data + legal_values 9600 19200 38400 57600 115200 + default_value 38400 + description " + This option controls the default baud rate used for the + GDB connection. + Note: this should match the value chosen for the console port if the + console and GDB port are the same." + } + + + cdl_component CYGBLD_GLOBAL_OPTIONS { + display "Global build options" + flavor none + parent CYGPKG_NONE + description " + Global build options including control over + compiler flags, linker flags and choice of toolchain." + + + cdl_option CYGBLD_GLOBAL_COMMAND_PREFIX { + display "Global command prefix" + flavor data + no_define + default_value { "arm-eabi" } + description " + This option specifies the command prefix used when + invoking the build tools." + } + + cdl_option CYGBLD_GLOBAL_CFLAGS { + display "Global compiler flags" + flavor data + no_define + default_value { "-mcpu=cortex-m3 -mthumb -Wall -Wpointer-arith -Wstrict-prototypes -Winline -Wundef -Woverloaded-virtual -g -O2 -ffunction-sections -fdata-sections -fno-rtti -fno-exceptions" } + description " + This option controls the global compiler flags which are used to + compile all packages by default. Individual packages may define + options which override these global flags." + } + + cdl_option CYGBLD_GLOBAL_LDFLAGS { + display "Global linker flags" + flavor data + no_define + default_value { "-mcpu=cortex-m3 -mthumb -Wl,--gc-sections -Wl,-static -Wl,-n -g -nostdlib" } + description " + This option controls the global linker flags. Individual + packages may define options which override these global flags." + } + } + + cdl_option CYGSEM_HAL_ROM_MONITOR { + display "Behave as a ROM monitor" + flavor bool + default_value 0 + parent CYGPKG_HAL_ROM_MONITOR + requires { CYG_HAL_STARTUP == "ROM" || CYG_HAL_STARTUP == "JTAG" } + requires { CYGDBG_HAL_CRCTABLE_LOCATION == "ROM" } + description " + Enable this option if this program is to be used as a ROM monitor, + i.e. applications will be loaded into RAM on the board, and this + ROM monitor may process exceptions or interrupts generated from the + application. This enables features such as utilizing a separate + interrupt stack when exceptions are generated." + } + + cdl_option CYGSEM_HAL_USE_ROM_MONITOR { + display "Work with a ROM monitor" + flavor booldata + legal_values { "Generic" "GDB_stubs" } + default_value { CYG_HAL_STARTUP == "RAM" ? "GDB_stubs" : 0 } + parent CYGPKG_HAL_ROM_MONITOR + requires { CYG_HAL_STARTUP == "RAM" } + description " + Support can be enabled for different varieties of ROM monitor. + This support changes various eCos semantics such as the encoding + of diagnostic output, or the overriding of hardware interrupt + vectors. + Firstly there is \"Generic\" support which prevents the HAL + from overriding the hardware vectors that it does not use, to + instead allow an installed ROM monitor to handle them. This is + the most basic support which is likely to be common to most + implementations of ROM monitor. + \"GDB_stubs\" provides support when GDB stubs are included in + the ROM monitor or boot ROM." + } + + cdl_component CYGPKG_REDBOOT_HAL_OPTIONS { + display "Redboot HAL options" + flavor none + no_define + parent CYGPKG_REDBOOT + active_if CYGPKG_REDBOOT + description " + This option lists the target's requirements for a valid Redboot + configuration." + + requires { CYGNUM_REDBOOT_FLASH_BASE == 0x64000000 } + + cdl_option CYGPRI_HAL_STM3210E_EVAL_MEM_SEGMENTS { + display "Set RedBoot memory segments" + requires { CYGBLD_REDBOOT_MAX_MEM_SEGMENTS == 3 } + no_define + calculated 2 + description "This CDL option is used to inform RedBoot of the + number of RAM memory segments on this platform." + } + + cdl_option CYGBLD_BUILD_REDBOOT_BIN { + display "Build Redboot ROM binary images" + active_if CYGBLD_BUILD_REDBOOT + default_value 1 + no_define + description "This option enables the conversion of the Redboot ELF + image to binary image formats suitable for ROM programming." + + make -priority 325 { + <PREFIX>/bin/redboot.bin : <PREFIX>/bin/redboot.elf + $(OBJCOPY) --strip-debug $< $(@:.bin=.img) + $(OBJCOPY) -O srec $< $(@:.bin=.srec) + $(OBJCOPY) -O binary $< $@ + } + } + } + + cdl_component CYGBLD_HAL_CORTEXM_STM3210E_EVAL_GDB_STUBS { + display "Create StubROM SREC and binary files" + active_if CYGBLD_BUILD_COMMON_GDB_STUBS + no_define + calculated 1 + requires { CYG_HAL_STARTUP == "ROM" } + + make -priority 325 { + <PREFIX>/bin/stubrom.srec : <PREFIX>/bin/gdb_module.img + $(OBJCOPY) -O srec $< $@ + } + make -priority 325 { + <PREFIX>/bin/stubrom.bin : <PREFIX>/bin/gdb_module.img + $(OBJCOPY) -O binary $< $@ + } + + description "This component causes the ELF image generated by the + build process to be converted to S-Record and binary + files." + } + +} \ No newline at end of file
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/pkgconf/mlt_cortexm_stm3210e_eval_jtag.h @@ -0,0 +1,15 @@ +// eCos memory layout + +#ifndef __ASSEMBLER__ +#include <cyg/infra/cyg_type.h> +#include <stddef.h> + +#endif +#define CYGMEM_REGION_ram (0x68000000) +#define CYGMEM_REGION_ram_SIZE (0x00100000) +#define CYGMEM_REGION_ram_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W) +#ifndef __ASSEMBLER__ +extern char CYG_LABEL_NAME (__heap1) []; +#endif +#define CYGMEM_SECTION_heap1 (CYG_LABEL_NAME (__heap1)) +#define CYGMEM_SECTION_heap1_SIZE (CYGMEM_REGION_ram+CYGMEM_REGION_ram_SIZE - (size_t) CYG_LABEL_NAME (__heap1))
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/pkgconf/mlt_cortexm_stm3210e_eval_jtag.ldi @@ -0,0 +1,36 @@ +// eCos memory layout + +#include <pkgconf/hal.h> +#include <cyg/infra/cyg_type.inc> + +MEMORY +{ + sram : ORIGIN = 0x20000000, LENGTH = 0x00010000-CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE + flash : ORIGIN = 0x08000000, LENGTH = 0x00080000 + rom : ORIGIN = 0x64000000, LENGTH = 0x01000000 + ram : ORIGIN = 0x68000000, LENGTH = 0x00100000 +} + +SECTIONS +{ + SECTIONS_BEGIN + SECTION_rom_vectors (ram, 0x68000000, LMA_EQ_VMA) + SECTION_RELOCS (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_text (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_fini (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_rodata (ram, ALIGN(0x8), LMA_EQ_VMA) + SECTION_rodata1 (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_fixup (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_gcc_except_table (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_eh_frame (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_got (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_data (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_bss (ram, ALIGN (0x8), LMA_EQ_VMA) + CYG_LABEL_DEFN(__heap1) = ALIGN (0x8); + SECTIONS_END +} + +hal_vsr_table = 0x20000000; +hal_virtual_vector_table = hal_vsr_table + 128*4; +hal_startup_stack = 0x20000000 + 1024*64; +
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/pkgconf/mlt_cortexm_stm3210e_eval_ram.h @@ -0,0 +1,21 @@ +// eCos memory layout + +#ifndef __ASSEMBLER__ +#include <cyg/infra/cyg_type.h> +#include <stddef.h> + +#endif +#define CYGMEM_REGION_sram (0x20000000) +#define CYGMEM_REGION_sram_SIZE (0x00010000) +#define CYGMEM_REGION_sram_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W) + +#define CYGMEM_REGION_ram (0x68000000) +#define CYGMEM_REGION_ram_SIZE (0x00100000-CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE) +#define CYGMEM_REGION_ram_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W) + +#ifndef __ASSEMBLER__ +extern char CYG_LABEL_NAME (__heap1) []; +#endif +#define CYGMEM_SECTION_heap1 (CYG_LABEL_NAME (__heap1)) +#define CYGMEM_SECTION_heap1_SIZE (CYGMEM_REGION_ram+CYGMEM_REGION_ram_SIZE - (size_t) CYG_LABEL_NAME (__heap1)) +
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/pkgconf/mlt_cortexm_stm3210e_eval_ram.ldi @@ -0,0 +1,35 @@ +// eCos memory layout + +#include <pkgconf/hal.h> +#include <cyg/infra/cyg_type.inc> + +MEMORY +{ + sram : ORIGIN = 0x20000000, LENGTH = 0x00010000 + flash : ORIGIN = 0x08000000, LENGTH = 0x00080000 + rom : ORIGIN = 0x64000000, LENGTH = 0x01000000 + ram : ORIGIN = 0x68000000, LENGTH = 0x00100000-CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE +} + +SECTIONS +{ + SECTIONS_BEGIN + SECTION_rom_vectors (ram, 0x68008000, LMA_EQ_VMA) + SECTION_RELOCS (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_text (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_fini (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_rodata (ram, ALIGN(0x8), LMA_EQ_VMA) + SECTION_rodata1 (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_fixup (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_gcc_except_table (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_eh_frame (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_got (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_data (ram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_bss (ram, ALIGN (0x8), LMA_EQ_VMA) + CYG_LABEL_DEFN(__heap1) = ALIGN (0x8); + SECTIONS_END +} + +hal_vsr_table = 0x20000000; +hal_virtual_vector_table = hal_vsr_table + 128*4; +hal_startup_stack = 0x68040000;
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/pkgconf/mlt_cortexm_stm3210e_eval_rom.h @@ -0,0 +1,24 @@ +// eCos memory layout + +#ifndef __ASSEMBLER__ +#include <cyg/infra/cyg_type.h> +#include <stddef.h> + +#endif +#define CYGMEM_REGION_sram (0x20000000) +#define CYGMEM_REGION_sram_SIZE (0x00010000-CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE) +#define CYGMEM_REGION_sram_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W) +#define CYGMEM_REGION_flash (0x08000000) +#define CYGMEM_REGION_flash_SIZE (0x00080000) +#define CYGMEM_REGION_flash_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W) +#define CYGMEM_REGION_ram (0x68000000) +#define CYGMEM_REGION_ram_SIZE (0x00100000) +#define CYGMEM_REGION_ram_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W) +#define CYGMEM_REGION_rom (0x64000000) +#define CYGMEM_REGION_rom_SIZE (0x01000000) +#define CYGMEM_REGION_rom_ATTR (CYGMEM_REGION_ATTR_R) +#ifndef __ASSEMBLER__ +extern char CYG_LABEL_NAME (__heap1) []; +#endif +#define CYGMEM_SECTION_heap1 (CYG_LABEL_NAME (__heap1)) +#define CYGMEM_SECTION_heap1_SIZE (CYGMEM_REGION_ram+CYGMEM_REGION_ram_SIZE - (size_t) CYG_LABEL_NAME (__heap1))
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/pkgconf/mlt_cortexm_stm3210e_eval_rom.ldi @@ -0,0 +1,37 @@ +// eCos memory layout + +#include <pkgconf/hal.h> +#include <cyg/infra/cyg_type.inc> + +MEMORY +{ + sram : ORIGIN = 0x20000000, LENGTH = 0x00010000-CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE + flash : ORIGIN = 0x08000000, LENGTH = 0x00080000 + rom : ORIGIN = 0x64000000, LENGTH = 0x01000000 + ram : ORIGIN = 0x68000000, LENGTH = 0x00100000 +} + +SECTIONS +{ + SECTIONS_BEGIN + SECTION_rom_vectors (flash, 0x08000000, LMA_EQ_VMA) + SECTION_RELOCS (flash, ALIGN (0x8), LMA_EQ_VMA) + SECTION_text (flash, ALIGN (0x8), LMA_EQ_VMA) + SECTION_fini (flash, ALIGN (0x8), LMA_EQ_VMA) + SECTION_rodata (flash, ALIGN (0x8), LMA_EQ_VMA) + SECTION_rodata1 (flash, ALIGN (0x8), LMA_EQ_VMA) + SECTION_fixup (flash, ALIGN (0x8), LMA_EQ_VMA) + SECTION_gcc_except_table (flash, ALIGN (0x8), LMA_EQ_VMA) + SECTION_eh_frame (flash, ALIGN (0x8), LMA_EQ_VMA) + SECTION_got (flash, ALIGN (0x8), LMA_EQ_VMA) + SECTION_data (ram, 0x68000000, FOLLOWING (.got)) + SECTION_bss (ram, ALIGN (0x8), LMA_EQ_VMA) + CYG_LABEL_DEFN(__heap1) = ALIGN (0x8); + SECTIONS_END +} + +hal_vsr_table = 0x20000000; +hal_virtual_vector_table = hal_vsr_table + 128*4; +hal_startup_stack = 0x20000000 + 1024*64; + +
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/pkgconf/mlt_cortexm_stm3210e_eval_sram.h @@ -0,0 +1,21 @@ +// eCos memory layout + +#ifndef __ASSEMBLER__ +#include <cyg/infra/cyg_type.h> +#include <stddef.h> + +#endif +#define CYGMEM_REGION_sram (0x20000000) +#define CYGMEM_REGION_sram_SIZE (0x00010000-CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE) +#define CYGMEM_REGION_sram_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W) + +#define CYGMEM_REGION_ram (0x68000000) +#define CYGMEM_REGION_ram_SIZE (0x00100000) +#define CYGMEM_REGION_ram_ATTR (CYGMEM_REGION_ATTR_R | CYGMEM_REGION_ATTR_W) + +#ifndef __ASSEMBLER__ +extern char CYG_LABEL_NAME (__heap1) []; +#endif +#define CYGMEM_SECTION_heap1 (CYG_LABEL_NAME (__heap1)) +#define CYGMEM_SECTION_heap1_SIZE (CYGMEM_REGION_sram+CYGMEM_REGION_sram_SIZE - (size_t) CYG_LABEL_NAME (__heap1)) +
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/pkgconf/mlt_cortexm_stm3210e_eval_sram.ldi @@ -0,0 +1,35 @@ +// eCos memory layout + +#include <pkgconf/hal.h> +#include <cyg/infra/cyg_type.inc> + +MEMORY +{ + sram : ORIGIN = 0x20000000, LENGTH = 0x00010000-CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE + flash : ORIGIN = 0x08000000, LENGTH = 0x00080000 + rom : ORIGIN = 0x64000000, LENGTH = 0x01000000 + ram : ORIGIN = 0x68000000, LENGTH = 0x00100000 +} + +SECTIONS +{ + SECTIONS_BEGIN + SECTION_rom_vectors (sram, 0x20000400, LMA_EQ_VMA) + SECTION_RELOCS (sram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_text (sram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_fini (sram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_rodata (sram, ALIGN(0x8), LMA_EQ_VMA) + SECTION_rodata1 (sram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_fixup (sram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_gcc_except_table (sram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_eh_frame (sram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_got (sram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_data (sram, ALIGN (0x8), LMA_EQ_VMA) + SECTION_bss (sram, ALIGN (0x8), LMA_EQ_VMA) + CYG_LABEL_DEFN(__heap1) = ALIGN (0x8); + SECTIONS_END +} + +hal_vsr_table = 0x20000000; +hal_virtual_vector_table = hal_vsr_table + 128*4; +hal_startup_stack = 0x20010000;
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/plf_arch.h @@ -0,0 +1,60 @@ +#ifndef CYGONCE_HAL_PLF_ARCH_H +#define CYGONCE_HAL_PLF_ARCH_H +//============================================================================= +// +// plf_arch.h +// +// Platform specific architecture overrides +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Purpose: STM3210E EVAL platform specific architecture overrides +// Description: +// Usage: #include <cyg/hal/plf_arch.h> +// +//####DESCRIPTIONEND#### +// +//============================================================================= + +#include <pkgconf/hal.h> +#include <pkgconf/hal_cortexm_stm32_stm3210e_eval.h> + + +//============================================================================= + +//----------------------------------------------------------------------------- +// end of plf_arch.h +#endif // CYGONCE_HAL_PLF_ARCH_H
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/plf_intr.h @@ -0,0 +1,60 @@ +#ifndef CYGONCE_HAL_PLF_INTR_H +#define CYGONCE_HAL_PLF_INTR_H +//============================================================================= +// +// plf_intr.h +// +// Platform specific interrupt overrides +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Purpose: STM3210E EVAL platform specific interrupt overrides +// Description: +// Usage: #include <cyg/hal/plf_intr.h> +// +//####DESCRIPTIONEND#### +// +//============================================================================= + +#include <pkgconf/hal.h> +#include <pkgconf/hal_cortexm_stm32_stm3210e_eval.h> + + +//============================================================================= + +//----------------------------------------------------------------------------- +// end of plf_intr.h +#endif // CYGONCE_HAL_PLF_INTR_H
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/include/plf_io.h @@ -0,0 +1,74 @@ +#ifndef CYGONCE_HAL_PLF_IO_H +#define CYGONCE_HAL_PLF_IO_H +//============================================================================= +// +// plf_io.h +// +// Platform specific registers +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Purpose: STM3210E EVAL platform specific registers +// Description: +// Usage: #include <cyg/hal/plf_io.h> +// +//####DESCRIPTIONEND#### +// +//============================================================================= + +#include <pkgconf/hal.h> +#include <pkgconf/hal_cortexm_stm32_stm3210e_eval.h> + +//============================================================================= +// Memory access checks. +// +// Accesses to areas not backed by real devices or memory can cause +// the CPU to hang. These macros allow the GDB stubs to avoid making +// accidental accesses to these areas. + +__externC int cyg_hal_stub_permit_data_access( CYG_ADDRESS addr, cyg_uint32 count ); + +#define CYG_HAL_STUB_PERMIT_DATA_READ(_addr_, _count_) cyg_hal_stub_permit_data_access( _addr_, _count_ ) + +#define CYG_HAL_STUB_PERMIT_DATA_WRITE(_addr_, _count_ ) cyg_hal_stub_permit_data_access( _addr_, _count_ ) + +//============================================================================= + +#define HAL_AM29XXXXX_UNCACHED_ADDRESS(__addr) (__addr) + +//----------------------------------------------------------------------------- +// end of plf_io.h +#endif // CYGONCE_HAL_PLF_IO_H
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/misc/redboot_JTAG.ecm @@ -0,0 +1,85 @@ +cdl_savefile_version 1; +cdl_savefile_command cdl_savefile_version {}; +cdl_savefile_command cdl_savefile_command {}; +cdl_savefile_command cdl_configuration { description hardware template package }; +cdl_savefile_command cdl_package { value_source user_value wizard_value inferred_value }; +cdl_savefile_command cdl_component { value_source user_value wizard_value inferred_value }; +cdl_savefile_command cdl_option { value_source user_value wizard_value inferred_value }; +cdl_savefile_command cdl_interface { value_source user_value wizard_value inferred_value }; + +cdl_configuration eCos { + description "" ; + template redboot ; + + package CYGPKG_IO_FLASH current ; +}; + +cdl_option CYGFUN_LIBC_STRING_BSD_FUNCS { + inferred_value 0 +}; + +cdl_option CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE { + user_value 4096 +}; + +cdl_option CYGDBG_HAL_COMMON_INTERRUPTS_SAVE_MINIMUM_CONTEXT { + user_value 0 +}; + +cdl_option CYGDBG_HAL_COMMON_CONTEXT_SAVE_MINIMUM { + inferred_value 0 +}; + +cdl_option CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS { + inferred_value 1 +}; + +cdl_option CYGSEM_HAL_ROM_MONITOR { + inferred_value 1 +}; + +cdl_option CYGSEM_HAL_USE_ROM_MONITOR { + inferred_value 0 0 +}; + +cdl_component CYG_HAL_STARTUP { + user_value JTAG +}; + +cdl_component CYGBLD_BUILD_REDBOOT { + user_value 1 +}; + +cdl_option CYGBLD_BUILD_REDBOOT_WITH_CACHES { + user_value 0 +}; + +cdl_option CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG { + user_value 1 +}; + +cdl_option CYGBLD_BUILD_REDBOOT_WITH_EXEC { + user_value 0 +}; + +cdl_option CYGBLD_ISO_STRTOK_R_HEADER { + inferred_value 1 <cyg/libc/string/string.h> +}; + +cdl_option CYGBLD_ISO_STRING_LOCALE_FUNCS_HEADER { + inferred_value 1 <cyg/libc/string/string.h> +}; + +cdl_option CYGBLD_ISO_STRING_BSD_FUNCS_HEADER { + inferred_value 1 <cyg/libc/string/bsdstring.h> +}; + +cdl_option CYGBLD_ISO_STRING_MEMFUNCS_HEADER { + inferred_value 1 <cyg/libc/string/string.h> +}; + +cdl_option CYGBLD_ISO_STRING_STRFUNCS_HEADER { + inferred_value 1 <cyg/libc/string/string.h> +}; + +
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/misc/redboot_ROM.ecm @@ -0,0 +1,85 @@ +cdl_savefile_version 1; +cdl_savefile_command cdl_savefile_version {}; +cdl_savefile_command cdl_savefile_command {}; +cdl_savefile_command cdl_configuration { description hardware template package }; +cdl_savefile_command cdl_package { value_source user_value wizard_value inferred_value }; +cdl_savefile_command cdl_component { value_source user_value wizard_value inferred_value }; +cdl_savefile_command cdl_option { value_source user_value wizard_value inferred_value }; +cdl_savefile_command cdl_interface { value_source user_value wizard_value inferred_value }; + +cdl_configuration eCos { + description "" ; + template redboot ; + + package CYGPKG_IO_FLASH current ; +}; + +cdl_option CYGFUN_LIBC_STRING_BSD_FUNCS { + inferred_value 0 +}; + +cdl_option CYGNUM_HAL_COMMON_INTERRUPTS_STACK_SIZE { + user_value 4096 +}; + +cdl_option CYGDBG_HAL_COMMON_INTERRUPTS_SAVE_MINIMUM_CONTEXT { + user_value 0 +}; + +cdl_option CYGDBG_HAL_COMMON_CONTEXT_SAVE_MINIMUM { + inferred_value 0 +}; + +cdl_option CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS { + inferred_value 1 +}; + +cdl_option CYGSEM_HAL_ROM_MONITOR { + inferred_value 1 +}; + +cdl_option CYGSEM_HAL_USE_ROM_MONITOR { + inferred_value 0 0 +}; + +cdl_component CYG_HAL_STARTUP { + user_value ROM +}; + +cdl_component CYGBLD_BUILD_REDBOOT { + user_value 1 +}; + +cdl_option CYGBLD_BUILD_REDBOOT_WITH_CACHES { + user_value 0 +}; + +cdl_option CYGSEM_REDBOOT_FLASH_COMBINED_FIS_AND_CONFIG { + user_value 1 +}; + +cdl_option CYGBLD_BUILD_REDBOOT_WITH_EXEC { + user_value 0 +}; + +cdl_option CYGBLD_ISO_STRTOK_R_HEADER { + inferred_value 1 <cyg/libc/string/string.h> +}; + +cdl_option CYGBLD_ISO_STRING_LOCALE_FUNCS_HEADER { + inferred_value 1 <cyg/libc/string/string.h> +}; + +cdl_option CYGBLD_ISO_STRING_BSD_FUNCS_HEADER { + inferred_value 1 <cyg/libc/string/bsdstring.h> +}; + +cdl_option CYGBLD_ISO_STRING_MEMFUNCS_HEADER { + inferred_value 1 <cyg/libc/string/string.h> +}; + +cdl_option CYGBLD_ISO_STRING_STRFUNCS_HEADER { + inferred_value 1 <cyg/libc/string/string.h> +}; + +
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/src/stm3210e_eval_flash.c @@ -0,0 +1,107 @@ +/*========================================================================== +// +// stm3210e_eval_flash.c +// +// Cortex-M3 STM3210E EVAL Flash setup +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Description: +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/hal.h> +#include <pkgconf/hal_cortexm.h> +#include <pkgconf/hal_cortexm_stm32.h> +#include <pkgconf/hal_cortexm_stm32_stm3210e_eval.h> +#ifdef CYGPKG_KERNEL +#include <pkgconf/kernel.h> +#endif + +#include <cyg/io/flash.h> +#include <cyg/io/flash_dev.h> +#include <cyg/hal/hal_io.h> + + +//-------------------------------------------------------------------------- +// Internal flash + +#include <cyg/io/stm32_flash.h> + +cyg_stm32_flash_dev hal_stm32_flash_priv; + +CYG_FLASH_DRIVER(hal_stm32_flash, + &cyg_stm32_flash_funs, + 0, + 0x08000000, + 0, + 0, + 0, + &hal_stm32_flash_priv +); + +//-------------------------------------------------------------------------- +// There is a Spansion S29GL128P90FFIR20 or a NUMONYX equivalent. +// These are AMD compatible and with CFI can all be handled by the AMD +// driver. + + +#include <cyg/io/am29xxxxx_dev.h> + +static const CYG_FLASH_FUNS(hal_stm3210e_flash_amd_funs, + &cyg_am29xxxxx_init_cfi_16, + &cyg_flash_devfn_query_nop, + &cyg_am29xxxxx_erase_16, + &cyg_am29xxxxx_program_16, + (int (*)(struct cyg_flash_dev*, const cyg_flashaddr_t, void*, size_t))0, + &cyg_flash_devfn_lock_nop, + &cyg_flash_devfn_unlock_nop); + +static const cyg_am29xxxxx_dev hal_stm3210e_flash_priv; + +CYG_FLASH_DRIVER(hal_stm3210e_flash, + &hal_stm3210e_flash_amd_funs, + 0, + 0x64000000, + 0, + 0, + hal_stm3210e_flash_priv.block_info, + &hal_stm3210e_flash_priv); + +//-------------------------------------------------------------------------- +// EOF stm3210e_eval_flash.c
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/stm3210e_eval/current/src/stm3210e_eval_misc.c @@ -0,0 +1,249 @@ +/*========================================================================== +// +// stm3210e_eval_misc.c +// +// Cortex-M3 STM3210E EVAL HAL functions +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Description: +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/hal.h> +#include <pkgconf/hal_cortexm.h> +#include <pkgconf/hal_cortexm_stm32.h> +#include <pkgconf/hal_cortexm_stm32_stm3210e_eval.h> +#ifdef CYGPKG_KERNEL +#include <pkgconf/kernel.h> +#endif + +#include <cyg/infra/diag.h> +#include <cyg/infra/cyg_type.h> +#include <cyg/infra/cyg_trac.h> // tracing macros +#include <cyg/infra/cyg_ass.h> // assertion macros + +#include <cyg/hal/hal_arch.h> // HAL header +#include <cyg/hal/hal_intr.h> // HAL header + + +//========================================================================== +// System init +// +// This is run to set up the basic system, including GPIO setting, +// clock feeds, power supply, and memory initialization. This code +// runs before the DATA is copied from ROM and the BSS cleared, hence +// it cannot make use of static variables or data tables. + +__externC void hal_system_init( void ) +{ + CYG_ADDRESS base; + +#if defined(CYG_HAL_STARTUP_ROM) | defined(CYG_HAL_STARTUP_SRAM) + + // Enable peripheral clocks in RCC + + base = CYGHWR_HAL_STM32_RCC; + + HAL_WRITE_UINT32(base+CYGHWR_HAL_STM32_RCC_AHBENR, + CYGHWR_HAL_STM32_RCC_AHBENR_FSMC | + CYGHWR_HAL_STM32_RCC_AHBENR_FLITF| + CYGHWR_HAL_STM32_RCC_AHBENR_SRAM ); + + HAL_WRITE_UINT32(base+CYGHWR_HAL_STM32_RCC_APB2ENR, + CYGHWR_HAL_STM32_RCC_APB2ENR_IOPA | + CYGHWR_HAL_STM32_RCC_APB2ENR_IOPB | + CYGHWR_HAL_STM32_RCC_APB2ENR_IOPC | + CYGHWR_HAL_STM32_RCC_APB2ENR_IOPD | + CYGHWR_HAL_STM32_RCC_APB2ENR_IOPE | + CYGHWR_HAL_STM32_RCC_APB2ENR_IOPF | + CYGHWR_HAL_STM32_RCC_APB2ENR_IOPG ); + + // Set all unused GPIO lines to input with pull down to prevent + // them floating and annoying any external hardware. + + base = CYGHWR_HAL_STM32_GPIOA; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRL, 0x88888888 ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRH, 0x88888888 ); + + base = CYGHWR_HAL_STM32_GPIOB; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRL, 0x88888888 ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRH, 0x88888888 ); + + base = CYGHWR_HAL_STM32_GPIOC; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRL, 0x88888888 ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRH, 0x88888888 ); + + // Set up GPIO lines for external bus + + base = CYGHWR_HAL_STM32_GPIOD; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRL, 0x44bb44bb ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRH, 0xbbbbbbbb ); + + base = CYGHWR_HAL_STM32_GPIOE; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRL, 0xbbbbb4bb ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRH, 0xbbbbbbbb ); + + base = CYGHWR_HAL_STM32_GPIOF; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRL, 0x44bbbbbb ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRH, 0xbbbb4444 ); + + base = CYGHWR_HAL_STM32_GPIOG; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRL, 0x44bbbbbb ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_GPIO_CRH, 0x44444bb4 ); + + + // Set up FSMC NOR/SRAM bank 2 for NOR Flash + + base = CYGHWR_HAL_STM32_FSMC; + + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FSMC_BCR2, 0x00001059 ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FSMC_BTR2, 0x10000705 ); + + // Set up FSMC NOR/SRAM bank 3 for SRAM + + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FSMC_BCR3, 0x00001011 ); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FSMC_BTR3, 0x00000200 ); + +#endif + + // Enable flash prefetch buffer and set latency to 2 wait states. + { + cyg_uint32 acr; + + base = CYGHWR_HAL_STM32_FLASH; + + HAL_READ_UINT32( base+CYGHWR_HAL_STM32_FLASH_ACR, acr ); + acr |= CYGHWR_HAL_STM32_FLASH_ACR_PRFTBE; + acr |= CYGHWR_HAL_STM32_FLASH_ACR_LATENCY(2); + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_FLASH_ACR, acr ); + } +} + +//========================================================================== + +__externC void hal_platform_init( void ) +{ +} + +//========================================================================== + +#ifdef CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS + +#include CYGHWR_MEMORY_LAYOUT_H + +//-------------------------------------------------------------------------- +// Accesses to areas not backed by real devices or memory can cause +// the CPU to hang. +// +// The following table defines the memory areas that GDB is allowed to +// touch. All others are disallowed. +// This table needs to be kept up to date with the set of memory areas +// that are available on the board. + +static struct +{ + CYG_ADDRESS start; // Region start address + CYG_ADDRESS end; // End address (last byte) +} hal_data_access[] = +{ + { CYGMEM_REGION_ram, CYGMEM_REGION_ram+CYGMEM_REGION_ram_SIZE-1 }, // External SRAM +#ifdef CYGMEM_REGION_sram + { CYGMEM_REGION_sram, CYGMEM_REGION_sram+CYGMEM_REGION_sram_SIZE-1 }, // On-chip SRAM +#endif +#ifdef CYGMEM_REGION_flash + { CYGMEM_REGION_flash, CYGMEM_REGION_flash+CYGMEM_REGION_flash_SIZE-1 }, // On-chip flash +#endif +#ifdef CYGMEM_REGION_rom + { CYGMEM_REGION_rom, CYGMEM_REGION_rom+CYGMEM_REGION_rom_SIZE-1 }, // External flash +#endif + { 0xE0000000, 0x00000000-1 }, // Cortex-M peripherals + { 0x40000000, 0x60000000-1 }, // STM32 peripherals +}; + +__externC int cyg_hal_stub_permit_data_access( CYG_ADDRESS addr, cyg_uint32 count ) +{ + int i; + for( i = 0; i < sizeof(hal_data_access)/sizeof(hal_data_access[0]); i++ ) + { + if( (addr >= hal_data_access[i].start) && + (addr+count) <= hal_data_access[i].end) + return true; + } + return false; +} + +#endif // CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS + +//========================================================================== + +#ifdef CYGPKG_REDBOOT +#include <redboot.h> +#include CYGHWR_MEMORY_LAYOUT_H + +//-------------------------------------------------------------------------- +// Memory layout +// +// We report the on-chip SRAM and external SRAM. + + +void +cyg_plf_memory_segment(int seg, unsigned char **start, unsigned char **end) +{ + switch (seg) { + case 0: + *start = (unsigned char *)CYGMEM_REGION_ram; + *end = (unsigned char *)(CYGMEM_REGION_ram + CYGMEM_REGION_ram_SIZE); + break; +#ifdef CYGMEM_REGION_sram + case 1: + *start = (unsigned char *)CYGMEM_REGION_sram; + *end = (unsigned char *)(CYGMEM_REGION_sram + CYGMEM_REGION_sram_SIZE); + break; +#endif + default: + *start = *end = NO_MEMORY; + break; + } +} // cyg_plf_memory_segment() + +#endif // CYGPKG_REDBOOT + + +//========================================================================== +// EOF stm3210e_eval_misc.c
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/ChangeLog @@ -0,0 +1,67 @@ +2008-10-14 Nick Garnett <nickg@ecoscentric.com> + + * tests/timers.c: Add ifdefs to avoid compiling tests when not all + packages or components are present. + +2008-10-10 Nick Garnett <nickg@ecoscentric.com> + + * cdl/hal_cortexm_stm32.cdl: Only build tests if the kernel is present. + + * include/var_io.h (CYGHWR_HAL_STM32_GPIO_CFG): Add PULLUP bit to mask. + + * tests/timers.c (timers_test): Terminate with PASS_FINISH rather + than just FINISH. + +2008-10-08 Nick Garnett <nickg@ecoscentric.com> + + * include/var_intr.h (CYGNUM_HAL_ISR_MAX, CYGNUM_HAL_VSR_MAX): Fix + definition of these values. + + * tests/timers.c: Fix to run for maximum duration of 2 minutes. + +2008-10-06 Nick Garnett <nickg@ecoscentric.com> + + * cdl/hal_cortexm_stm32.cdl: + * include/variant.inc: + * include/var_arch.h: + * include/var_intr.h: + * include/var_io.h: + * include/hal_cache.h: + * include/hal_diag.h: + * include/plf_stub.h: + * src/hal_diag.c: + * src/stm32_misc.c: + New package -- ST STM32 variant HAL. + +//=========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//===========================================================================
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/cdl/hal_cortexm_stm32.cdl @@ -0,0 +1,231 @@ +##========================================================================== +## +## hal_cortexm_stm32.cdl +## +## Cortex-M STM32 variant HAL configuration data +## +##========================================================================== +######ECOSGPLCOPYRIGHTBEGIN#### +## ------------------------------------------- +## This file is part of eCos, the Embedded Configurable Operating System. +## Copyright (C) 2008 eCosCentric Limited. +## +## eCos 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 2 or (at your option) any later version. +## +## eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +## 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +## +## As a special exception, if other files instantiate templates or use macros +## or inline functions from this file, or you compile this file and link it +## with other works to produce a work based on this file, this file does not +## by itself cause the resulting work to be covered by the GNU General Public +## License. However the source code for this file must still be made available +## in accordance with section (3) of the GNU General Public License. +## +## This exception does not invalidate any other reasons why a work based on +## this file might be covered by the GNU General Public License. +## ------------------------------------------- +######ECOSGPLCOPYRIGHTEND#### +##========================================================================== +#######DESCRIPTIONBEGIN#### +## +## Author(s): nickg +## Date: 2008-07-30 +## +######DESCRIPTIONEND#### +## +##========================================================================== + +cdl_package CYGPKG_HAL_CORTEXM_STM32 { + display "Cortex-M3 STM32 Variant" + parent CYGPKG_HAL_CORTEXM + hardware + include_dir cyg/hal + define_header hal_cortexm_stm32.h + description " + This package provides generic support for the ST Cortex-M based STM32 + microcontroller family. + It is also necessary to select a variant and platform HAL package." + + compile hal_diag.c stm32_misc.c + + implements CYGINT_HAL_DEBUG_GDB_STUBS + implements CYGINT_HAL_DEBUG_GDB_STUBS_BREAK + implements CYGINT_HAL_VIRTUAL_VECTOR_SUPPORT + implements CYGINT_HAL_VIRTUAL_VECTOR_COMM_BAUD_SUPPORT + implements CYGINT_PROFILE_HAL_TIMER + + requires { CYGHWR_HAL_CORTEXM == "M3" } + + cdl_option CYGHWR_HAL_CORTEXM_STM32 { + display "STM32 variant in use" + flavor data + default_value {"F103ZE"} + legal_values {"F103RC" "F103VC" "F103ZC" + "F103RD" "F103VD" "F103ZD" + "F103RE" "F103VE" "F103ZE" } + description "The STM32 has several variants, the main differences + being in the size of on-chip FLASH and SRAM + and numbers of some peripherals. This option + allows the platform HAL to select the specific + microcontroller fitted." + } + + cdl_option CYGNUM_HAL_CORTEXM_PRIORITY_LEVEL_BITS { + display "CPU priority levels" + flavor data + calculated 4 + description "This option defines the number of bits used to + encode the exception priority levels that this + variant of the Cortex-M CPU implements." + } + + + + cdl_component CYGHWR_HAL_CORTEXM_STM32_CLOCK { + display "Clock setup calculations" + default_value 1 + + cdl_option CYGHWR_HAL_CORTEXM_STM32_CLOCK_PLL_SOURCE { + display "PLL input source" + flavor data + default_value { "HSE" } + legal_values { "HSI_HALF" "HSE" "HSE_HALF" } + } + + cdl_option CYGHWR_HAL_CORTEXM_STM32_CLOCK_PLL_MUL { + display "PLL multiplier" + flavor data + default_value 9 + legal_values 2 to 16 + } + + cdl_option CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV { + display "HCLK divider" + flavor data + default_value 1 + legal_values { 1 2 4 8 16 64 128 256 512 } + } + + cdl_option CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK1_DIV { + display "PCLK1 divider" + flavor data + default_value 2 + legal_values { 1 2 4 8 16 } + } + + cdl_option CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK2_DIV { + display "PCLK2 divider" + flavor data + default_value 1 + legal_values { 1 2 4 8 16 } + } + } + + cdl_option CYGNUM_HAL_KERNEL_COUNTERS_CLOCK_ISR_DEFAULT_PRIORITY { + display "Clock interrupt ISR priority" + flavor data + calculated 0xE0 + description "Set clock ISR priority to lowest priority." + } + + cdl_component CYGNUM_HAL_RTC_CONSTANTS { + display "Real-time clock constants" + flavor none + no_define + cdl_option CYGNUM_HAL_RTC_NUMERATOR { + display "Real-time clock numerator" + flavor data + default_value 1000000000 + } + cdl_option CYGNUM_HAL_RTC_DENOMINATOR { + display "Real-time clock denominator" + flavor data + default_value 100 + } + cdl_option CYGNUM_HAL_RTC_PERIOD { + display "Real-time clock period" + flavor data + default_value 1000000 / CYGNUM_HAL_RTC_DENOMINATOR + description "The period defined here is something of a fake, it is expressed + in terms of a notional 1MHz clock. The value actually installed + in the hardware is calculated from the current settings of the + clock generation hardware." + } + } + + + cdl_interface CYGINT_HAL_STM32_UART0 { + display "Platform has UART0 serial port" + description "The platform has a socket on UART0." + } + + cdl_interface CYGINT_HAL_STM32_UART1 { + display "Platform has UART1 serial port" + description "The platform has a socket on UART1." + } + + cdl_interface CYGINT_HAL_STM32_UART2 { + display "Platform has UART2 serial port" + description "The platform has a socket on UART2." + } + + cdl_interface CYGINT_HAL_STM32_UART3 { + display "Platform has UART3 serial port" + description "The platform has a socket on UART3." + } + + cdl_interface CYGINT_HAL_STM32_UART4 { + display "Platform has UART4 serial port" + description "The platform has a socket on UART4." + } + + cdl_component CYGPKG_HAL_CORTEXM_STM32_OPTIONS { + display "Build options" + flavor none + description " + Package specific build options including control over + compiler flags used only in building this package." + + cdl_option CYGPKG_HAL_CORTEXM_STM32_CFLAGS_ADD { + display "Additional compiler flags" + flavor data + no_define + default_value { "" } + description " + This option modifies the set of compiler flags for + building the STM32 variant HAL package. These flags are used + in addition to the set of global flags." + } + + cdl_option CYGPKG_HAL_CORTEXM_STM32_CFLAGS_REMOVE { + display "Suppressed compiler flags" + flavor data + no_define + default_value { "" } + description " + This option modifies the set of compiler flags for + building the STM32 variant HAL package. These flags are removed from + the set of global flags if present." + } + } + + cdl_option CYGPKG_HAL_CORTEXM_STM32_TESTS { + display "STM32 tests" + active_if CYGPKG_KERNEL + flavor data + no_define + calculated { "tests/timers" } + description " + This option specifies the set of tests for the STM32 HAL." + } + +} \ No newline at end of file
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/include/hal_cache.h @@ -0,0 +1,193 @@ +#ifndef CYGONCE_HAL_CACHE_H +#define CYGONCE_HAL_CACHE_H + +//============================================================================= +// +// hal_cache.h +// +// HAL cache control API +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc. +// Copyright (C) 2004, 2005, 2006, 2008 eCosCentric Limited +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= +//#####DESCRIPTIONBEGIN#### +// +// Author(s): jlarmour +// Contributors: +// Date: 2004-07-23 +// Purpose: Cache control API +// Description: The macros defined here provide the HAL APIs for handling +// cache control operations. +// +// For the STM32, these are empty macros as there +// is no cache. +// Usage: +// #include <cyg/hal/hal_cache.h> +// ... +// +// +//####DESCRIPTIONEND#### +// +//============================================================================= + +#include <cyg/infra/cyg_type.h> + +//----------------------------------------------------------------------------- +// Cache dimensions + +// Data cache +//#define HAL_DCACHE_SIZE 0 // Size of data cache in bytes +//#define HAL_DCACHE_LINE_SIZE 0 // Size of a data cache line +//#define HAL_DCACHE_WAYS 0 // Associativity of the cache + +// Instruction cache +//#define HAL_ICACHE_SIZE 0 // Size of cache in bytes +//#define HAL_ICACHE_LINE_SIZE 0 // Size of a cache line +//#define HAL_ICACHE_WAYS 0 // Associativity of the cache + +//#define HAL_DCACHE_SETS (HAL_DCACHE_SIZE/(HAL_DCACHE_LINE_SIZE*HAL_DCACHE_WAYS)) +//#define HAL_ICACHE_SETS (HAL_ICACHE_SIZE/(HAL_ICACHE_LINE_SIZE*HAL_ICACHE_WAYS)) + +//----------------------------------------------------------------------------- +// Global control of data cache + +// Enable the data cache +#define HAL_DCACHE_ENABLE() + +// Disable the data cache +#define HAL_DCACHE_DISABLE() + +// Invalidate the entire cache +#define HAL_DCACHE_INVALIDATE_ALL() + +// Synchronize the contents of the cache with memory. +#define HAL_DCACHE_SYNC() + +// Purge contents of data cache +#define HAL_DCACHE_PURGE_ALL() + +// Query the state of the data cache (does not affect the caching) +#define HAL_DCACHE_IS_ENABLED(_state_) \ + CYG_MACRO_START \ + (_state_) = 0; \ + CYG_MACRO_END + +// Set the data cache refill burst size +//#define HAL_DCACHE_BURST_SIZE(_size_) + +// Set the data cache write mode +//#define HAL_DCACHE_WRITE_MODE( _mode_ ) + +//#define HAL_DCACHE_WRITETHRU_MODE 0 +//#define HAL_DCACHE_WRITEBACK_MODE 1 + +// Load the contents of the given address range into the data cache +// and then lock the cache so that it stays there. +//#define HAL_DCACHE_LOCK(_base_, _size_) + +// Undo a previous lock operation +//#define HAL_DCACHE_UNLOCK(_base_, _size_) + +// Unlock entire cache +//#define HAL_DCACHE_UNLOCK_ALL() + +//----------------------------------------------------------------------------- +// Data cache line control + +// Allocate cache lines for the given address range without reading its +// contents from memory. +//#define HAL_DCACHE_ALLOCATE( _base_ , _size_ ) + +// Write dirty cache lines to memory and invalidate the cache entries +// for the given address range. +//#define HAL_DCACHE_FLUSH( _base_ , _size_ ) + +// Invalidate cache lines in the given range without writing to memory. +//#define HAL_DCACHE_INVALIDATE( _base_ , _size_ ) + +// Write dirty cache lines to memory for the given address range. +//#define HAL_DCACHE_STORE( _base_ , _size_ ) + +// Preread the given range into the cache with the intention of reading +// from it later. +//#define HAL_DCACHE_READ_HINT( _base_ , _size_ ) + +// Preread the given range into the cache with the intention of writing +// to it later. +//#define HAL_DCACHE_WRITE_HINT( _base_ , _size_ ) + +// Allocate and zero the cache lines associated with the given range. +//#define HAL_DCACHE_ZERO( _base_ , _size_ ) + +//----------------------------------------------------------------------------- +// Global control of Instruction cache + +// Enable the instruction cache +#define HAL_ICACHE_ENABLE() + +// Disable the instruction cache +#define HAL_ICACHE_DISABLE() + +// Invalidate the entire cache +#define HAL_ICACHE_INVALIDATE_ALL() + +// Synchronize the contents of the cache with memory. +#define HAL_ICACHE_SYNC() + +// Query the state of the instruction cache (does not affect the caching) +#define HAL_ICACHE_IS_ENABLED(_state_) \ + CYG_MACRO_START \ + (_state_) = 0; \ + CYG_MACRO_END + +// Set the instruction cache refill burst size +//#define HAL_ICACHE_BURST_SIZE(_size_) + +// Load the contents of the given address range into the instruction cache +// and then lock the cache so that it stays there. +//#define HAL_ICACHE_LOCK(_base_, _size_) + +// Undo a previous lock operation +//#define HAL_ICACHE_UNLOCK(_base_, _size_) + +// Unlock entire cache +//#define HAL_ICACHE_UNLOCK_ALL() + +//----------------------------------------------------------------------------- +// Instruction cache line control + +// Invalidate cache lines in the given range without writing to memory. +//#define HAL_ICACHE_INVALIDATE( _base_ , _size_ ) + +//----------------------------------------------------------------------------- +#endif // ifndef CYGONCE_HAL_CACHE_H +// End of hal_cache.h
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/include/hal_diag.h @@ -0,0 +1,89 @@ +#ifndef CYGONCE_HAL_DIAG_H +#define CYGONCE_HAL_DIAG_H +//============================================================================= +// +// hal_diag.h +// +// HAL diagnostics +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Purpose: HAL diagnostics +// Description: +// Usage: #include <cyg/hal/var_io.h> +// +//####DESCRIPTIONEND#### +// +//============================================================================= + +#include <pkgconf/hal.h> + +#include <cyg/infra/cyg_type.h> + +#include <cyg/hal/hal_if.h> + +//----------------------------------------------------------------------------- + +#if defined(CYGSEM_HAL_VIRTUAL_VECTOR_DIAG) + +#define HAL_DIAG_INIT() hal_if_diag_init() +#define HAL_DIAG_WRITE_CHAR(_c_) hal_if_diag_write_char(_c_) +#define HAL_DIAG_READ_CHAR(_c_) hal_if_diag_read_char(&_c_) + +#else + +__externC void hal_stm32_diag_init(void); +__externC void hal_stm32_diag_putc(char); +__externC cyg_uint8 hal_stm32_diag_getc(void); + +# ifndef HAL_DIAG_INIT +# define HAL_DIAG_INIT() hal_stm32_diag_init() +# endif + +# ifndef HAL_DIAG_WRITE_CHAR +# define HAL_DIAG_WRITE_CHAR(__c) hal_stm32_diag_putc(__c) +# endif + +# ifndef HAL_DIAG_READ_CHAR +# define HAL_DIAG_READ_CHAR(__c) (__c) = hal_stm32_diag_getc() +# endif + +#endif + + +//----------------------------------------------------------------------------- +// end of hal_diag.h +#endif // CYGONCE_HAL_DIAG_H
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/include/plf_stub.h @@ -0,0 +1,87 @@ +#ifndef CYGONCE_HAL_PLF_STUB_H +#define CYGONCE_HAL_PLF_STUB_H + +//============================================================================= +// +// plf_stub.h +// +// Platform header for GDB stub support. +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc. +// Copyright (C) 2004, 2005, 2006, 2008 eCosCentric Ltd. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Contributors:jskov, gthomas, jlarmour +// Date: 2008-07-30 +// Purpose: Platform HAL stub support for STM32 variant boards. +// Usage: #include <cyg/hal/plf_stub.h> +// +//####DESCRIPTIONEND#### +// +//============================================================================= + +#include <pkgconf/hal.h> +#include CYGBLD_HAL_PLATFORM_H + +#ifdef CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS + +#include <cyg/infra/cyg_type.h> // CYG_UNUSED_PARAM + +#include <cyg/hal/cortexm_stub.h> // architecture stub support + +#include <cyg/hal/hal_io.h> + +//---------------------------------------------------------------------------- +// Define some platform specific communication details. This is mostly +// handled by hal_if now, but we need to make sure the comms tables are +// properly initialized. + +__externC void cyg_hal_plf_comms_init(void); + +#define HAL_STUB_PLATFORM_INIT_SERIAL() cyg_hal_plf_comms_init() + +#define HAL_STUB_PLATFORM_SET_BAUD_RATE(baud) CYG_UNUSED_PARAM(int, (baud)) +#define HAL_STUB_PLATFORM_INTERRUPTIBLE 0 +#define HAL_STUB_PLATFORM_INIT_BREAK_IRQ() CYG_EMPTY_STATEMENT + +//---------------------------------------------------------------------------- +// Stub initializer. + +#define HAL_STUB_PLATFORM_INIT() CYG_EMPTY_STATEMENT + +#endif // ifdef CYGDBG_HAL_DEBUG_GDB_INCLUDE_STUBS + +//----------------------------------------------------------------------------- +#endif // CYGONCE_HAL_PLF_STUB_H +// End of plf_stub.h
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/include/var_arch.h @@ -0,0 +1,59 @@ +#ifndef CYGONCE_HAL_VAR_ARCH_H +#define CYGONCE_HAL_VAR_ARCH_H +//============================================================================= +// +// var_arch.h +// +// STM32 variant architecture overrides +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Purpose: STM32 variant architecture overrides +// Description: +// Usage: #include <cyg/hal/hal_arch.h> +// +//####DESCRIPTIONEND#### +// +//============================================================================= + +#include <pkgconf/hal.h> +#include <cyg/hal/hal_io.h> + +#include <cyg/hal/plf_arch.h> + +//----------------------------------------------------------------------------- +// end of var_arch.h +#endif // CYGONCE_HAL_VAR_ARCH_H
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/include/var_intr.h @@ -0,0 +1,271 @@ +#ifndef CYGONCE_HAL_VAR_INTR_H +#define CYGONCE_HAL_VAR_INTR_H +//========================================================================== +// +// var_intr.h +// +// HAL Interrupt and clock assignments for STR7XX variants +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Purpose: Define Interrupt support +// Description: The interrupt specifics for ST STR7XX variants are +// defined here. +// +// Usage: #include <cyg/hal/var_intr.h> +// However applications should include using <cyg/hal/hal_intr.h> +// instead to allow for platform overrides. +// +//####DESCRIPTIONEND#### +// +//========================================================================== + +#include <cyg/hal/plf_intr.h> + +//========================================================================== + + +#define CYGNUM_HAL_INTERRUPT_WWDG ( 0+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_PVD ( 1+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TAMPER ( 2+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_RTC_GLOBAL ( 3+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_FLASH ( 4+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_RCC ( 5+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_EXTI0 ( 6+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_EXTI1 ( 7+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_EXTI2 ( 8+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_EXTI3 ( 9+CYGNUM_HAL_INTERRUPT_EXTERNAL) + +#define CYGNUM_HAL_INTERRUPT_EXTI4 (10+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA0_CH1 (11+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA0_CH2 (12+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA0_CH3 (13+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA0_CH4 (14+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA0_CH5 (15+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA0_CH6 (16+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA0_CH7 (17+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_ADC1_2 (18+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_USB_HP (19+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_CAN_TX (19+CYGNUM_HAL_INTERRUPT_EXTERNAL) + +#define CYGNUM_HAL_INTERRUPT_USB_LP (20+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_CAN_RX0 (20+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_CAN_RX1 (21+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_CAN_SCE (22+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_EXTI9_5 (23+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM1_BRK (24+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM1_UP (25+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM1_TRG (26+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM1_CC (27+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM2 (28+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM3 (29+CYGNUM_HAL_INTERRUPT_EXTERNAL) + +#define CYGNUM_HAL_INTERRUPT_TIM4 (30+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_I2C1_EV (31+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_I2C1_EE (32+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_I2C2_EV (33+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_I2C2_EE (34+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_SPI1 (35+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_SPI2 (36+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_UART1 (37+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_UART2 (38+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_UART3 (39+CYGNUM_HAL_INTERRUPT_EXTERNAL) + +#define CYGNUM_HAL_INTERRUPT_EXTI15_10 (40+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_RTC_ALARM (41+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_USB_WAKEUP (42+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM8_BRK (43+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM8_UP (44+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM8_TRG (45+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM8_CC (46+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_ADC3 (47+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_FSMC (48+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_SDIO (49+CYGNUM_HAL_INTERRUPT_EXTERNAL) + +#define CYGNUM_HAL_INTERRUPT_TIM5 (50+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_SPI3 (51+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_UART4 (52+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_UART5 (53+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM6 (54+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_TIM7 (55+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA2_CH1 (56+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA2_CH2 (57+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA2_CH3 (58+CYGNUM_HAL_INTERRUPT_EXTERNAL) +#define CYGNUM_HAL_INTERRUPT_DMA2_CH4_5 (59+CYGNUM_HAL_INTERRUPT_EXTERNAL) + +#define CYGNUM_HAL_INTERRUPT_NVIC_MAX (59+CYGNUM_HAL_INTERRUPT_EXTERNAL) + +#define CYGNUM_HAL_INTERRUPT_EXTI5 ( 1+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI6 ( 2+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI7 ( 3+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI8 ( 4+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI9 ( 5+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI10 ( 6+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI11 ( 7+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI12 ( 8+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI13 ( 9+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI14 (10+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI15 (11+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI16 (12+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI17 (13+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#define CYGNUM_HAL_INTERRUPT_EXTI18 (14+CYGNUM_HAL_INTERRUPT_NVIC_MAX) + +#define CYGNUM_HAL_ISR_MIN 0 +#define CYGNUM_HAL_ISR_MAX CYGNUM_HAL_INTERRUPT_EXTI18 +#define CYGNUM_HAL_ISR_COUNT (CYGNUM_HAL_ISR_MAX + 1) + +#define CYGNUM_HAL_VSR_MIN 0 +#ifndef CYGNUM_HAL_VSR_MAX +#define CYGNUM_HAL_VSR_MAX (CYGNUM_HAL_VECTOR_SYS_TICK+CYGNUM_HAL_INTERRUPT_NVIC_MAX) +#endif +#define CYGNUM_HAL_VSR_COUNT (CYGNUM_HAL_VSR_MAX+1) + +//========================================================================== +// Interrupt mask and config for variant-specific devices + +#define HAL_VAR_INTERRUPT_MASK( __vector ) \ +{ \ + cyg_int32 __v = -1; \ + \ + switch( __vector ) \ + { \ + case CYGNUM_HAL_INTERRUPT_EXTI0...CYGNUM_HAL_INTERRUPT_EXTI4: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI0; \ + break; \ + \ + case CYGNUM_HAL_INTERRUPT_EXTI5...CYGNUM_HAL_INTERRUPT_EXTI9: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI5 + 5; \ + break; \ + \ + case CYGNUM_HAL_INTERRUPT_EXTI10...CYGNUM_HAL_INTERRUPT_EXTI15: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI5 + 5; \ + break; \ + \ + case CYGNUM_HAL_INTERRUPT_EXTI16...CYGNUM_HAL_INTERRUPT_EXTI18: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI5 + 5; \ + break; \ + } \ + \ + if( __v > 0 ) \ + { \ + cyg_uint32 __imr; \ + HAL_READ_UINT32( CYGHWR_HAL_STM32_EXTI+CYGHWR_HAL_STM32_EXTI_IMR, __imr ); \ + __imr &= ~CYGHWR_HAL_STM32_EXTI_BIT(__v); \ + HAL_READ_UINT32( CYGHWR_HAL_STM32_EXTI+CYGHWR_HAL_STM32_EXTI_IMR, __imr ); \ + } \ +} + +#define HAL_VAR_INTERRUPT_UNMASK( __vector ) \ +{ \ + cyg_int32 __v = -1; \ + \ + switch( __vector ) \ + { \ + case CYGNUM_HAL_INTERRUPT_EXTI0...CYGNUM_HAL_INTERRUPT_EXTI4: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI0; \ + break; \ + \ + case CYGNUM_HAL_INTERRUPT_EXTI5...CYGNUM_HAL_INTERRUPT_EXTI9: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI5 + 5; \ + HAL_WRITE_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_SER(CYGNUM_HAL_INTERRUPT_EXTI9_5-CYGNUM_HAL_INTERRUPT_EXTERNAL), \ + CYGARC_REG_NVIC_IBIT(CYGNUM_HAL_INTERRUPT_EXTI9_5-CYGNUM_HAL_INTERRUPT_EXTERNAL) ); \ + break; \ + \ + case CYGNUM_HAL_INTERRUPT_EXTI10...CYGNUM_HAL_INTERRUPT_EXTI15: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI5 + 5; \ + HAL_WRITE_UINT32( CYGARC_REG_NVIC_BASE+CYGARC_REG_NVIC_SER(CYGNUM_HAL_INTERRUPT_EXTI15_10-CYGNUM_HAL_INTERRUPT_EXTERNAL), \ + CYGARC_REG_NVIC_IBIT(CYGNUM_HAL_INTERRUPT_EXTI15_10-CYGNUM_HAL_INTERRUPT_EXTERNAL) ); \ + break; \ + \ + case CYGNUM_HAL_INTERRUPT_EXTI16...CYGNUM_HAL_INTERRUPT_EXTI18: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI5 + 5; \ + break; \ + } \ + \ + if( __v > 0 ) \ + { \ + cyg_uint32 __imr; \ + HAL_READ_UINT32( CYGHWR_HAL_STM32_EXTI+CYGHWR_HAL_STM32_EXTI_IMR, __imr ); \ + __imr |= CYGHWR_HAL_STM32_EXTI_BIT(__v); \ + HAL_READ_UINT32( CYGHWR_HAL_STM32_EXTI+CYGHWR_HAL_STM32_EXTI_IMR, __imr ); \ + } \ +} + +#define HAL_VAR_INTERRUPT_SET_LEVEL( __vector, __level ) CYG_EMPTY_STATEMENT + +#define HAL_VAR_INTERRUPT_ACKNOWLEDGE( __vector ) CYG_EMPTY_STATEMENT + +#define HAL_VAR_INTERRUPT_CONFIGURE( __vector, __level, __up ) \ +{ \ + cyg_int32 __v = -1; \ + \ + switch( __vector ) \ + { \ + case CYGNUM_HAL_INTERRUPT_EXTI0...CYGNUM_HAL_INTERRUPT_EXTI4: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI0; \ + break; \ + \ + case CYGNUM_HAL_INTERRUPT_EXTI5...CYGNUM_HAL_INTERRUPT_EXTI9: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI5 + 5; \ + break; \ + \ + case CYGNUM_HAL_INTERRUPT_EXTI10...CYGNUM_HAL_INTERRUPT_EXTI15: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI5 + 5; \ + break; \ + \ + case CYGNUM_HAL_INTERRUPT_EXTI16...CYGNUM_HAL_INTERRUPT_EXTI18: \ + __v -= CYGNUM_HAL_INTERRUPT_EXTI5 + 5; \ + break; \ + } \ + \ + if( !(__level) ) \ + { \ + cyg_uint32 __base = CYGHWR_HAL_STM32_EXTI; \ + cyg_uint32 __rtsr, __ftsr; \ + cyg_uint32 __bit = CYGHWR_HAL_STM32_EXTI_BIT(__v); \ + HAL_READ_UINT32( __base+CYGHWR_HAL_STM32_EXTI_RTSR, __rtsr ); \ + HAL_READ_UINT32( __base+CYGHWR_HAL_STM32_EXTI_RTSR, __ftsr ); \ + if( __up ) __rtsr |= __bit, __ftsr &= ~__bit; \ + else __ftsr |= __bit, __rtsr &= ~__bit; \ + HAL_WRITE_UINT32( __base+CYGHWR_HAL_STM32_EXTI_RTSR, __rtsr ); \ + HAL_WRITE_UINT32( __base+CYGHWR_HAL_STM32_EXTI_RTSR, __ftsr ); \ + } \ +} + + +//---------------------------------------------------------------------------- +#endif // CYGONCE_HAL_VAR_INTR_H +// EOF var_intr.h
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/include/var_io.h @@ -0,0 +1,548 @@ +#ifndef CYGONCE_HAL_VAR_IO_H +#define CYGONCE_HAL_VAR_IO_H +//============================================================================= +// +// var_io.h +// +// Variant specific registers +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Purpose: STM32 variant specific registers +// Description: +// Usage: #include <cyg/hal/var_io.h> +// +//####DESCRIPTIONEND#### +// +//============================================================================= + +#include <pkgconf/hal_cortexm_stm32.h> + +#include <cyg/hal/plf_io.h> + +//============================================================================= +// Peripherals + +#define CYGHWR_HAL_STM32_TIM2 0x40000000 +#define CYGHWR_HAL_STM32_TIM3 0x40000400 +#define CYGHWR_HAL_STM32_TIM4 0x40000800 +#define CYGHWR_HAL_STM32_TIM5 0x40000C00 +#define CYGHWR_HAL_STM32_TIM6 0x40001000 +#define CYGHWR_HAL_STM32_TIM7 0x40001400 +#define CYGHWR_HAL_STM32_RTC 0x40002800 +#define CYGHWR_HAL_STM32_WWDG 0x40002C00 +#define CYGHWR_HAL_STM32_IWDG 0x40003000 +#define CYGHWR_HAL_STM32_SPI2 0x40003800 +#define CYGHWR_HAL_STM32_SPI3 0x40003C00 +#define CYGHWR_HAL_STM32_UART2 0x40004400 +#define CYGHWR_HAL_STM32_UART3 0x40004800 +#define CYGHWR_HAL_STM32_UART4 0x40004C00 +#define CYGHWR_HAL_STM32_UART5 0x40005000 +#define CYGHWR_HAL_STM32_I2C1 0x40005400 +#define CYGHWR_HAL_STM32_I2C2 0x40005800 +#define CYGHWR_HAL_STM32_USB 0x40005C00 +#define CYGHWR_HAL_STM32_USB_CAN_SRAM 0x40006000 +#define CYGHWR_HAL_STM32_BXCAN 0x40006400 +#define CYGHWR_HAL_STM32_BKP 0x40006C00 +#define CYGHWR_HAL_STM32_PWR 0x40007000 +#define CYGHWR_HAL_STM32_DAC 0x40007400 +#define CYGHWR_HAL_STM32_AFIO 0x40010000 +#define CYGHWR_HAL_STM32_EXTI 0x40010400 +#define CYGHWR_HAL_STM32_GPIOA 0x40010800 +#define CYGHWR_HAL_STM32_GPIOB 0x40010C00 +#define CYGHWR_HAL_STM32_GPIOC 0x40011000 +#define CYGHWR_HAL_STM32_GPIOD 0x40011400 +#define CYGHWR_HAL_STM32_GPIOE 0x40011800 +#define CYGHWR_HAL_STM32_GPIOF 0x40011C00 +#define CYGHWR_HAL_STM32_GPIOG 0x40012000 +#define CYGHWR_HAL_STM32_ADC1 0x40012400 +#define CYGHWR_HAL_STM32_ADC2 0x40012800 +#define CYGHWR_HAL_STM32_TIM1 0x40012C00 +#define CYGHWR_HAL_STM32_SPI1 0x40013000 +#define CYGHWR_HAL_STM32_TIM8 0x40013400 +#define CYGHWR_HAL_STM32_UART1 0x40013800 +#define CYGHWR_HAL_STM32_ADC3 0x40013C00 +#define CYGHWR_HAL_STM32_SDIO 0x40018000 +#define CYGHWR_HAL_STM32_DMA1 0x40020000 +#define CYGHWR_HAL_STM32_DMA2 0x40020400 +#define CYGHWR_HAL_STM32_RCC 0x40021000 +#define CYGHWR_HAL_STM32_FLASH 0x40022000 +#define CYGHWR_HAL_STM32_CRC 0x40023000 + +#define CYGHWR_HAL_STM32_FSMC 0xA0000000 + +//============================================================================= +// Device signature and ID registers + +#define CYGHWR_HAL_STM32_DEV_SIG 0x1FFFF7E0 +#define CYGHWR_HAL_STM32_DEV_SIG_FSIZE(__s) (((__s)>>16)&0xFFFF) +#define CYGHWR_HAL_STM32_DEV_SIG_RSIZE(__s) ((__s)&0xFFFF) + +#define CYGHWR_HAL_STM32_MCU_ID 0xe0042000 +#define CYGHWR_HAL_STM32_MCU_ID_DEV(__x) ((__x)&0xFFF) +#define CYGHWR_HAL_STM32_MCU_ID_DEV_MEDIUM 0x410 +#define CYGHWR_HAL_STM32_MCU_ID_DEV_HIGH 0x414 +#define CYGHWR_HAL_STM32_MCU_ID_REV(__x) (((__x)>>16)&0xFFFF) + +//============================================================================= +// RCC +// +// Not all registers are described here + +#define CYGHWR_HAL_STM32_RCC_CR 0x00 +#define CYGHWR_HAL_STM32_RCC_CFGR 0x04 +#define CYGHWR_HAL_STM32_RCC_CIR 0x08 +#define CYGHWR_HAL_STM32_RCC_APB2RSTR 0x0C +#define CYGHWR_HAL_STM32_RCC_APB1RSTR 0x10 +#define CYGHWR_HAL_STM32_RCC_AHBENR 0x14 +#define CYGHWR_HAL_STM32_RCC_APB2ENR 0x18 +#define CYGHWR_HAL_STM32_RCC_APB1ENR 0x1C +#define CYGHWR_HAL_STM32_RCC_BDCR 0x20 +#define CYGHWR_HAL_STM32_RCC_CSR 0x24 + +#define CYGHWR_HAL_STM32_RCC_CR_HSION BIT_(0) +#define CYGHWR_HAL_STM32_RCC_CR_HSIRDY BIT_(1) +#define CYGHWR_HAL_STM32_RCC_CR_HSITRIM MASK_(3,5) +#define CYGHWR_HAL_STM32_RCC_CR_HSICAL MASK_(8,8) +#define CYGHWR_HAL_STM32_RCC_CR_HSEON BIT_(16) +#define CYGHWR_HAL_STM32_RCC_CR_HSERDY BIT_(17) +#define CYGHWR_HAL_STM32_RCC_CR_HSEBYP BIT_(18) +#define CYGHWR_HAL_STM32_RCC_CR_CSSON BIT_(19) +#define CYGHWR_HAL_STM32_RCC_CR_PLLON BIT_(24) +#define CYGHWR_HAL_STM32_RCC_CR_PLLRDY BIT_(25) + +#define CYGHWR_HAL_STM32_RCC_CFGR_SW_HSI VALUE_(0,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_SW_HSE VALUE_(0,1) +#define CYGHWR_HAL_STM32_RCC_CFGR_SW_PLL VALUE_(0,2) +#define CYGHWR_HAL_STM32_RCC_CFGR_SW_XXX VALUE_(0,3) +#define CYGHWR_HAL_STM32_RCC_CFGR_SWS_HSI VALUE_(2,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_SWS_HSE VALUE_(2,1) +#define CYGHWR_HAL_STM32_RCC_CFGR_SWS_PLL VALUE_(2,2) +#define CYGHWR_HAL_STM32_RCC_CFGR_SWS_XXX VALUE_(2,3) +#define CYGHWR_HAL_STM32_RCC_CFGR_HPRE_1 VALUE_(4,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_HPRE_2 VALUE_(4,8) +#define CYGHWR_HAL_STM32_RCC_CFGR_HPRE_4 VALUE_(4,9) +#define CYGHWR_HAL_STM32_RCC_CFGR_HPRE_8 VALUE_(4,10) +#define CYGHWR_HAL_STM32_RCC_CFGR_HPRE_16 VALUE_(4,11) +#define CYGHWR_HAL_STM32_RCC_CFGR_HPRE_64 VALUE_(4,12) +#define CYGHWR_HAL_STM32_RCC_CFGR_HPRE_128 VALUE_(4,13) +#define CYGHWR_HAL_STM32_RCC_CFGR_HPRE_256 VALUE_(4,14) +#define CYGHWR_HAL_STM32_RCC_CFGR_HPRE_512 VALUE_(4,15) +#define CYGHWR_HAL_STM32_RCC_CFGR_PPRE1_1 VALUE_(8,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_PPRE1_2 VALUE_(8,4) +#define CYGHWR_HAL_STM32_RCC_CFGR_PPRE1_4 VALUE_(8,5) +#define CYGHWR_HAL_STM32_RCC_CFGR_PPRE1_8 VALUE_(8,6) +#define CYGHWR_HAL_STM32_RCC_CFGR_PPRE1_16 VALUE_(8,7) +#define CYGHWR_HAL_STM32_RCC_CFGR_PPRE2_1 VALUE_(11,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_PPRE2_2 VALUE_(11,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_PPRE2_4 VALUE_(11,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_PPRE2_8 VALUE_(11,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_PPRE2_16 VALUE_(11,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_ADCPRE_2 VALUE_(14,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_ADCPRE_4 VALUE_(14,1) +#define CYGHWR_HAL_STM32_RCC_CFGR_ADCPRE_6 VALUE_(14,2) +#define CYGHWR_HAL_STM32_RCC_CFGR_ADCPRE_8 VALUE_(14,3) +#define CYGHWR_HAL_STM32_RCC_CFGR_PLLSRC_HSI 0 +#define CYGHWR_HAL_STM32_RCC_CFGR_PLLSRC_HSE BIT_(16) +#define CYGHWR_HAL_STM32_RCC_CFGR_PLLXTPRE BIT_(17) +#define CYGHWR_HAL_STM32_RCC_CFGR_PLLMUL(__x) VALUE_(18,(__x)-2) +#define CYGHWR_HAL_STM32_RCC_CFGR_USBPRE BIT_(22) +#define CYGHWR_HAL_STM32_RCC_CFGR_MCO_NONE VALUE_(24,0) +#define CYGHWR_HAL_STM32_RCC_CFGR_MCO_SYSCLK VALUE_(24,4) +#define CYGHWR_HAL_STM32_RCC_CFGR_MCO_HSI VALUE_(24,5) +#define CYGHWR_HAL_STM32_RCC_CFGR_MCO_HSE VALUE_(24,6) +#define CYGHWR_HAL_STM32_RCC_CFGR_MCO_PLL VALUE_(24,7) + + +#define CYGHWR_HAL_STM32_RCC_AHBENR_DMA1 BIT_(0) +#define CYGHWR_HAL_STM32_RCC_AHBENR_DMA2 BIT_(1) +#define CYGHWR_HAL_STM32_RCC_AHBENR_SRAM BIT_(2) +#define CYGHWR_HAL_STM32_RCC_AHBENR_FLITF BIT_(4) +#define CYGHWR_HAL_STM32_RCC_AHBENR_CRC BIT_(6) +#define CYGHWR_HAL_STM32_RCC_AHBENR_FSMC BIT_(8) +#define CYGHWR_HAL_STM32_RCC_AHBENR_SDIO BIT_(10) + +#define CYGHWR_HAL_STM32_RCC_APB2ENR_AFIO BIT_(0) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_IOPA BIT_(2) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_IOPB BIT_(3) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_IOPC BIT_(4) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_IOPD BIT_(5) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_IOPE BIT_(6) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_IOPF BIT_(7) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_IOPG BIT_(8) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_ADC1 BIT_(9) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_ADC2 BIT_(10) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_TIM1 BIT_(11) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_SPI1 BIT_(12) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_TIM8 BIT_(13) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_UART1 BIT_(14) +#define CYGHWR_HAL_STM32_RCC_APB2ENR_ADC3 BIT_(15) + + +#define CYGHWR_HAL_STM32_RCC_APB1ENR_TIM2 BIT_(0) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_TIM3 BIT_(1) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_TIM4 BIT_(2) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_TIM5 BIT_(3) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_TIM6 BIT_(4) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_TIM7 BIT_(5) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_WWDG BIT_(11) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_SPI2 BIT_(14) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_SPI3 BIT_(15) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_UART2 BIT_(17) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_UART3 BIT_(18) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_UART4 BIT_(19) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_UART5 BIT_(20) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_I2C1 BIT_(21) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_USB BIT_(22) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_CAN BIT_(25) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_BKP BIT_(27) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_PWR BIT_(28) +#define CYGHWR_HAL_STM32_RCC_APB1ENR_DAC BIT_(29) + +#define CYGHWR_HAL_STM32_RCC_CSR_LSION BIT_(0) +#define CYGHWR_HAL_STM32_RCC_CSR_LSIRDY BIT_(1) +#define CYGHWR_HAL_STM32_RCC_CSR_RMVF BIT_(24) +#define CYGHWR_HAL_STM32_RCC_CSR_PINRSTF BIT_(26) +#define CYGHWR_HAL_STM32_RCC_CSR_PORRSTF BIT_(27) +#define CYGHWR_HAL_STM32_RCC_CSR_SFTRSTF BIT_(28) +#define CYGHWR_HAL_STM32_RCC_CSR_IWDGRSTF BIT_(29) +#define CYGHWR_HAL_STM32_RCC_CSR_WWDGRSTF BIT_(30) +#define CYGHWR_HAL_STM32_RCC_CSR_LPWRRSTF BIT_(31) + + +//============================================================================= +// External interrupt controller + +#define CYGHWR_HAL_STM32_EXTI_IMR 0x00 +#define CYGHWR_HAL_STM32_EXTI_EMR 0x04 +#define CYGHWR_HAL_STM32_EXTI_RTSR 0x08 +#define CYGHWR_HAL_STM32_EXTI_FTSR 0x0C +#define CYGHWR_HAL_STM32_EXTI_SWIER 0x10 +#define CYGHWR_HAL_STM32_EXTI_PR 0x14 + +#define CYGHWR_HAL_STM32_EXTI_BIT(__b) BIT_(__b) + +//============================================================================= +// GPIO ports + +#define CYGHWR_HAL_STM32_GPIO_CRL 0x00 +#define CYGHWR_HAL_STM32_GPIO_CRH 0x04 +#define CYGHWR_HAL_STM32_GPIO_IDR 0x08 +#define CYGHWR_HAL_STM32_GPIO_ODR 0x0C +#define CYGHWR_HAL_STM32_GPIO_BSRR 0x10 +#define CYGHWR_HAL_STM32_GPIO_BRR 0x14 +#define CYGHWR_HAL_STM32_GPIO_LCKR 0x18 + +#define CYGHWR_HAL_STM32_GPIO_MODE_IN VALUE_(0,0) // Input mode +#define CYGHWR_HAL_STM32_GPIO_MODE_OUT_10MHz VALUE_(0,1) // Output mode, max 10MHz +#define CYGHWR_HAL_STM32_GPIO_MODE_OUT_2MHz VALUE_(0,2) // Output mode, max 2MHz +#define CYGHWR_HAL_STM32_GPIO_MODE_OUT_50MHZ VALUE_(0,3) // Output mode, max 50MHz + +#define CYGHWR_HAL_STM32_GPIO_CNF_AIN VALUE_(2,0) // Analog input +#define CYGHWR_HAL_STM32_GPIO_CNF_FIN VALUE_(2,1) // Floating input +#define CYGHWR_HAL_STM32_GPIO_CNF_PULL VALUE_(2,2) // Input with pull up/down +#define CYGHWR_HAL_STM32_GPIO_CNF_RESV VALUE_(2,3) // Reserved + +#define CYGHWR_HAL_STM32_GPIO_CNF_GPOPP VALUE_(2,0) // GP output push/pull +#define CYGHWR_HAL_STM32_GPIO_CNF_GPOOD VALUE_(2,1) // GP output open drain +#define CYGHWR_HAL_STM32_GPIO_CNF_AOPP VALUE_(2,2) // Alt output push/pull +#define CYGHWR_HAL_STM32_GPIO_CNF_AOOD VALUE_(2,3) // Alt output open drain + + +// Alternative, more readable, config names +// Inputs +#define CYGHWR_HAL_STM32_GPIO_CNF_ANALOG CYGHWR_HAL_STM32_GPIO_CNF_AIN +#define CYGHWR_HAL_STM32_GPIO_CNF_FLOATING CYGHWR_HAL_STM32_GPIO_CNF_FIN +#define CYGHWR_HAL_STM32_GPIO_CNF_PULLDOWN (CYGHWR_HAL_STM32_GPIO_CNF_PULL) +#define CYGHWR_HAL_STM32_GPIO_CNF_PULLUP (CYGHWR_HAL_STM32_GPIO_CNF_PULL|CYGHWR_HAL_STM32_GPIO_PULLUP) +// Outputs +#define CYGHWR_HAL_STM32_GPIO_CNF_OUT_OPENDRAIN CYGHWR_HAL_STM32_GPIO_CNF_GPOOD +#define CYGHWR_HAL_STM32_GPIO_CNF_OUT_PUSHPULL CYGHWR_HAL_STM32_GPIO_CNF_GPOPP +#define CYGHWR_HAL_STM32_GPIO_CNF_ALT_OPENDRAIN CYGHWR_HAL_STM32_GPIO_CNF_AOOD +#define CYGHWR_HAL_STM32_GPIO_CNF_ALT_PUSHPULL CYGHWR_HAL_STM32_GPIO_CNF_AOPP + + +// This macro packs the port number, bit number, mode and +// configuration for a GPIO pin into a single word. The packing puts +// the mode and config in the ls 5 bits, the bit number in 16:20 and +// the offset of the GPIO port from GPIOA in bits 8:15. The port, mode +// and config are only specified using the last component of the names +// to keep definitions short. + +#define CYGHWR_HAL_STM32_GPIO(__port, __bit, __mode, __cnf ) \ + ((CYGHWR_HAL_STM32_GPIO##__port - CYGHWR_HAL_STM32_GPIOA) | \ + (__bit<<16) | \ + (CYGHWR_HAL_STM32_GPIO_MODE_##__mode) | \ + (CYGHWR_HAL_STM32_GPIO_CNF_##__cnf)) + +// Macros to extract encoded values +#define CYGHWR_HAL_STM32_GPIO_PORT(__pin) (CYGHWR_HAL_STM32_GPIOA+((__pin)&0x0000FF00)) +#define CYGHWR_HAL_STM32_GPIO_BIT(__pin) (((__pin)>>16)&0x1F) +#define CYGHWR_HAL_STM32_GPIO_CFG(__pin) ((__pin)&0x1F) +#define CYGHWR_HAL_STM32_GPIO_PULLUP BIT_(4) + + +#define CYGHWR_HAL_STM32_GPIO_NONE (0xFFFFFFFF) + +// Functions and macros to configure GPIO ports. + +__externC void hal_stm32_gpio_set( cyg_uint32 pin ); +__externC void hal_stm32_gpio_out( cyg_uint32 pin, int val ); +__externC void hal_stm32_gpio_in ( cyg_uint32 pin, int *val ); + +#define CYGHWR_HAL_STM32_GPIO_SET(__pin ) hal_stm32_gpio_set( __pin ) +#define CYGHWR_HAL_STM32_GPIO_OUT(__pin, __val ) hal_stm32_gpio_out( __pin, __val ) +#define CYGHWR_HAL_STM32_GPIO_IN(__pin, __val ) hal_stm32_gpio_in( __pin, __val ) + +//============================================================================= +// UARTs + +#define CYGHWR_HAL_STM32_UART_SR 0x00 +#define CYGHWR_HAL_STM32_UART_DR 0x04 +#define CYGHWR_HAL_STM32_UART_BRR 0x08 +#define CYGHWR_HAL_STM32_UART_CR1 0x0C +#define CYGHWR_HAL_STM32_UART_CR2 0x10 +#define CYGHWR_HAL_STM32_UART_CR3 0x14 +#define CYGHWR_HAL_STM32_UART_GTPR 0x18 + +// SR Bits + +#define CYGHWR_HAL_STM32_UART_SR_PE BIT_(0) +#define CYGHWR_HAL_STM32_UART_SR_FE BIT_(1) +#define CYGHWR_HAL_STM32_UART_SR_NE BIT_(2) +#define CYGHWR_HAL_STM32_UART_SR_ORE BIT_(3) +#define CYGHWR_HAL_STM32_UART_SR_IDLE BIT_(4) +#define CYGHWR_HAL_STM32_UART_SR_RXNE BIT_(5) +#define CYGHWR_HAL_STM32_UART_SR_TC BIT_(6) +#define CYGHWR_HAL_STM32_UART_SR_TXE BIT_(7) +#define CYGHWR_HAL_STM32_UART_SR_LBD BIT_(8) +#define CYGHWR_HAL_STM32_UART_SR_CTS BIT_(9) + +// BRR bits + +#define CYGHWR_HAL_STM32_UART_DR_DIVF(__f) VALUE_(0,__f) +#define CYGHWR_HAL_STM32_UART_DR_DIVM(__m) VALUE_(4,__m) + +// CR1 bits + +#define CYGHWR_HAL_STM32_UART_CR1_SBK BIT_(0) +#define CYGHWR_HAL_STM32_UART_CR1_RWU BIT_(1) +#define CYGHWR_HAL_STM32_UART_CR1_RE BIT_(2) +#define CYGHWR_HAL_STM32_UART_CR1_TE BIT_(3) +#define CYGHWR_HAL_STM32_UART_CR1_IDLEIE BIT_(4) +#define CYGHWR_HAL_STM32_UART_CR1_RXNEIE BIT_(5) +#define CYGHWR_HAL_STM32_UART_CR1_TCIE BIT_(6) +#define CYGHWR_HAL_STM32_UART_CR1_TXEIE BIT_(7) +#define CYGHWR_HAL_STM32_UART_CR1_PEIE BIT_(8) +#define CYGHWR_HAL_STM32_UART_CR1_PS_EVEN 0 +#define CYGHWR_HAL_STM32_UART_CR1_PS_ODD BIT_(9) +#define CYGHWR_HAL_STM32_UART_CR1_PCE BIT_(10) +#define CYGHWR_HAL_STM32_UART_CR1_WAKE BIT_(11) +#define CYGHWR_HAL_STM32_UART_CR1_M_8 0 +#define CYGHWR_HAL_STM32_UART_CR1_M_9 BIT_(12) +#define CYGHWR_HAL_STM32_UART_CR1_UE BIT_(13) + +// CR2 bits + +#define CYGHWR_HAL_STM32_UART_CR2_ADD(__a) VALUE_(0,__a) +#define CYGHWR_HAL_STM32_UART_CR2_LBDL BIT_(5) +#define CYGHWR_HAL_STM32_UART_CR2_LBDIE BIT_(6) +#define CYGHWR_HAL_STM32_UART_CR2_LBCL BIT_(8) +#define CYGHWR_HAL_STM32_UART_CR2_CPHA BIT_(9) +#define CYGHWR_HAL_STM32_UART_CR2_CPOL BIT_(10) +#define CYGHWR_HAL_STM32_UART_CR2_CLKEN BIT_(11) +#define CYGHWR_HAL_STM32_UART_CR2_STOP_1 VALUE_(12,0) +#define CYGHWR_HAL_STM32_UART_CR2_STOP_0_5 VALUE_(12,1) +#define CYGHWR_HAL_STM32_UART_CR2_STOP_2 VALUE_(12,2) +#define CYGHWR_HAL_STM32_UART_CR2_STOP_1_5 VALUE_(12,3) +#define CYGHWR_HAL_STM32_UART_CR2_LINEN BIT_(14) + +// CR3 bits + +#define CYGHWR_HAL_STM32_UART_CR3_EIE BIT_(0) +#define CYGHWR_HAL_STM32_UART_CR3_IREN BIT_(1) +#define CYGHWR_HAL_STM32_UART_CR3_IRLP BIT_(2) +#define CYGHWR_HAL_STM32_UART_CR3_HDSEL BIT_(3) +#define CYGHWR_HAL_STM32_UART_CR3_NACK BIT_(4) +#define CYGHWR_HAL_STM32_UART_CR3_SCEN BIT_(5) +#define CYGHWR_HAL_STM32_UART_CR3_DMAR BIT_(6) +#define CYGHWR_HAL_STM32_UART_CR3_DMAT BIT_(7) +#define CYGHWR_HAL_STM32_UART_CR3_RTSE BIT_(8) +#define CYGHWR_HAL_STM32_UART_CR3_CTSE BIT_(9) +#define CYGHWR_HAL_STM32_UART_CR3_CTSIE BIT_(10) + +// GTPR fields + +#define CYGHWR_HAL_STM32_UART_GTPR_PSC(__p) VALUE_(0,__p) +#define CYGHWR_HAL_STM32_UART_GTPR_GT(__g) VALUE_(8,__g) + +// UART GPIO pins + +#define CYGHWR_HAL_STM32_UART1_RX CYGHWR_HAL_STM32_GPIO( A, 10, IN , FLOATING ) +#define CYGHWR_HAL_STM32_UART1_TX CYGHWR_HAL_STM32_GPIO( A, 9, OUT_50MHZ , ALT_PUSHPULL ) +#define CYGHWR_HAL_STM32_UART1_CTS CYGHWR_HAL_STM32_GPIO( A, 11, IN , FLOATING ) +#define CYGHWR_HAL_STM32_UART1_RTS CYGHWR_HAL_STM32_GPIO( A, 12, OUT_50MHZ , OUT_PUSHPULL ) + +#define CYGHWR_HAL_STM32_UART2_RX CYGHWR_HAL_STM32_GPIO( A, 3, IN , FLOATING ) +#define CYGHWR_HAL_STM32_UART2_TX CYGHWR_HAL_STM32_GPIO( A, 2, OUT_50MHZ , ALT_PUSHPULL ) +#define CYGHWR_HAL_STM32_UART2_CTS CYGHWR_HAL_STM32_GPIO( A, 0, IN , FLOATING ) +#define CYGHWR_HAL_STM32_UART2_RTS CYGHWR_HAL_STM32_GPIO( A, 1, OUT_50MHZ , OUT_PUSHPULL ) + +#define CYGHWR_HAL_STM32_UART3_RX CYGHWR_HAL_STM32_GPIO( B, 11, IN , FLOATING ) +#define CYGHWR_HAL_STM32_UART3_TX CYGHWR_HAL_STM32_GPIO( B, 10, OUT_50MHZ , ALT_PUSHPULL ) +#define CYGHWR_HAL_STM32_UART3_CTS CYGHWR_HAL_STM32_GPIO( B, 13, IN , FLOATING ) +#define CYGHWR_HAL_STM32_UART3_RTS CYGHWR_HAL_STM32_GPIO( B, 14, OUT_50MHZ , OUT_PUSHPULL ) + +#define CYGHWR_HAL_STM32_UART4_RX CYGHWR_HAL_STM32_GPIO( C, 11, IN , FLOATING ) +#define CYGHWR_HAL_STM32_UART4_TX CYGHWR_HAL_STM32_GPIO( C, 10, OUT_50MHZ , ALT_PUSHPULL ) +#define CYGHWR_HAL_STM32_UART4_CTS CYGHWR_HAL_STM32_GPIO_NONE +#define CYGHWR_HAL_STM32_UART4_RTS CYGHWR_HAL_STM32_GPIO_NONE + +#define CYGHWR_HAL_STM32_UART5_RX CYGHWR_HAL_STM32_GPIO( C, 2, IN , FLOATING ) +#define CYGHWR_HAL_STM32_UART5_TX CYGHWR_HAL_STM32_GPIO( C, 12, OUT_50MHZ , ALT_PUSHPULL ) +#define CYGHWR_HAL_STM32_UART5_CTS CYGHWR_HAL_STM32_GPIO_NONE +#define CYGHWR_HAL_STM32_UART5_RTS CYGHWR_HAL_STM32_GPIO_NONE + +#ifndef __ASSEMBLER__ + +__externC void hal_stm32_uart_setbaud( CYG_ADDRESS uart, cyg_uint32 baud ); + +#endif + +//============================================================================= +// Timers +// +// This currently only defines the basic registers and functionality +// common to all timers. + +#define CYGHWR_HAL_STM32_TIM_CR1 0x00 +#define CYGHWR_HAL_STM32_TIM_CR2 0x04 +#define CYGHWR_HAL_STM32_TIM_DIER 0x0C +#define CYGHWR_HAL_STM32_TIM_SR 0x10 +#define CYGHWR_HAL_STM32_TIM_EGR 0x14 +#define CYGHWR_HAL_STM32_TIM_CNT 0x24 +#define CYGHWR_HAL_STM32_TIM_PSC 0x28 +#define CYGHWR_HAL_STM32_TIM_ARR 0x2C + +#define CYGHWR_HAL_STM32_TIM_CR1_CEN BIT_(0) +#define CYGHWR_HAL_STM32_TIM_CR1_UDIS BIT_(1) +#define CYGHWR_HAL_STM32_TIM_CR1_URS BIT_(2) +#define CYGHWR_HAL_STM32_TIM_CR1_OPM BIT_(3) +#define CYGHWR_HAL_STM32_TIM_CR1_ARPE BIT_(7) + +#define CYGHWR_HAL_STM32_TIM_CR2_MMS_RESET VALUE_(4,0) +#define CYGHWR_HAL_STM32_TIM_CR2_MMS_ENABLE VALUE_(4,1) +#define CYGHWR_HAL_STM32_TIM_CR2_MMS_UPDATE VALUE_(4,2) + +#define CYGHWR_HAL_STM32_TIM_DIER_UIE BIT_(0) +#define CYGHWR_HAL_STM32_TIM_DIER_UDE BIT_(8) + +#define CYGHWR_HAL_STM32_TIM_SR_UIF BIT_(0) + +#define CYGHWR_HAL_STM32_TIM_EGR_UG BIT_(0) + +//============================================================================= +// Flash controller + +#define CYGHWR_HAL_STM32_FLASH_ACR 0x00 +#define CYGHWR_HAL_STM32_FLASH_KEYR 0x04 +#define CYGHWR_HAL_STM32_FLASH_OPTKEYR 0x08 +#define CYGHWR_HAL_STM32_FLASH_SR 0x0C +#define CYGHWR_HAL_STM32_FLASH_CR 0x10 +#define CYGHWR_HAL_STM32_FLASH_AR 0x14 +#define CYGHWR_HAL_STM32_FLASH_OBR 0x1C +#define CYGHWR_HAL_STM32_FLASH_WRPR 0x20 + +// Key values + +#define CYGHWR_HAL_STM32_FLASH_KEYR_KEY1 0x45670123 +#define CYGHWR_HAL_STM32_FLASH_KEYR_KEY2 0xCDEF89AB + +// ACR fields + +#define CYGHWR_HAL_STM32_FLASH_ACR_LATENCY(__x) VALUE_(0,__x) +#define CYGHWR_HAL_STM32_FLASH_ACR_HLFCYA BIT_(3) +#define CYGHWR_HAL_STM32_FLASH_ACR_PRFTBE BIT_(4) +#define CYGHWR_HAL_STM32_FLASH_ACR_PRFTBS BIT_(5) + +// SR fields + +#define CYGHWR_HAL_STM32_FLASH_SR_BSY BIT_(0) +#define CYGHWR_HAL_STM32_FLASH_SR_PGERR BIT_(2) +#define CYGHWR_HAL_STM32_FLASH_SR_WRPRTERR BIT_(4) +#define CYGHWR_HAL_STM32_FLASH_SR_EOP BIT_(5) + +// CR fields + +#define CYGHWR_HAL_STM32_FLASH_CR_PG BIT_(0) +#define CYGHWR_HAL_STM32_FLASH_CR_PER BIT_(1) +#define CYGHWR_HAL_STM32_FLASH_CR_MER BIT_(2) +#define CYGHWR_HAL_STM32_FLASH_CR_OPTPG BIT_(4) +#define CYGHWR_HAL_STM32_FLASH_CR_OPTER BIT_(5) +#define CYGHWR_HAL_STM32_FLASH_CR_STRT BIT_(6) +#define CYGHWR_HAL_STM32_FLASH_CR_LOCK BIT_(7) +#define CYGHWR_HAL_STM32_FLASH_CR_OPTWRE BIT_(9) +#define CYGHWR_HAL_STM32_FLASH_CR_ERRIE BIT_(10) +#define CYGHWR_HAL_STM32_FLASH_CR_EOPIE BIT_(12) + +// OBR fields + +#define CYGHWR_HAL_STM32_FLASH_OBR_OPTERR BIT_(0) +#define CYGHWR_HAL_STM32_FLASH_OBR_RDPRT BIT_(1) +#define CYGHWR_HAL_STM32_FLASH_OBR_WDG_SW BIT_(2) +#define CYGHWR_HAL_STM32_FLASH_OBR_nRST_STOP BIT_(3) +#define CYGHWR_HAL_STM32_FLASH_OBR_nRST_STDBY BIT_(4) + + +//============================================================================= +// FSMC +// +// These registers are usually set up in hal_system_init() using direct +// binary values. Hence we don't define all the fields here (of which +// there are many). + +#define CYGHWR_HAL_STM32_FSMC_BCR1 0x00 +#define CYGHWR_HAL_STM32_FSMC_BTR1 0x04 +#define CYGHWR_HAL_STM32_FSMC_BCR2 0x08 +#define CYGHWR_HAL_STM32_FSMC_BTR2 0x0C +#define CYGHWR_HAL_STM32_FSMC_BCR3 0x10 +#define CYGHWR_HAL_STM32_FSMC_BTR3 0x14 +#define CYGHWR_HAL_STM32_FSMC_BCR4 0x18 +#define CYGHWR_HAL_STM32_FSMC_BTR4 0x1C + +//----------------------------------------------------------------------------- +// end of var_io.h +#endif // CYGONCE_HAL_VAR_IO_H
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/include/variant.inc @@ -0,0 +1,52 @@ +/*========================================================================== +// +// variant.inc +// +// Variant specific asm definitions +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Description: +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/hal_cortexm_stm32.h> + +//========================================================================== +// EOF variant.inc +
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/src/hal_diag.c @@ -0,0 +1,390 @@ +/*============================================================================= +// +// hal_diag.c +// +// HAL diagnostic output code +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 1998, 1999, 2000, 2001, 2002 Red Hat, Inc. +// Copyright (C) 2004, 2005, 2006, 2008 eCosCentric Limited +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Purpose: HAL diagnostic output +// Description: Implementations of HAL diagnostic output support. +// +//####DESCRIPTIONEND#### +// +//===========================================================================*/ + +#include <pkgconf/hal.h> +#include CYGBLD_HAL_PLATFORM_H + +#include <cyg/infra/cyg_type.h> // base types +#include <cyg/infra/cyg_trac.h> // tracing + +#include <cyg/hal/hal_arch.h> // SAVE/RESTORE GP macros +#include <cyg/hal/hal_io.h> // IO macros +#include <cyg/hal/hal_if.h> // interface API +#include <cyg/hal/hal_intr.h> // HAL_ENABLE/MASK/UNMASK_INTERRUPTS +#include <cyg/hal/hal_misc.h> // Helper functions +#include <cyg/hal/drv_api.h> // CYG_ISR_HANDLED + +#include <cyg/hal/var_io.h> // USART registers + +//----------------------------------------------------------------------------- + +typedef struct { + cyg_uint32 uart; + CYG_ADDRESS base; + cyg_int32 msec_timeout; + int isr_vector; + cyg_uint32 rxpin; + cyg_uint32 txpin; + cyg_uint32 baud_rate; + int irq_state; + +} channel_data_t; + +static channel_data_t stm32_ser_channels[] = { +#if CYGINT_HAL_STM32_UART0>0 + { 0, CYGHWR_HAL_STM32_UART1, 1000, CYGNUM_HAL_INTERRUPT_UART1, CYGHWR_HAL_STM32_UART1_RX, CYGHWR_HAL_STM32_UART1_TX }, +#endif +#if CYGINT_HAL_STM32_UART1>0 + { 1, CYGHWR_HAL_STM32_UART2, 1000, CYGNUM_HAL_INTERRUPT_UART2, CYGHWR_HAL_STM32_UART2_RX, CYGHWR_HAL_STM32_UART2_TX }, +#endif +#if CYGINT_HAL_STM32_UART2>0 + { 2, CYGHWR_HAL_STM32_UART3, 1000, CYGNUM_HAL_INTERRUPT_UART3, CYGHWR_HAL_STM32_UART3_RX, CYGHWR_HAL_STM32_UART3_TX }, +#endif +#if CYGINT_HAL_STM32_UART3>0 + { 3, CYGHWR_HAL_STM32_UART4, 1000, CYGNUM_HAL_INTERRUPT_UART4, CYGHWR_HAL_STM32_UART4_RX, CYGHWR_HAL_STM32_UART4_TX }, +#endif +#if CYGINT_HAL_STM32_UART4>0 + { 4, CYGHWR_HAL_STM32_UART5, 1000, CYGNUM_HAL_INTERRUPT_UART5, CYGHWR_HAL_STM32_UART5_RX, CYGHWR_HAL_STM32_UART5_TX }, +#endif +}; + +//----------------------------------------------------------------------------- + +static void +hal_stm32_serial_init_channel(void* __ch_data) +{ + channel_data_t *chan = (channel_data_t*)__ch_data; + CYG_ADDRESS base = chan->base; + cyg_uint32 cr1, cr2; + + // Enable the PIO lines for the serial channel + + CYGHWR_HAL_STM32_GPIO_SET( chan->rxpin ); + CYGHWR_HAL_STM32_GPIO_SET( chan->txpin ); + + cr2 = CYGHWR_HAL_STM32_UART_CR2_STOP_1; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_UART_CR2, cr2 ); + + cr1 = CYGHWR_HAL_STM32_UART_CR1_M_8; + cr1 |= CYGHWR_HAL_STM32_UART_CR1_TE | CYGHWR_HAL_STM32_UART_CR1_RE; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_UART_CR1, cr1 ); + + // Set up Baud rate + chan->baud_rate = CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL_BAUD; + hal_stm32_uart_setbaud( base, chan->baud_rate ); + + // Enable the uart + cr1 |= CYGHWR_HAL_STM32_UART_CR1_UE; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_UART_CR1, cr1 ); + +} + +void +hal_stm32_serial_putc(void *__ch_data, char c) +{ + CYG_ADDRESS base = ((channel_data_t*)__ch_data)->base; + cyg_uint32 sr; + CYGARC_HAL_SAVE_GP(); + + do + { + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_SR, sr ); + } while ((sr & CYGHWR_HAL_STM32_UART_SR_TXE) == 0); + + HAL_WRITE_UINT32( base + CYGHWR_HAL_STM32_UART_DR, c ); + + CYGARC_HAL_RESTORE_GP(); +} + +static cyg_bool +hal_stm32_serial_getc_nonblock(void* __ch_data, cyg_uint8* ch) +{ + CYG_ADDRESS base = ((channel_data_t*)__ch_data)->base; + cyg_uint32 sr; + cyg_uint32 c; + CYGARC_HAL_SAVE_GP(); + + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_SR, sr ); + + if( (sr & CYGHWR_HAL_STM32_UART_SR_RXNE) == 0 ) + return false; + + HAL_READ_UINT32( base + CYGHWR_HAL_STM32_UART_DR, c ); + + *ch = (cyg_uint8)c; + + CYGARC_HAL_RESTORE_GP(); + + return true; +} + +cyg_uint8 +hal_stm32_serial_getc(void* __ch_data) +{ + cyg_uint8 ch; + CYGARC_HAL_SAVE_GP(); + + while(!hal_stm32_serial_getc_nonblock(__ch_data, &ch)); + + CYGARC_HAL_RESTORE_GP(); + return ch; +} + +//============================================================================= +// Virtual vector HAL diagnostics + +#if defined(CYGSEM_HAL_VIRTUAL_VECTOR_DIAG) + +static void +hal_stm32_serial_write(void* __ch_data, const cyg_uint8* __buf, + cyg_uint32 __len) +{ + CYGARC_HAL_SAVE_GP(); + + while(__len-- > 0) + hal_stm32_serial_putc(__ch_data, *__buf++); + + CYGARC_HAL_RESTORE_GP(); +} + +static void +hal_stm32_serial_read(void* __ch_data, cyg_uint8* __buf, cyg_uint32 __len) +{ + CYGARC_HAL_SAVE_GP(); + + while(__len-- > 0) + *__buf++ = hal_stm32_serial_getc(__ch_data); + + CYGARC_HAL_RESTORE_GP(); +} + +cyg_bool +hal_stm32_serial_getc_timeout(void* __ch_data, cyg_uint8* ch) +{ + int delay_count; + channel_data_t* chan = (channel_data_t*)__ch_data; + cyg_bool res; + CYGARC_HAL_SAVE_GP(); + + delay_count = chan->msec_timeout * 10; // delay in .1 ms steps + + for(;;) { + res = hal_stm32_serial_getc_nonblock(__ch_data, ch); + if (res || 0 == delay_count--) + break; + + CYGACC_CALL_IF_DELAY_US(100); + } + + CYGARC_HAL_RESTORE_GP(); + return res; +} + +static int +hal_stm32_serial_control(void *__ch_data, __comm_control_cmd_t __func, ...) +{ + channel_data_t* chan = (channel_data_t*)__ch_data; + CYG_ADDRESS base = ((channel_data_t*)__ch_data)->base; + int ret = 0; + cyg_uint32 cr1; + + va_list ap; + + CYGARC_HAL_SAVE_GP(); + + va_start(ap, __func); + + switch (__func) { + case __COMMCTL_IRQ_ENABLE: + chan->irq_state = 1; + HAL_INTERRUPT_ACKNOWLEDGE( chan->isr_vector ); + HAL_INTERRUPT_UNMASK( chan->isr_vector ); + HAL_READ_UINT32( base+CYGHWR_HAL_STM32_UART_CR1, cr1 ); + cr1 |= CYGHWR_HAL_STM32_UART_CR1_RXNEIE; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_UART_CR1, cr1 ); + break; + case __COMMCTL_IRQ_DISABLE: + ret = chan->irq_state; + chan->irq_state = 0; + HAL_INTERRUPT_MASK( chan->isr_vector ); + HAL_READ_UINT32( base+CYGHWR_HAL_STM32_UART_CR1, cr1 ); + cr1 &= ~CYGHWR_HAL_STM32_UART_CR1_RXNEIE; + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_UART_CR1, cr1 ); + break; + case __COMMCTL_DBG_ISR_VECTOR: + ret = chan->isr_vector; + break; + case __COMMCTL_SET_TIMEOUT: + { + va_list ap; + + va_start(ap, __func); + + ret = chan->msec_timeout; + chan->msec_timeout = va_arg(ap, cyg_uint32); + + va_end(ap); + } + case __COMMCTL_GETBAUD: + ret = chan->baud_rate; + break; + case __COMMCTL_SETBAUD: + chan->baud_rate = va_arg(ap, cyg_int32); + // Should we verify this value here? + hal_stm32_uart_setbaud( base, chan->baud_rate ); + ret = 0; + break; + default: + break; + } + va_end(ap); + CYGARC_HAL_RESTORE_GP(); + return ret; +} + +static int +hal_stm32_serial_isr(void *__ch_data, int* __ctrlc, + CYG_ADDRWORD __vector, CYG_ADDRWORD __data) +{ + channel_data_t* chan = (channel_data_t*)__ch_data; + cyg_uint8 ch; + + CYGARC_HAL_SAVE_GP(); + + *__ctrlc = 0; + + if( hal_stm32_serial_getc_nonblock(__ch_data, &ch) ) + { + if( cyg_hal_is_break( (char *)&ch , 1 ) ) + *__ctrlc = 1; + } + + HAL_INTERRUPT_ACKNOWLEDGE(chan->isr_vector); + + CYGARC_HAL_RESTORE_GP(); + return 1; +} + +static void +hal_stm32_serial_init(void) +{ + hal_virtual_comm_table_t* comm; + int cur; + int i; + + cur = CYGACC_CALL_IF_SET_CONSOLE_COMM(CYGNUM_CALL_IF_SET_COMM_ID_QUERY_CURRENT); + + for( i = 0; i < CYGNUM_HAL_VIRTUAL_VECTOR_COMM_CHANNELS ; i++ ) + { + hal_stm32_serial_init_channel(&stm32_ser_channels[i]); + + CYGACC_CALL_IF_SET_CONSOLE_COMM(i); + comm = CYGACC_CALL_IF_CONSOLE_PROCS(); + CYGACC_COMM_IF_CH_DATA_SET(*comm, &stm32_ser_channels[i]); + CYGACC_COMM_IF_WRITE_SET(*comm, hal_stm32_serial_write); + CYGACC_COMM_IF_READ_SET(*comm, hal_stm32_serial_read); + CYGACC_COMM_IF_PUTC_SET(*comm, hal_stm32_serial_putc); + CYGACC_COMM_IF_GETC_SET(*comm, hal_stm32_serial_getc); + CYGACC_COMM_IF_CONTROL_SET(*comm, hal_stm32_serial_control); + CYGACC_COMM_IF_DBG_ISR_SET(*comm, hal_stm32_serial_isr); + CYGACC_COMM_IF_GETC_TIMEOUT_SET(*comm, hal_stm32_serial_getc_timeout); + } + + // Restore original console + CYGACC_CALL_IF_SET_CONSOLE_COMM(cur); + + // set debug channel baud rate if different +#if (CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL_BAUD != CYGNUM_HAL_VIRTUAL_VECTOR_DEBUG_CHANNEL_BAUD) + stm32_ser_channels[CYGNUM_HAL_VIRTUAL_VECTOR_DEBUG_CHANNEL]->baud_rate = + CYGNUM_HAL_VIRTUAL_VECTOR_DEBUG_CHANNEL_BAUD; + update_baud_rate( &stm32_ser_channels[CYGNUM_HAL_VIRTUAL_VECTOR_DEBUG_CHANNEL] ); +#endif + +} + +void +cyg_hal_plf_comms_init(void) +{ + static int initialized = 0; + + if (initialized) + return; + + initialized = 1; + + hal_stm32_serial_init(); +} + +#endif + +//============================================================================= +// Non-Virtual vector HAL diagnostics + +#if !defined(CYGSEM_HAL_VIRTUAL_VECTOR_DIAG) + +void hal_stm32_diag_init(void) +{ + hal_stm32_serial_init( &stm32_ser_channels[CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL] ); +} + +void hal_stm32_diag_putc(char c) +{ + hal_stm32_serial_putc( &stm32_ser_channels[CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL], c); +} + +cyg_uint8 hal_stm32_diag_getc(void) +{ + return hal_stm32_serial_getc( &stm32_ser_channels[CYGNUM_HAL_VIRTUAL_VECTOR_CONSOLE_CHANNEL] ); +} + + +#endif + +//----------------------------------------------------------------------------- +// End of hal_diag.c
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/src/stm32_misc.c @@ -0,0 +1,337 @@ +/*========================================================================== +// +// stm32_misc.c +// +// Cortex-M STM32 HAL functions +// +//========================================================================== +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//========================================================================== +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-07-30 +// Description: +// +//####DESCRIPTIONEND#### +// +//========================================================================*/ + +#include <pkgconf/hal.h> +#include <pkgconf/hal_cortexm.h> +#include <pkgconf/hal_cortexm_stm32.h> +#ifdef CYGPKG_KERNEL +#include <pkgconf/kernel.h> +#endif + +#include <cyg/infra/diag.h> +#include <cyg/infra/cyg_type.h> +#include <cyg/infra/cyg_trac.h> // tracing macros +#include <cyg/infra/cyg_ass.h> // assertion macros + +#include <cyg/hal/hal_arch.h> // HAL header +#include <cyg/hal/hal_intr.h> // HAL header +#include <cyg/hal/hal_if.h> // HAL header + +//========================================================================== +// Clock Initialization values + +#if CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV == 1 +# define CYGHWR_HAL_STM32_RCC_CFGR_HPRE CYGHWR_HAL_STM32_RCC_CFGR_HPRE_1 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV == 2 +# define CYGHWR_HAL_STM32_RCC_CFGR_HPRE CYGHWR_HAL_STM32_RCC_CFGR_HPRE_2 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV == 4 +# define CYGHWR_HAL_STM32_RCC_CFGR_HPRE CYGHWR_HAL_STM32_RCC_CFGR_HPRE_4 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV == 8 +# define CYGHWR_HAL_STM32_RCC_CFGR_HPRE CYGHWR_HAL_STM32_RCC_CFGR_HPRE_8 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV == 16 +# define CYGHWR_HAL_STM32_RCC_CFGR_HPRE CYGHWR_HAL_STM32_RCC_CFGR_HPRE_16 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV == 64 +# define CYGHWR_HAL_STM32_RCC_CFGR_HPRE CYGHWR_HAL_STM32_RCC_CFGR_HPRE_64 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV == 128 +# define CYGHWR_HAL_STM32_RCC_CFGR_HPRE CYGHWR_HAL_STM32_RCC_CFGR_HPRE_128 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV == 256 +# define CYGHWR_HAL_STM32_RCC_CFGR_HPRE CYGHWR_HAL_STM32_RCC_CFGR_HPRE_256 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV == 512 +# define CYGHWR_HAL_STM32_RCC_CFGR_HPRE CYGHWR_HAL_STM32_RCC_CFGR_HPRE_512 +#endif + +#if CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK1_DIV == 1 +# define CYGHWR_HAL_STM32_RCC_CFGR_PPRE1 CYGHWR_HAL_STM32_RCC_CFGR_PPRE1_1 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK1_DIV == 2 +# define CYGHWR_HAL_STM32_RCC_CFGR_PPRE1 CYGHWR_HAL_STM32_RCC_CFGR_PPRE1_2 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK1_DIV == 4 +# define CYGHWR_HAL_STM32_RCC_CFGR_PPRE1 CYGHWR_HAL_STM32_RCC_CFGR_PPRE1_4 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK1_DIV == 8 +# define CYGHWR_HAL_STM32_RCC_CFGR_PPRE1 CYGHWR_HAL_STM32_RCC_CFGR_PPRE1_8 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK1_DIV == 16 +# define CYGHWR_HAL_STM32_RCC_CFGR_PPRE1 CYGHWR_HAL_STM32_RCC_CFGR_PPRE1_16 +#endif + +#if CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK2_DIV == 1 +# define CYGHWR_HAL_STM32_RCC_CFGR_PPRE2 CYGHWR_HAL_STM32_RCC_CFGR_PPRE2_1 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK2_DIV == 2 +# define CYGHWR_HAL_STM32_RCC_CFGR_PPRE2 CYGHWR_HAL_STM32_RCC_CFGR_PPRE2_2 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK2_DIV == 4 +# define CYGHWR_HAL_STM32_RCC_CFGR_PPRE2 CYGHWR_HAL_STM32_RCC_CFGR_PPRE2_4 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK2_DIV == 8 +# define CYGHWR_HAL_STM32_RCC_CFGR_PPRE2 CYGHWR_HAL_STM32_RCC_CFGR_PPRE2_8 +#elif CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK2_DIV == 16 +# define CYGHWR_HAL_STM32_RCC_CFGR_PPRE2 CYGHWR_HAL_STM32_RCC_CFGR_PPRE2_16 +#endif + + +//========================================================================== +// Clock frequencies +// +// These are set to the frequencies of the various system clocks. + +cyg_uint32 hal_stm32_sysclk; +cyg_uint32 hal_stm32_hclk; +cyg_uint32 hal_stm32_pclk1; +cyg_uint32 hal_stm32_pclk2; +cyg_uint32 hal_cortexm_systick_clock; + +cyg_uint32 hal_exti_isr( cyg_uint32 vector, CYG_ADDRWORD data ); + +//========================================================================== + +void hal_variant_init( void ) +{ + CYG_ADDRESS rcc = CYGHWR_HAL_STM32_RCC; + + // Enable all devices in RCC + { + HAL_WRITE_UINT32( CYGHWR_HAL_STM32_RCC+CYGHWR_HAL_STM32_RCC_APB2ENR, 0xFFFFFFFF ); + HAL_WRITE_UINT32( CYGHWR_HAL_STM32_RCC+CYGHWR_HAL_STM32_RCC_APB1ENR, 0xFFFFFFFF ); + } + + +#if 1 //!defined(CYG_HAL_STARTUP_RAM) + // Set up clocks from configuration. In the future this should be moved to a + // function so that clock rates can be changed at runtime. + { + cyg_uint32 cr, cfgr; + + // Reset RCC + + HAL_WRITE_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CR, 0x00000001 ); + + // Start up HSE clock + + HAL_READ_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CR, cr ); + cr &= CYGHWR_HAL_STM32_RCC_CR_HSEON|CYGHWR_HAL_STM32_RCC_CR_HSEBYP; + HAL_WRITE_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CR, cr ); + + HAL_READ_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CR, cr ); + cr |= CYGHWR_HAL_STM32_RCC_CR_HSEON; + HAL_WRITE_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CR, cr ); + + // Wait for HSE clock to startup + do + { + HAL_READ_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CR, cr ); + } while( !(cr & CYGHWR_HAL_STM32_RCC_CR_HSERDY) ); + +// HAL_READ_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CFGR, cfgr ); + + // Configure clocks + + hal_stm32_sysclk = CYGARC_HAL_CORTEXM_STM32_INPUT_CLOCK; + + cfgr = 0; + +#if defined(CYGHWR_HAL_CORTEXM_STM32_CLOCK_PLL_SOURCE_HSE) + cfgr |= CYGHWR_HAL_STM32_RCC_CFGR_PLLSRC_HSE; +#elif defined(CYGHWR_HAL_CORTEXM_STM32_CLOCK_PLL_SOURCE_HSE_HALF) + cfgr |= CYGHWR_HAL_STM32_RCC_CFGR_PLLSRC_HSE | + CYGHWR_HAL_STM32_RCC_CFGR_PLLXTPRE; + hal_stm32_sysclk /= 2; +#elif defined(CYGHWR_HAL_CORTEXM_STM32_CLOCK_PLL_SOURCE_HSI_HALF) + hal_stm32_sysclk /= 2; +#endif + + cfgr |= CYGHWR_HAL_STM32_RCC_CFGR_PLLMUL(CYGHWR_HAL_CORTEXM_STM32_CLOCK_PLL_MUL); + cfgr |= CYGHWR_HAL_STM32_RCC_CFGR_HPRE; + cfgr |= CYGHWR_HAL_STM32_RCC_CFGR_PPRE1; + cfgr |= CYGHWR_HAL_STM32_RCC_CFGR_PPRE2; + + HAL_WRITE_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CFGR, cfgr ); + + // Enable the PLL and wait for it to lock + + cr |= CYGHWR_HAL_STM32_RCC_CR_PLLON; + + HAL_WRITE_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CR, cr ); + do + { + HAL_READ_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CR, cr ); + } while( !(cr & CYGHWR_HAL_STM32_RCC_CR_PLLRDY) ); + + // Now switch to use PLL as SYSCLK + + cfgr |= CYGHWR_HAL_STM32_RCC_CFGR_SW_PLL; + + HAL_WRITE_UINT32( rcc+CYGHWR_HAL_STM32_RCC_CFGR, cfgr ); + + // Calculate clocks from configuration + + hal_stm32_sysclk *= CYGHWR_HAL_CORTEXM_STM32_CLOCK_PLL_MUL; + hal_stm32_hclk = hal_stm32_sysclk / CYGHWR_HAL_CORTEXM_STM32_CLOCK_HCLK_DIV; + hal_stm32_pclk1 = hal_stm32_hclk / CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK1_DIV; + hal_stm32_pclk2 = hal_stm32_hclk / CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK2_DIV; + hal_cortexm_systick_clock = hal_stm32_hclk / 8; + } +#endif + + // Attach EXTI springboard to interrupt vectors + HAL_INTERRUPT_ATTACH( CYGNUM_HAL_INTERRUPT_EXTI9_5, hal_exti_isr, 0, 0 ); + HAL_INTERRUPT_ATTACH( CYGNUM_HAL_INTERRUPT_EXTI15_10, hal_exti_isr, 0, 0 ); + + +#ifdef CYGSEM_HAL_VIRTUAL_VECTOR_SUPPORT + hal_if_init(); +#endif +} + +//========================================================================== +// ISR springboard +// +// This is attached to the ISR table entries for EXTI9_5 and EXTI15_10 +// to decode the contents of the EXTI registers and deliver the +// interrupt to the correct ISR. + +cyg_uint32 hal_exti_isr( cyg_uint32 vector, CYG_ADDRWORD data ) +{ + CYG_ADDRESS base = CYGHWR_HAL_STM32_EXTI; + cyg_uint32 imr, pr; + + // Get EXTI pending and interrupt mask registers + HAL_READ_UINT32( base+CYGHWR_HAL_STM32_EXTI_IMR, imr ); + HAL_READ_UINT32( base+CYGHWR_HAL_STM32_EXTI_PR, pr ); + + // Mask PR by IMR and lose ls 5 bits + pr &= imr; + pr &= 0xFFFFFFE0; + + // Isolate LS pending bit and translate into interrupt vector + // number. + HAL_LSBIT_INDEX( vector, pr ); + vector += CYGNUM_HAL_INTERRUPT_EXTI5 - 5; + + // Deliver it + hal_deliver_interrupt( vector ); + + return 0; +} + +//========================================================================== +// GPIO support +// +// These functions provide configuration and IO for GPIO pins. + +__externC void hal_stm32_gpio_set( cyg_uint32 pin ) +{ + cyg_uint32 port = CYGHWR_HAL_STM32_GPIO_PORT(pin); + int bit = CYGHWR_HAL_STM32_GPIO_BIT(pin); + cyg_uint32 cm = CYGHWR_HAL_STM32_GPIO_CFG(pin); + cyg_uint32 cr; + + if( pin == CYGHWR_HAL_STM32_GPIO_NONE ) + return; + + if( bit > 7 ) port += 4, bit -= 8; + HAL_READ_UINT32( port, cr ); + cr &= ~(0xF<<(bit*4)); + cr |= cm<<(bit*4); + HAL_WRITE_UINT32( port, cr ); + + // If this is a pullup/down input, set the ODR bit to switch on + // the appropriate pullup/down resistor. + if( cm == (CYGHWR_HAL_STM32_GPIO_MODE_IN|CYGHWR_HAL_STM32_GPIO_CNF_PULL) ) + { + cyg_uint32 odr; + port = CYGHWR_HAL_STM32_GPIO_PORT( pin ); + HAL_READ_UINT32( port+CYGHWR_HAL_STM32_GPIO_ODR, odr ); + if( pin & CYGHWR_HAL_STM32_GPIO_PULLUP ) + odr |= (1<<bit); + else + odr &= ~(1<<bit); + HAL_WRITE_UINT32( port+CYGHWR_HAL_STM32_GPIO_ODR, odr ); + } +} + +__externC void hal_stm32_gpio_out( cyg_uint32 pin, int val ) +{ + cyg_uint32 port = CYGHWR_HAL_STM32_GPIO_PORT(pin); + int bit = CYGHWR_HAL_STM32_GPIO_BIT(pin); + + port += CYGHWR_HAL_STM32_GPIO_BSRR; + if( (val&1) == 0 ) port += 4; + HAL_WRITE_UINT32( port, 1<<bit ); +} + +__externC void hal_stm32_gpio_in ( cyg_uint32 pin, int *val ) +{ + cyg_uint32 port = CYGHWR_HAL_STM32_GPIO_PORT(pin); + int bit = CYGHWR_HAL_STM32_GPIO_BIT(pin); + cyg_uint32 pd; + + HAL_READ_UINT32( port+CYGHWR_HAL_STM32_GPIO_IDR, pd ); + *val = (pd>>bit)&1; +} + +//========================================================================== +// UART baud rate +// +// Set the baud rate divider of a UART based on the requested rate and +// the current APB clock settings. + +void hal_stm32_uart_setbaud( cyg_uint32 base, cyg_uint32 baud ) +{ + cyg_uint32 apbclk = hal_stm32_pclk1; + cyg_uint32 int_div, frac_div; + cyg_uint32 brr; + + if( base == CYGHWR_HAL_STM32_UART1 ) + apbclk = hal_stm32_pclk2; + + int_div = (25 * apbclk ) / (4 * baud ); + brr = ( int_div / 100 ) << 4; + frac_div = int_div - (( brr >> 4 ) * 100 ); + + brr |= (((frac_div * 16 ) + 50 ) / 100) & 0xF; + + HAL_WRITE_UINT32( base+CYGHWR_HAL_STM32_UART_BRR, brr ); +} + +//========================================================================== +// EOF stm32_misc.c
new file mode 100644 --- /dev/null +++ b/packages/hal/cortexm/stm32/var/current/tests/timers.c @@ -0,0 +1,358 @@ +/*============================================================================= +// +// timers.c +// +// Test for STM32 Timers +// +//============================================================================= +//####ECOSGPLCOPYRIGHTBEGIN#### +// ------------------------------------------- +// This file is part of eCos, the Embedded Configurable Operating System. +// Copyright (C) 2008 eCosCentric Limited. +// +// eCos 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 2 or (at your option) any later version. +// +// eCos 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 eCos; if not, write to the Free Software Foundation, Inc., +// 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA. +// +// As a special exception, if other files instantiate templates or use macros +// or inline functions from this file, or you compile this file and link it +// with other works to produce a work based on this file, this file does not +// by itself cause the resulting work to be covered by the GNU General Public +// License. However the source code for this file must still be made available +// in accordance with section (3) of the GNU General Public License. +// +// This exception does not invalidate any other reasons why a work based on +// this file might be covered by the GNU General Public License. +// ------------------------------------------- +//####ECOSGPLCOPYRIGHTEND#### +//============================================================================= +//#####DESCRIPTIONBEGIN#### +// +// Author(s): nickg +// Date: 2008-09-11 +// +//####DESCRIPTIONEND#### +// +//===========================================================================*/ + +#include <pkgconf/system.h> +#include <pkgconf/hal.h> + +#if defined(CYGPKG_KERNEL) +#include <pkgconf/kernel.h> +#endif + +#include <cyg/infra/testcase.h> + +//============================================================================= +// Check all required packages and components are present + +#if !defined(CYGPKG_KERNEL) || !defined(CYGPKG_KERNEL_API) + +#define NA_MSG "Configuration insufficient" + +#endif + +//============================================================================= +// If everything is present, compile the full test. + +#ifndef NA_MSG + +#include <cyg/hal/hal_arch.h> +#include <cyg/hal/hal_io.h> +#include <cyg/hal/hal_if.h> + +#include <cyg/kernel/kapi.h> +#include <cyg/infra/diag.h> +#include <string.h> + +//============================================================================= + +#define LOOPS 24 // == 2 minutes + +#define STACK_SIZE 8000 + +static int test_stack[(STACK_SIZE/sizeof(int))]; +static cyg_thread test_thread; +static cyg_handle_t main_thread; + +//============================================================================= + +struct timer +{ + cyg_uint32 timer; + cyg_uint32 base; + cyg_uint32 vector; + cyg_uint32 priority; + cyg_uint32 interval; + + cyg_uint32 ticks; + + cyg_uint32 preempt[10]; + + cyg_uint32 preempt_dsr[10]; + cyg_uint32 dsr_count[10]; + + cyg_interrupt interrupt_object; + cyg_handle_t interrupt_handle; +}; + +struct timer timers[] = +{ +#if 0 + { 1, CYGHWR_HAL_STM32_TIM1, CYGNUM_HAL_INTERRUPT_TIM1_UP, 0x20, 1000 }, +#elif 1 + { 1, CYGHWR_HAL_STM32_TIM1, CYGNUM_HAL_INTERRUPT_TIM1_UP, 0x20, 127 }, + { 2, CYGHWR_HAL_STM32_TIM2, CYGNUM_HAL_INTERRUPT_TIM2, 0x30, 355 }, + { 3, CYGHWR_HAL_STM32_TIM3, CYGNUM_HAL_INTERRUPT_TIM3, 0x40, 731 }, + { 4, CYGHWR_HAL_STM32_TIM4, CYGNUM_HAL_INTERRUPT_TIM4, 0x50, 999 }, + { 5, CYGHWR_HAL_STM32_TIM5, CYGNUM_HAL_INTERRUPT_TIM5, 0x60, 1453 }, + { 6, CYGHWR_HAL_STM32_TIM6, CYGNUM_HAL_INTERRUPT_TIM6, 0x70, 1931 }, + { 7, CYGHWR_HAL_STM32_TIM7, CYGNUM_HAL_INTERRUPT_TIM7, 0x80, 2011 }, + { 8, CYGHWR_HAL_STM32_TIM8, CYGNUM_HAL_INTERRUPT_TIM8_UP, 0x90, 2345 }, +#endif + { 0, 0, 0, 0 } +}; + +//============================================================================= + +volatile cyg_uint32 ticks = 0; +volatile cyg_uint32 nesting = 0; +volatile cyg_uint32 max_nesting = 0; +volatile cyg_uint32 max_nesting_seen = 0; +volatile cyg_uint32 current = 0; +volatile cyg_uint32 in_dsr = 0; + +//============================================================================= + +__externC cyg_uint32 hal_stm32_pclk1; +__externC cyg_uint32 hal_stm32_pclk2; + +void init_timer( cyg_uint32 base, cyg_uint32 interval ) +{ + cyg_uint32 period = hal_stm32_pclk1; + + if( base == CYGHWR_HAL_STM32_TIM1 || base == CYGHWR_HAL_STM32_TIM8 ) + { + period = hal_stm32_pclk2; + if( CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK2_DIV != 1 ) + period *= 2; + } + else + { + if( CYGHWR_HAL_CORTEXM_STM32_CLOCK_PCLK1_DIV != 1 ) + period *= 2; + } + + period = period / 1000000; + + HAL_WRITE_UINT32(base+CYGHWR_HAL_STM32_TIM_PSC, period-1 ); + + HAL_WRITE_UINT32(base+CYGHWR_HAL_STM32_TIM_CR2, 0 ); + + HAL_WRITE_UINT32(base+CYGHWR_HAL_STM32_TIM_DIER, CYGHWR_HAL_STM32_TIM_DIER_UIE ); + + HAL_WRITE_UINT32(base+CYGHWR_HAL_STM32_TIM_ARR, interval ); + + HAL_WRITE_UINT32(base+CYGHWR_HAL_STM32_TIM_CR1, CYGHWR_HAL_STM32_TIM_CR1_CEN); +} + +//============================================================================= + +cyg_uint32 timer_isr( cyg_uint32 vector, CYG_ADDRWORD data ) +{ + struct timer *t = (struct timer *)data; + cyg_uint32 preempt = current; + CYG_ADDRWORD base = t->base; + cyg_uint32 cnt; + + current = t->timer; + t->ticks++; + ticks++; + t->preempt[preempt]++; + nesting++; + + // Count only first ISR to preempt a DSR + if( preempt == 0 ) + t->preempt_dsr[in_dsr]++; + + HAL_WRITE_UINT32(t->base+CYGHWR_HAL_STM32_TIM_SR, 0 ); + + if( nesting > max_nesting ) + max_nesting = nesting; + + // Loiter here for a proportion of the timer interval to give + // other timers the chance to preempt us. + do + { + HAL_READ_UINT32( base+CYGHWR_HAL_STM32_TIM_CNT, cnt ); + } while( cnt < t->interval/10 ); + + nesting--; + current = preempt; + + if( (t->ticks % 10) == 0 ) + return 3; + else + return 1; +} + +//============================================================================= + +void timer_dsr( cyg_uint32 vector, cyg_uint32 count, CYG_ADDRWORD data ) +{ + struct timer *t = (struct timer *)data; + int i; + + in_dsr = t->timer; + + if( count >= 8 ) + count = 8; + + t->dsr_count[count]++; + + // Loiter for a while + for( i = 0; i < t->interval/10; i++) + continue; + + in_dsr = 0; +} + +//============================================================================= + +void +timers_test(cyg_addrword_t data) +{ + int loops = LOOPS; + int i; + CYG_INTERRUPT_STATE istate; + + CYG_TEST_INIT(); + + CYG_TEST_INFO("Start Timers test"); + + for( i = 0; timers[i].timer != 0; i++ ) + { + struct timer *t = &timers[i]; + + init_timer( t->base, t->interval ); + + cyg_interrupt_create( t->vector, + t->priority, + (cyg_addrword_t)t, + timer_isr, + timer_dsr, + &t->interrupt_handle, + &t->interrupt_object + ); + + cyg_interrupt_attach( t->interrupt_handle ); + cyg_interrupt_unmask( t->vector ); + + } + + while( loops-- ) + { + int j; + + // 5 second delay + cyg_thread_delay( 5*100 ); + + // Disable interrupts while we print details, otherwise it + // comes out very slowly. + HAL_DISABLE_INTERRUPTS( istate ); + + if( max_nesting > max_nesting_seen ) + max_nesting_seen = max_nesting; + + diag_printf("\nISRs max_nesting %d max_nesting_seen %d\n", max_nesting, max_nesting_seen ); + max_nesting = 0; + + diag_printf(" T Ticks "); + + for( j = 0; j < 9; j++ ) + diag_printf("%9d ", j ); + diag_printf("\n"); + + for( i = 0; timers[i].timer != 0; i++ ) + { + struct timer *t = &timers[i]; + + diag_printf("%2d: %9d ", t->timer, t->ticks ); + + for( j = 0; j < 9; j++ ) + diag_printf("%9d ", t->preempt[j] ); + diag_printf("\n"); + + } + + diag_printf("DSRs\n"); + + diag_printf(" T: "); + + for( j = 0; j < 9; j++ ) + diag_printf("%9d ", j ); + diag_printf("\n"); + + for( i = 0; timers[i].timer != 0; i++ ) + { + struct timer *t = &timers[i]; + + diag_printf("%2d: preempt: ", t->timer); + + for( j = 0; j < 9; j++ ) + diag_printf("%9d ", t->preempt_dsr[j] ); + diag_printf("\n"); + + diag_printf(" count: "); + + for( j = 0; j < 9; j++ ) + diag_printf("%9d ", t->dsr_count[j] ); + diag_printf("\n"); + } + + HAL_RESTORE_INTERRUPTS( istate ); + } + + CYG_TEST_PASS_FINISH("Timers test"); +} + +//============================================================================= + +void cyg_user_start(void) +{ + cyg_thread_create(0, // Priority + timers_test, + 0, + "timers test", // Name + test_stack, // Stack + STACK_SIZE, // Size + &main_thread, // Handle + &test_thread // Thread data structure + ); + cyg_thread_resume( main_thread); +} + +//============================================================================= +// Print a message if we cannot run + +#else // NA_MSG + +void cyg_user_start(void) +{ + CYG_TEST_NA(NA_MSG); +} + +#endif // NA_MSG + +//============================================================================= +/* EOF timers.c */
--- a/packages/services/memalloc/common/current/ChangeLog +++ b/packages/services/memalloc/common/current/ChangeLog @@ -1,3 +1,10 @@ +2008-11-03 Nick Garnett <nickg@ecoscentric.com> + + * src/dlmalloc.cxx (MALLOC_COPY): Replace memmove() with memcpy(). + + * include/dlmallocimpl.hxx (class Cyg_Mempool_dlmalloc_Implementation): + Remove spurious typedef in definition of struct malloc_chunk. + 2008-01-06 Andrew Lunn <andrew.lunn@ascom.ch> * src/dlmalloc.cxx (MALLOC_COPY):
--- a/packages/services/memalloc/common/current/include/dlmallocimpl.hxx +++ b/packages/services/memalloc/common/current/include/dlmallocimpl.hxx @@ -102,7 +102,7 @@ public: typedef size_t Cyg_dlmalloc_size_t; - typedef struct malloc_chunk + struct malloc_chunk { Cyg_dlmalloc_size_t prev_size; /* Size of previous chunk (if free). */ Cyg_dlmalloc_size_t size; /* Size in bytes, including overhead. */
--- a/packages/services/memalloc/common/current/src/dlmalloc.cxx +++ b/packages/services/memalloc/common/current/src/dlmalloc.cxx @@ -333,7 +333,7 @@ do { *mcdst++ = *mcsrc++; \ *mcdst++ = *mcsrc++; \ *mcdst = *mcsrc ; \ - } else memmove(dest, src, mcsz); \ + } else memcpy(dest, src, mcsz); \ } while(0) #else /* !CYGIMP_MEMALLOC_ALLOCATOR_DLMALLOC_USE_MEMCPY */
