First coarse run to fix coding style in locm3.

Added --terse and --mailback options to the make stylecheck target. It
also does continue even if it enounters a possible error.

We decided on two exceptions from the linux kernel coding standard:
- Empty wait while loops may end with ; on the same line.
- All blocks after while, if, for have to be in brackets even if they
  only contain one statement. Otherwise it is easy to introduce an
  error.

Checkpatch needs to be adapted to reflect those changes.
This commit is contained in:
Piotr Esden-Tempski
2013-06-12 17:44:07 -07:00
parent 48e0f3326b
commit 7df63fcae0
147 changed files with 3323 additions and 2565 deletions

View File

@@ -49,25 +49,26 @@ LGPL License Terms @ref lgpl_license
#include <libopencm3/cm3/common.h>
#define CM3_LIKELY(expr) (__builtin_expect (!!(expr), 1))
#define CM3_LIKELY(expr) (__builtin_expect(!!(expr), 1))
#ifdef NDEBUG
# define cm3_assert(expr) do { (void)0; } while(0)
# define cm3_assert_not_reached() while(1)
# define cm3_assert(expr) (void)0
# define cm3_assert_not_reached() do { } while (1)
#else
# ifdef CM3_ASSERT_VERBOSE
# define cm3_assert(expr) do { \
if(CM3_LIKELY(expr)) { (void)0; } else { \
if (CM3_LIKELY(expr)) { \
(void)0; \
} else { \
cm3_assert_failed_verbose( \
__FILE__, __LINE__, \
__func__, #expr); \
} \
} while(0)
# define cm3_assert_not_reached() do { \
cm3_assert_failed_verbose( \
__FILE__, __LINE__, \
__func__, 0); \
} while(0)
} while (0)
# define cm3_assert_not_reached() \
cm3_assert_failed_verbose( \
__FILE__, __LINE__, \
__func__, 0)
# else
/** @brief Check if assertion is true.
*
@@ -82,10 +83,12 @@ LGPL License Terms @ref lgpl_license
*
* @param expr expression to check */
# define cm3_assert(expr) do { \
if(CM3_LIKELY(expr)) { (void)0; } else { \
if (CM3_LIKELY(expr)) { \
(void)0; \
} else { \
cm3_assert_failed(); \
} \
} while(0)
} while (0)
/** @brief Check if unreachable code is reached.
*
* If NDEBUG macro is defined, this macro generates code for an infinite loop.
@@ -95,9 +98,7 @@ LGPL License Terms @ref lgpl_license
* The purpose of this macro is to aid in debugging libopencm3 and
* applications using it. It can be used for example to stop execution if an
* unreachable portion of code is reached. */
# define cm3_assert_not_reached() do { \
cm3_assert_failed(); \
} while(0)
# define cm3_assert_not_reached() cm3_assert_failed()
# endif
#endif
@@ -111,7 +112,7 @@ BEGIN_DECLS
* implementation. Usually, a custom implementation of this function should
* report an error in some way (print a message to a debug console, display,
* LED, ...) and halt execution or reboot the device. */
void cm3_assert_failed(void) __attribute__ ((__noreturn__));
void cm3_assert_failed(void) __attribute__((__noreturn__));
/** @brief Called on a failed assertion with verbose messages enabled.
*
@@ -127,7 +128,7 @@ void cm3_assert_failed(void) __attribute__ ((__noreturn__));
* @param func Name of the function where the failed assertion occurred
* @param assert_expr Expression that evaluated to false (can be NULL) */
void cm3_assert_failed_verbose(const char *file, int line, const char *func,
const char *assert_expr) __attribute__ ((__noreturn__));
const char *assert_expr) __attribute__((__noreturn__));
END_DECLS

View File

@@ -46,9 +46,9 @@ typedef uint64_t u64;
#ifdef __GNUC__
# if __GNUC__ > 4 || (__GNUC__ == 4 && __GNUC_MINOR__ > 4)
# define LIBOPENCM3_DEPRECATED(x) __attribute__ ((deprecated (x)))
# define LIBOPENCM3_DEPRECATED(x) __attribute__((deprecated(x)))
# else
# define LIBOPENCM3_DEPRECATED(x) __attribute__ ((deprecated))
# define LIBOPENCM3_DEPRECATED(x) __attribute__((deprecated))
# endif
#else
# define LIBOPENCM3_DEPRECATED(x)
@@ -95,4 +95,7 @@ typedef uint64_t u64;
#define BIT30 (1<<30)
#define BIT31 (1<<31)
#define __packed __attribute__((packed))
#define __aligned(x) __attribute__((aligned(x)))
#endif

View File

@@ -44,37 +44,43 @@ LGPL License Terms @ref lgpl_license
/* ISER: Interrupt Set Enable Registers */
/* Note: 8 32bit Registers */
#define NVIC_ISER(iser_id) MMIO32(NVIC_BASE + 0x00 + (iser_id * 4))
#define NVIC_ISER(iser_id) MMIO32(NVIC_BASE + 0x00 + \
(iser_id * 4))
/* NVIC_BASE + 0x020 (0xE000 E120 - 0xE000 E17F): Reserved */
/* ICER: Interrupt Clear Enable Registers */
/* Note: 8 32bit Registers */
#define NVIC_ICER(icer_id) MMIO32(NVIC_BASE + 0x80 + (icer_id * 4))
#define NVIC_ICER(icer_id) MMIO32(NVIC_BASE + 0x80 + \
(icer_id * 4))
/* NVIC_BASE + 0x0A0 (0xE000 E1A0 - 0xE000 E1FF): Reserved */
/* ISPR: Interrupt Set Pending Registers */
/* Note: 8 32bit Registers */
#define NVIC_ISPR(ispr_id) MMIO32(NVIC_BASE + 0x100 + (ispr_id * 4))
#define NVIC_ISPR(ispr_id) MMIO32(NVIC_BASE + 0x100 + \
(ispr_id * 4))
/* NVIC_BASE + 0x120 (0xE000 E220 - 0xE000 E27F): Reserved */
/* ICPR: Interrupt Clear Pending Registers */
/* Note: 8 32bit Registers */
#define NVIC_ICPR(icpr_id) MMIO32(NVIC_BASE + 0x180 + (icpr_id * 4))
#define NVIC_ICPR(icpr_id) MMIO32(NVIC_BASE + 0x180 + \
(icpr_id * 4))
/* NVIC_BASE + 0x1A0 (0xE000 E2A0 - 0xE00 E2FF): Reserved */
/* IABR: Interrupt Active Bit Register */
/* Note: 8 32bit Registers */
#define NVIC_IABR(iabr_id) MMIO32(NVIC_BASE + 0x200 + (iabr_id * 4))
#define NVIC_IABR(iabr_id) MMIO32(NVIC_BASE + 0x200 + \
(iabr_id * 4))
/* NVIC_BASE + 0x220 (0xE000 E320 - 0xE000 E3FF): Reserved */
/* IPR: Interrupt Priority Registers */
/* Note: 240 8bit Registers */
#define NVIC_IPR(ipr_id) MMIO8(NVIC_BASE + 0x300 + ipr_id)
#define NVIC_IPR(ipr_id) MMIO8(NVIC_BASE + 0x300 + \
ipr_id)
/* STIR: Software Trigger Interrupt Register */
#define NVIC_STIR MMIO32(STIR_BASE)
@@ -104,12 +110,12 @@ IRQ numbers -3 and -6 to -9 are reserved
* specific header file in the corresponding subfolder.
*/
#define WEAK __attribute__((weak))
#include <libopencm3/dispatch/nvic.h>
/* --- NVIC functions ------------------------------------------------------ */
#define WEAK __attribute__ ((weak))
BEGIN_DECLS
void nvic_enable_irq(u8 irqn);

View File

@@ -374,7 +374,7 @@ struct scb_exception_stack_frame {
u32 lr;
u32 pc;
u32 xpsr;
} __attribute__((packed));
} __packed;
#define SCB_GET_EXCEPTION_STACK_FRAME(f) \
do { \

View File

@@ -21,15 +21,17 @@
#ifndef LIBOPENCM3_CM3_SCS_H
#define LIBOPENCM3_CM3_SCS_H
/*
/*
* All the definition hereafter are generic for CortexMx ARMv7-M
* See ARM document "ARMv7-M Architecture Reference Manual" for more details.
* See also ARM document "ARM Compiler toolchain Developing Software for ARM Processors" for details on System Timer/SysTick.
* See also ARM document "ARM Compiler toolchain Developing Software for ARM
* Processors" for details on System Timer/SysTick.
*/
/*
* The System Control Space (SCS) is a memory-mapped 4KB address space that provides 32-bit registers for
* configuration, status reporting and control. The SCS registers divide into the following groups:
* The System Control Space (SCS) is a memory-mapped 4KB address space that
* provides 32-bit registers for configuration, status reporting and control.
* The SCS registers divide into the following groups:
* - system control and identification
* - the CPUID processor identification space
* - system configuration and status
@@ -46,25 +48,27 @@
/*
* Debug Halting Control and Status Register (DHCSR).
*
*
* Purpose Controls halting debug.
* Usage constraints: The effect of modifying the C_STEP or C_MASKINTS bit when the system
* is running with halting debug enabled is UNPREDICTABLE.
* Halting debug is enabled when C_DEBUGEN is set to 1. The system is running when S_HALT is set to 0.
* - When C_DEBUGEN is set to 0, the processor ignores the values of all other bits in this register.
* - For more information about the use of DHCSR see Debug stepping on
* page C1-824.
* Usage constraints: The effect of modifying the C_STEP or C_MASKINTS bit when
* the system is running with halting debug enabled is UNPREDICTABLE.
* Halting debug is enabled when C_DEBUGEN is set to 1. The system is running
* when S_HALT is set to 0.
* - When C_DEBUGEN is set to 0, the processor ignores the values of all other
* bits in this register.
* - For more information about the use of DHCSR see Debug stepping on page
* C1-824.
* Configurations Always implemented.
*/
/* SCS_DHCSR register */
#define SCS_DHCSR MMIO32(SCS_BASE + 0xDF0)
/*
* Debug Core Register Selector Register (DCRSR).
*
* Purpose With the DCRDR, the DCRSR provides debug access to the ARM core registers,
* special-purpose registers, and Floating-point extension registers. A write to DCRSR
* specifies the register to transfer, whether the transfer is a read or a write, and starts
* the transfer.
*
* Purpose With the DCRDR, the DCRSR provides debug access to the ARM core
* registers, special-purpose registers, and Floating-point extension
* registers. A write to DCRSR specifies the register to transfer, whether the
* transfer is a read or a write, and starts the transfer.
* Usage constraints: Only accessible in Debug state.
* Configurations Always implemented.
*
@@ -73,15 +77,16 @@
#define SCS_DCRSR MMIO32(SCS_BASE + 0xDF4)
/*
* Debug Core Register Data Register (DCRDR)
*
* Purpose With the DCRSR, see Debug Core Register Selector Register,
* the DCRDR provides debug access to the ARM core registers,
* special-purpose registers, and Floating-point extension registers. The
* DCRDR is the data register for these accesses.
* - Used on its own, the DCRDR provides a message passing resource between
* an external debugger and a debug agent running on the processor.
*
* Purpose With the DCRSR, see Debug Core Register Selector Register, the DCRDR
* provides debug access to the ARM core registers, special-purpose registers,
* and Floating-point extension registers. The DCRDR is the data register for
* these accesses.
* - Used on its own, the DCRDR provides a message passing resource between an
* external debugger and a debug agent running on the processor.
* Note:
* The architecture does not define any handshaking mechanism for this use of DCRDR.
* The architecture does not define any handshaking mechanism for this use of
* DCRDR.
* Usage constraints: See Use of DCRSR and DCRDR for constraints that apply to
* particular transfers using the DCRSR and DCRDR.
* Configurations Always implemented.
@@ -92,12 +97,13 @@
/*
* Debug Exception and Monitor Control Register (DEMCR).
*
* Purpose Manages vector catch behavior and DebugMonitor handling when debugging.
* Purpose Manages vector catch behavior and DebugMonitor handling when
* debugging.
* Usage constraints:
* - Bits [23:16] provide DebugMonitor exception control.
* - Bits [15:0] provide Debug state, halting debug, control.
* Configurations Always implemented.
*
*
*/
/* SCS_DEMCR register */
#define SCS_DEMCR MMIO32(SCS_BASE + 0xDFC)
@@ -143,20 +149,22 @@
/*
* System Control Space (SCS) => System timer register support in the SCS.
* To configure SysTick, load the interval required between SysTick events to the SysTick Reload
* Value register. The timer interrupt, or COUNTFLAG bit in the SysTick Control and Status
* register, is activated on the transition from 1 to 0, therefore it activates every n+1 clock ticks.
* If you require a period of 100, write 99 to the SysTick Reload Value register. The SysTick Reload
* Value register supports values between 0x1 and 0x00FFFFFF.
* To configure SysTick, load the interval required between SysTick events to
* the SysTick Reload Value register. The timer interrupt, or COUNTFLAG bit in
* the SysTick Control and Status register, is activated on the transition from
* 1 to 0, therefore it activates every n+1 clock ticks. If you require a
* period of 100, write 99 to the SysTick Reload Value register. The SysTick
* Reload Value register supports values between 0x1 and 0x00FFFFFF.
*
* If you want to use SysTick to generate an event at a timed interval, for example 1ms, you can
* use the SysTick Calibration Value Register to scale your value for the Reload register. The
* SysTick Calibration Value Register is a read-only register that contains the number of pulses for
* a period of 10ms, in the TENMS field, bits[23:0].
* If you want to use SysTick to generate an event at a timed interval, for
* example 1ms, you can use the SysTick Calibration Value Register to scale
* your value for the Reload register. The SysTick Calibration Value Register
* is a read-only register that contains the number of pulses for a period of
* 10ms, in the TENMS field, bits[23:0].
*
* This register also has a SKEW bit. Bit[30] == 1 indicates that the calibration for 10ms in the
* TENMS section is not exactly 10ms due to clock frequency. Bit[31] == 1 indicates that the
* reference clock is not provided.
* This register also has a SKEW bit. Bit[30] == 1 indicates that the
* calibration for 10ms in the TENMS section is not exactly 10ms due to clock
* frequency. Bit[31] == 1 indicates that the reference clock is not provided.
*/
/*
* SysTick Control and Status Register (CSR).
@@ -176,14 +184,14 @@
*/
#define CM_SCS_SYST_RVR MMIO32(SCS_BASE + 0x14)
/* SysTick Current Value Register (RVR).
/* SysTick Current Value Register (RVR).
* Purpose Holds the reload value of the SYST_CVR.
* Usage constraints There are no usage constraints.
* Configurations Always implemented.
*/
#define CM_SCS_SYST_CVR MMIO32(SCS_BASE + 0x18)
/*
/*
* SysTick Calibration value Register(Read Only) (CALIB)
* Purpose Reads the calibration value and parameters for SysTick.
* Usage constraints: There are no usage constraints.
@@ -198,72 +206,86 @@
#define SCS_SYST_CSR_TICKINT (BIT1)
/* SysTick uses the processor clock. */
#define SCS_SYST_CSR_CLKSOURCE (BIT2)
/*
* Indicates whether the counter has counted to 0 since the last read of this register:
/*
* Indicates whether the counter has counted to 0 since the last read of this
* register:
* 0 = Timer has not counted to 0
* 1 = Timer has counted to 0.
* 1 = Timer has counted to 0.
*/
#define SCS_SYST_CSR_COUNTFLAG (BIT16)
/* --- CM_SCS_SYST_RVR values ----------------------------------------------- */
/* Bit 0 to 23 => RELOAD The value to load into the SYST_CVR when the counter reaches 0. */
/* --- CM_SCS_SYST_RVR values ---------------------------------------------- */
/* Bit 0 to 23 => RELOAD The value to load into the SYST_CVR when the counter
* reaches 0.
*/
/* Bit 24 to 31 are Reserved */
/* --- CM_SCS_SYST_CVR values ----------------------------------------------- */
/* --- CM_SCS_SYST_CVR values ---------------------------------------------- */
/* Bit0 to 31 => Reads or clears the current counter value. */
/* --- CM_SCS_SYST_CALIB values ----------------------------------------------- */
/*
* Bit0 to 23 => TENMS Optionally, holds a reload value to be used for 10ms (100Hz) timing, subject to system clock
* skew errors. If this field is zero, the calibration value is not known.
/* --- CM_SCS_SYST_CALIB values -------------------------------------------- */
/*
* Bit0 to 23 => TENMS Optionally, holds a reload value to be used for 10ms
* (100Hz) timing, subject to system clock skew errors. If this field is zero,
* the calibration value is not known.
*/
#define SCS_SYST_SYST_CALIB_TENMS_MASK (BIT24-1)
/*
/*
* Bit30 => SKEW Indicates whether the 10ms calibration value is exact:
* 0 = 10ms calibration value is exact.
* 1 = 10ms calibration value is inexact, because of the clock frequency
*/
#define SCS_SYST_SYST_CALIB_VALUE_INEXACT (BIT30)
/*
* Bit31 => NOREF Indicates whether the IMPLEMENTATION DEFINED reference clock is implemented:
/*
* Bit31 => NOREF Indicates whether the IMPLEMENTATION DEFINED reference clock
* is implemented:
* 0 = The reference clock is implemented.
* 1 = The reference clock is not implemented.
* When this bit is 1, the CLKSOURCE bit of the SYST_CSR register is forced to 1 and cannot
* be cleared to 0.
* When this bit is 1, the CLKSOURCE bit of the SYST_CSR register is forced to
* 1 and cannot be cleared to 0.
*/
#define SCS_SYST_SYST_CALIB_REF_NOT_IMPLEMENTED (BIT31)
/*
/*
* System Control Space (SCS) => Data Watchpoint and Trace (DWT).
* See http://infocenter.arm.com/help/index.jsp?topic=/com.arm.doc.ddi0403c/index.html (ARMv7-M Architecture Reference Manual)
* The DWT is an optional debug unit that provides watchpoints, data tracing, and system profiling
* for the processor.
* See http://goo.gl/mZm30 (ARMv7-M Architecture Reference Manual)
* The DWT is an optional debug unit that provides watchpoints, data tracing,
* and system profiling for the processor.
*/
/*
* DWT Control register
* Purpose Provides configuration and status information for the DWT block, and used to control features of the block
/*
* DWT Control register
* Purpose Provides configuration and status information for the DWT block, and
* used to control features of the block
* Usage constraints: There are no usage constraints.
* Configurations Always implemented.
*/
#define SCS_DWT_CTRL MMIO32(DWT_BASE + 0x00)
/*
* DWT_CYCCNT register
* Cycle Count Register (Shows or sets the value of the processor cycle counter, CYCCNT)
* When enabled, CYCCNT increments on each processor clock cycle. On overflow, CYCCNT wraps to zero.
* Cycle Count Register (Shows or sets the value of the processor cycle
* counter, CYCCNT)
* When enabled, CYCCNT increments on each processor clock cycle. On overflow,
* CYCCNT wraps to zero.
*
* Purpose Shows or sets the value of the processor cycle counter, CYCCNT.
* Usage constraints: The DWT unit suspends CYCCNT counting when the processor is in Debug state.
* Configurations Implemented: only when DWT_CTRL.NOCYCCNT is RAZ, see Control register, DWT_CTRL.
* When DWT_CTRL.NOCYCCNT is RAO no cycle counter is implemented and this register is UNK/SBZP.
* Usage constraints: The DWT unit suspends CYCCNT counting when the processor
* is in Debug state.
* Configurations Implemented: only when DWT_CTRL.NOCYCCNT is RAZ, see Control
* register, DWT_CTRL.
* When DWT_CTRL.NOCYCCNT is RAO no cycle counter is implemented and this
* register is UNK/SBZP.
*/
#define SCS_DWT_CYCCNT MMIO32(DWT_BASE + 0x04)
/* DWT_CPICNT register
* Purpose Counts additional cycles required to execute multi-cycle instructions and instruction fetch stalls.
* Usage constraints: The counter initializes to 0 when software enables its counter overflow event by
/* DWT_CPICNT register
* Purpose Counts additional cycles required to execute multi-cycle
* instructions and instruction fetch stalls.
* Usage constraints: The counter initializes to 0 when software enables its
* counter overflow event by
* setting the DWT_CTRL.CPIEVTENA bit to 1.
* Configurations Implemented: only when DWT_CTRL.NOPRFCNT is RAZ, see Control register, DWT_CTRL.
* Configurations Implemented: only when DWT_CTRL.NOPRFCNT is RAZ, see Control
* register, DWT_CTRL.
* If DWT_CTRL.NOPRFCNT is RAO, indicating that the implementation does not
* include the profiling counters, this register is UNK/SBZP.
*/
@@ -284,8 +306,8 @@
/* DWT_PCSR register */
#define SCS_DWT_PCSR MMIO32(DWT_BASE + 0x18)
/* --- SCS_DWT_CTRL values ----------------------------------------------- */
/*
/* --- SCS_DWT_CTRL values ------------------------------------------------- */
/*
* Enables CYCCNT:
* 0 = Disabled, 1 = Enabled
* This bit is UNK/SBZP if the NOCYCCNT bit is RAO.
@@ -295,15 +317,20 @@
/* TODO bit definition values for other DWT_XXX register */
/* Macro to be called at startup to enable SCS & Cycle Counter */
#define SCS_DWT_CYCLE_COUNTER_ENABLED() ( (SCS_DEMCR |= SCS_DEMCR_TRCENA)\
(SCS_DWT_CTRL |= SCS_DWT_CTRL_CYCCNTENA) )
#define SCS_DWT_CYCLE_COUNTER_ENABLED() ((SCS_DEMCR |= SCS_DEMCR_TRCENA)\
(SCS_DWT_CTRL |= SCS_DWT_CTRL_CYCCNTENA))
#define SCS_SYSTICK_DISABLED() (SCS_SYST_CSR=0)
#define SCS_SYSTICK_DISABLED() (SCS_SYST_CSR = 0)
/* Macro to be called at startup to Enable CortexMx SysTick (but IRQ not enabled) */
#define SCS_SYSTICK_ENABLED() (SCS_SYST_CSR=(SCS_SYST_CSR_ENABLE | SCS_SYST_CSR_CLKSOURCE))
/* Macro to be called at startup to Enable CortexMx SysTick (but IRQ not
* enabled)
*/
#define SCS_SYSTICK_ENABLED() (SCS_SYST_CSR = (SCS_SYST_CSR_ENABLE | \
SCS_SYST_CSR_CLKSOURCE))
/* Macro to be called at startup to Enable CortexMx SysTick and IRQ */
#define SCS_SYSTICK_AND_IRQ_ENABLED() (SCS_SYST_CSR=(SCS_SYST_CSR_ENABLE | SCS_SYST_CSR_CLKSOURCE | SCS_SYST_CSR_TICKINT))
#define SCS_SYSTICK_AND_IRQ_ENABLED() (SCS_SYST_CSR = (SCS_SYST_CSR_ENABLE | \
SCS_SYST_CSR_CLKSOURCE | \
SCS_SYST_CSR_TICKINT))
#endif

View File

@@ -29,8 +29,8 @@
/* --- Exclusive load and store instructions ------------------------------- */
u32 __ldrex(volatile u32* addr);
u32 __strex(u32 val, volatile u32* addr);
u32 __ldrex(volatile u32 *addr);
u32 __strex(u32 val, volatile u32 *addr);
void __dmb(void);
/* --- Convenience functions ----------------------------------------------- */
@@ -42,7 +42,7 @@ typedef u32 mutex_t;
#define MUTEX_UNLOCKED 0
#define MUTEX_LOCKED 1
void mutex_lock(mutex_t* m);
void mutex_unlock(mutex_t* m);
void mutex_lock(mutex_t *m);
void mutex_unlock(mutex_t *m);
#endif

View File

@@ -53,14 +53,14 @@
* bit[N] == 0, trace port width of (N+1) not supported
* bit[N] == 1, trace port width of (N+1) supported
*/
#define TPIU_SSPSR_BYTE (1 << 0)
#define TPIU_SSPSR_BYTE (1 << 0)
#define TPIU_SSPSR_HALFWORD (1 << 1)
#define TPIU_SSPSR_WORD (1 << 3)
/* --- TPIU_SSPSR values --------------------------------------------------- */
/* Same format as TPIU_SSPSR, except only one is set */
#define TPIU_CSPSR_BYTE (1 << 0)
#define TPIU_CSPSR_BYTE (1 << 0)
#define TPIU_CSPSR_HALFWORD (1 << 1)
#define TPIU_CSPSR_WORD (1 << 3)

View File

@@ -45,7 +45,7 @@
typedef void (*vector_table_entry_t)(void);
typedef struct {
unsigned int *initial_sp_value; /**< The value the stack pointer is set to initially */
unsigned int *initial_sp_value; /**< Initial stack pointer value. */
vector_table_entry_t reset;
vector_table_entry_t nmi;
vector_table_entry_t hard_fault;