From: rtel Date: Tue, 22 Mar 2016 16:23:37 +0000 (+0000) Subject: Notes: X-Git-Tag: V9.0.0rc2~6 X-Git-Url: https://git.sur5r.net/?a=commitdiff_plain;h=83a941cc6541b83e72fd4c5c31902fdd911dc87a;p=freertos Notes: + The MPU port is not supported in this revision number. + The documentation for the static allocation functions in the header files has not yet been updated for this revision. Kernel updates: + Simplify the static allocation of objects implementation. + Introduce configSUPPORT_DYNAMIC_ALLOCATION in addition to the existing configSUPPORT_STATIC_ALLOCATION so FreeRTOS can be built without providing a heap at all. Demo application updates: + Update the demos to take into account the new configSUPPORT_DYNAMIC_ALLOCATION constant. + Add an MSVC demo that only uses static allocation, and does not include a FreeRTOS heap. + Update the MSVC project to use both configSUPPORT_STATIC_ALLOCATION and configSUPPORT_DYNAMIC_ALLOCATION. + Update the MingW project to use only configSUPPORT_DYNAMIC_ALLOCATION. git-svn-id: https://svn.code.sf.net/p/freertos/code/trunk@2428 1d2547de-c912-0410-9cb9-b8ca96c0e9e2 --- diff --git a/FreeRTOS/Demo/CORTEX_M4F_CEC1302_Keil/peripheral_library/interrupt/interrupt.h~RF181e805.TMP b/FreeRTOS/Demo/CORTEX_M4F_CEC1302_Keil/peripheral_library/interrupt/interrupt.h~RF181e805.TMP deleted file mode 100644 index 9e5ce5e3e..000000000 --- a/FreeRTOS/Demo/CORTEX_M4F_CEC1302_Keil/peripheral_library/interrupt/interrupt.h~RF181e805.TMP +++ /dev/null @@ -1,1177 +0,0 @@ -/**************************************************************************** -* © 2013 Microchip Technology Inc. and its subsidiaries. -* You may use this software and any derivatives exclusively with -* Microchip products. -* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". -* NO WARRANTIES, WHETHER EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, -* INCLUDING ANY IMPLIED WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, -* AND FITNESS FOR A PARTICULAR PURPOSE, OR ITS INTERACTION WITH MICROCHIP -* PRODUCTS, COMBINATION WITH ANY OTHER PRODUCTS, OR USE IN ANY APPLICATION. -* IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, PUNITIVE, -* INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY KIND -* WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP HAS -* BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. -* TO THE FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL -* CLAIMS IN ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF -* FEES, IF ANY, THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE. -* MICROCHIP PROVIDES THIS SOFTWARE CONDITIONALLY UPON YOUR ACCEPTANCE -* OF THESE TERMS. -*/ - -/** @defgroup interrupt interrupt - * @{ - */ -/** @file interrupt.h - \brief This is the header file for interrupt.c - This program is designed to allow the other C programs to be able to use this component - - There are entry points for all C wrapper API implementation - -Platform: This is ARC-based component - -Toolset: Metaware IDE(8.5.1) -Reference: smsc_reusable_fw_requirement.doc */ - -/******************************************************************************* - * SMSC version control information (Perforce): - * - * FILE: $File: //depot_pcs/FWEng/Release/projects/CEC1302_CLIB/release2/Source/hw_blks/kernel/skern/source/interrupt/interrupt.h $ - * REVISION: $Revision: #1 $ - * DATETIME: $DateTime: 2015/12/23 15:37:58 $ - * AUTHOR: $Author: akrishnan $ - * - * Revision history (latest first): - * #xx - *********************************************************************************** - */ - -#ifndef _INTERRUPT_H_ -#define _INTERRUPT_H_ - - -/* public function prototypes */ -void interrupt_block_init(void); -void null_handler(void); -__irq void SysTick_Handler(void); - -/* macro for interrupt control */ -/* 16-bit timers interrupt control */ -#define sbit_TIMER0 ( 1UL << 0UL ) -#define sbit_TIMER1 ( 1UL << 1UL ) -#define sbit_TIMER2 ( 1UL << 2UL ) -#define sbit_TIMER3 ( 1UL << 3Ul ) - -#define disable_timer0_irq() mCLR_BIT(sbit_TIMER0, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_timer0_irq() mSET_BIT(sbit_TIMER0, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_timer0_source() mCLR_SRC_BIT(sbit_TIMER0, MMCR_EC_GIRQ23_SOURCE) -#define get_timer0_source() mGET_BIT(sbit_TIMER0, MMCR_EC_GIRQ23_SOURCE) - -#define disable_timer1_irq() mCLR_BIT(sbit_TIMER1, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_timer1_irq() mSET_BIT(sbit_TIMER1, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_timer1_source() mCLR_SRC_BIT(sbit_TIMER1, MMCR_EC_GIRQ23_SOURCE) -#define get_timer1_source() mGET_BIT(sbit_TIMER1, MMCR_EC_GIRQ23_SOURCE) - -#define disable_timer2_irq() mCLR_BIT(sbit_TIMER2, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_timer2_irq() mSET_BIT(sbit_TIMER2, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_timer2_source() mCLR_SRC_BIT(sbit_TIMER2, MMCR_EC_GIRQ23_SOURCE) -#define get_timer2_source() mGET_BIT(sbit_TIMER2, MMCR_EC_GIRQ23_SOURCE) - -#define disable_timer3_irq() mCLR_BIT(sbit_TIMER3, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_timer3_irq() mSET_BIT(sbit_TIMER3, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_timer3_source() mCLR_SRC_BIT(sbit_TIMER3, MMCR_EC_GIRQ23_SOURCE) -#define get_timer3_source() mGET_BIT(sbit_TIMER3, MMCR_EC_GIRQ23_SOURCE) - - -/* hibernation timers interrupt control */ -#define sbit_HTIMER0 b_bit20 -#define sbit_HTIMER1 b_bit14 - -#define disable_htimer0_irq() mCLR_BIT(sbit_HTIMER0, MMCR_EC_GIRQ17_ENABLE_SET) -#define enable_htimer0_irq() mSET_BIT(sbit_HTIMER0, MMCR_EC_GIRQ17_ENABLE_SET) -#define clear_htimer0_source() mCLR_SRC_BIT(sbit_HTIMER0, MMCR_EC_GIRQ17_SOURCE) -#define get_htimer0_source() mGET_BIT(sbit_HTIMER0, MMCR_EC_GIRQ17_SOURCE) - -#define disable_htimer1_irq() mCLR_BIT(sbit_HTIMER1, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_htimer1_irq() mSET_BIT(sbit_HTIMER1, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_htimer1_source() mCLR_SRC_BIT(sbit_HTIMER1, MMCR_EC_GIRQ23_SOURCE) -#define get_htimer1_source() mGET_BIT(sbit_HTIMER1, MMCR_EC_GIRQ23_SOURCE) - -/* RTC interrupt control */ -#define b_bit18 (1 << 18) -#define b_bit19 (1 << 19) -#define sbit_RTC_INT b_bit18 -#define disable_rtc_irq() mCLR_BIT(sbit_RTC_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define enable_rtc_irq() mSET_BIT(sbit_RTC_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define clear_rtc_irq_source() mCLR_SRC_BIT(sbit_RTC_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define get_rtc_irq_source() mGET_BIT(sbit_RTC_INT, MMCR_EC_GIRQ17_ENABLE_SET) -/* RTC alarm interrupt control */ -#define sbit_RTC_ALM_INT b_bit19 -#define disable_rtc_alm_irq() mCLR_BIT(sbit_RTC_ALM_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define enable_rtc_alm_irq() mSET_BIT(sbit_RTC_ALM_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define clear_rtc_irq_alm_source() mCLR_SRC_BIT(sbit_RTC_ALM_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define get_rtc_irq_alm_source() mGET_BIT(sbit_RTC_ALM_INT, MMCR_EC_GIRQ17_ENABLE_SET) - -/* week timer interrupt control */ -#define sbit_WKTIMER b_bit7 - -#define disable_wktimer_irq() mCLR_BIT(sbit_WKTIMER, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_wktimer_irq() mSET_BIT(sbit_WKTIMER, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_wktimer_source() mCLR_SRC_BIT(sbit_WKTIMER, MMCR_EC_GIRQ23_SOURCE) -#define get_wktimer_source() mGET_BIT(sbit_WKTIMER, MMCR_EC_GIRQ23_SOURCE) - - -/* scan matrix interrupt control */ -#define sbit_SCANNER b_bit16 -#define disable_scanner_irq() mCLR_BIT(sbit_SCANNER, MMCR_EC_GIRQ18_ENABLE_SET) -#define enable_scanner_irq() mSET_BIT(sbit_SCANNER, MMCR_EC_GIRQ18_ENABLE_SET) -#define clear_scanner_source() mCLR_SRC_BIT(sbit_SCANNER, MMCR_EC_GIRQ18_SOURCE) -#define get_scanner_source() mGET_BIT(sbit_SCANNER, MMCR_EC_GIRQ18_SOURCE) - - -/* PS2 interrupt control */ -/* PS2 activity interrupt */ -#define sbit_PS2_ACT_0 b_bit13 -#define sbit_PS2_ACT_1 b_bit14 -#define sbit_PS2_ACT_2 b_bit15 -/* PS2 wakeup interrupt: detect start bit */ -#define sbit_PS2_WK_0A b_bit17 -#define sbit_PS2_WK_1B b_bit20 -#define sbit_PS2_WK_2 b_bit21 - -/* PS2 activity interrupt control */ -#define disable_ps2_act_0_irq() mCLR_BIT(sbit_PS2_ACT_0, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_act_0_irq() mSET_BIT(sbit_PS2_ACT_0, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_act_0_source() mCLR_SRC_BIT(sbit_PS2_ACT_0, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_act_0_source() mGET_BIT(sbit_PS2_ACT_0, MMCR_EC_GIRQ19_SOURCE) - -#define disable_ps2_act_1_irq() mCLR_BIT(sbit_PS2_ACT_1, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_act_1_irq() mSET_BIT(sbit_PS2_ACT_1, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_act_1_source() mCLR_SRC_BIT(sbit_PS2_ACT_1, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_act_1_source() mGET_BIT(sbit_PS2_ACT_1, MMCR_EC_GIRQ19_SOURCE) - -#define disable_ps2_act_2_irq() mCLR_BIT(sbit_PS2_ACT_2, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_act_2_irq() mSET_BIT(sbit_PS2_ACT_2, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_act_2_source() mCLR_SRC_BIT(sbit_PS2_ACT_2, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_act_2_source() mGET_BIT(sbit_PS2_ACT_2, MMCR_EC_GIRQ19_SOURCE) - -/* PS2 wakeup interrupt control */ -#define disable_ps2_wk_0_irq() mCLR_BIT(sbit_PS2_WK_0A, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_wk_0_irq() mSET_BIT(sbit_PS2_WK_0A, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_wk_0_source() mCLR_SRC_BIT(sbit_PS2_WK_0A, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_wk_0_source() mGET_BIT(sbit_PS2_WK_0A, MMCR_EC_GIRQ19_SOURCE) - -#define disable_ps2_wk_1_irq() mCLR_BIT(sbit_PS2_WK_1B, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_wk_1_irq() mSET_BIT(sbit_PS2_WK_1B, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_wk_1_source() mCLR_SRC_BIT(sbit_PS2_WK_1B, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_wk_1_source() mGET_BIT(sbit_PS2_WK_1B, MMCR_EC_GIRQ19_SOURCE) - -#define disable_ps2_wk_2_irq() mCLR_BIT(sbit_PS2_WK_2, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_wk_2_irq() mSET_BIT(sbit_PS2_WK_2, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_wk_2_source() mCLR_SRC_BIT(sbit_PS2_WK_2, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_wk_2_source() mGET_BIT(sbit_PS2_WK_2, MMCR_EC_GIRQ19_SOURCE) - - -/* ICT interrupt control */ -/* capture 0~5 interrupt */ -#define sbit_ICT_CAPTURE0 b_bit17 -#define sbit_ICT_CAPTURE1 b_bit18 -#define sbit_ICT_CAPTURE2 b_bit19 -#define sbit_ICT_CAPTURE3 b_bit20 -#define sbit_ICT_CAPTURE4 b_bit21 -#define sbit_ICT_CAPTURE5 b_bit22 - -/* capture 0 interrupt control */ -#define disable_capture0_irq() mCLR_BIT(sbit_ICT_CAPTURE0, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_capture0_irq() mSET_BIT(sbit_ICT_CAPTURE0, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_capture0_source() mCLR_SRC_BIT(sbit_ICT_CAPTURE0, MMCR_EC_GIRQ23_SOURCE) -#define get_capture0_source() mGET_BIT(sbit_ICT_CAPTURE0, MMCR_EC_GIRQ23_SOURCE) - - -/* SMBus interrupt control */ - - -/* GPIO interrupt control */ - - -/* BC link interrupt control */ -/* bclink A~D interrupt */ -#define sbit_BCLINK_A_BUSY b_bit0 -#define sbit_BCLINK_A_ERR b_bit1 -#define sbit_BCLINK_A_INT b_bit2 -#define sbit_BCLINK_B_BUSY b_bit3 -#define sbit_BCLINK_B_ERR b_bit4 -#define sbit_BCLINK_B_INT b_bit5 -#define sbit_BCLINK_C_BUSY b_bit6 -#define sbit_BCLINK_C_ERR b_bit7 -#define sbit_BCLINK_C_INT b_bit8 -#define sbit_BCLINK_D_BUSY b_bit9 -#define sbit_BCLINK_D_ERR b_bit10 -#define sbit_BCLINK_D_INT b_bit11 - -/* bclink B interrupt control */ -#define disable_bclink_b_busy_irq() mCLR_BIT(sbit_BCLINK_B_BUSY, MMCR_EC_GIRQ18_ENABLE_SET) -#define enable_bclink_b_busy_irq() mSET_BIT(sbit_BCLINK_B_BUSY, MMCR_EC_GIRQ18_ENABLE_SET) -#define clear_bclink_b_busy_source() mCLR_SRC_BIT(sbit_BCLINK_B_BUSY, MMCR_EC_GIRQ18_SOURCE) -#define get_bclink_b_busy_source() mGET_BIT(sbit_BCLINK_B_BUSY, MMCR_EC_GIRQ18_SOURCE) - -#define disable_bclink_b_err_irq() mCLR_BIT(sbit_BCLINK_B_ERR, MMCR_EC_GIRQ18_ENABLE_SET) -#define enable_bclink_b_err_irq() mSET_BIT(sbit_BCLINK_B_ERR, MMCR_EC_GIRQ18_ENABLE_SET) -#define clear_bclink_b_err_source() mCLR_SRC_BIT(sbit_BCLINK_B_ERR, MMCR_EC_GIRQ18_SOURCE) -#define get_bclink_b_err_source() mGET_BIT(sbit_BCLINK_B_ERR, MMCR_EC_GIRQ18_SOURCE) - -#define disable_bclink_b_int_irq() mCLR_BIT(sbit_BCLINK_B_INT, MMCR_EC_GIRQ18_ENABLE_SET) -#define enable_bclink_b_int_irq() mSET_BIT(sbit_BCLINK_B_INT, MMCR_EC_GIRQ18_ENABLE_SET) -#define clear_bclink_b_int_source() mCLR_SRC_BIT(sbit_BCLINK_B_INT, MMCR_EC_GIRQ18_SOURCE) -#define get_bclink_b_int_source() mGET_BIT(sbit_BCLINK_B_INT, MMCR_EC_GIRQ18_SOURCE) - -/* UART interrupt control */ -#define sbit_UART_INT b_bit0 - -#define disable_uart_irq() mCLR_BIT(sbit_UART_INT, MMCR_EC_GIRQ15_ENABLE_SET) -#define enable_uart_irq() mSET_BIT(sbit_UART_INT, MMCR_EC_GIRQ15_ENABLE_SET) -#define clear_uart_irq_source() mCLR_SRC_BIT(sbit_UART_INT, MMCR_EC_GIRQ15_SOURCE) -#define get_uart_irq_source() mGET_BIT(sbit_UART_INT, MMCR_EC_GIRQ15_SOURCE) - -// GIRQ IDs for EC Interrupt Aggregator -enum MEC_GIRQ_IDS -{ - MEC_GIRQ08_ID = 0, - MEC_GIRQ09_ID, - MEC_GIRQ10_ID, - MEC_GIRQ11_ID, - MEC_GIRQ12_ID, - MEC_GIRQ13_ID, - MEC_GIRQ14_ID, - MEC_GIRQ15_ID, - MEC_GIRQ16_ID, - MEC_GIRQ17_ID, - MEC_GIRQ18_ID, - MEC_GIRQ19_ID, - MEC_GIRQ20_ID, - MEC_GIRQ21_ID, - MEC_GIRQ22_ID, - MEC_GIRQ23_ID, - MEC_GIRQ_ID_MAX -}; - -//Bitmask of GIRQ in ECIA Block Registers -#define MEC_GIRQ08_BITMASK (1UL << (MEC_GIRQ08_ID + 8)) -#define MEC_GIRQ09_BITMASK (1UL << (MEC_GIRQ09_ID + 8)) -#define MEC_GIRQ10_BITMASK (1UL << (MEC_GIRQ10_ID + 8)) -#define MEC_GIRQ11_BITMASK (1UL << (MEC_GIRQ11_ID + 8)) -#define MEC_GIRQ12_BITMASK (1UL << (MEC_GIRQ12_ID + 8)) -#define MEC_GIRQ13_BITMASK (1UL << (MEC_GIRQ13_ID + 8)) -#define MEC_GIRQ14_BITMASK (1UL << (MEC_GIRQ14_ID + 8)) -#define MEC_GIRQ15_BITMASK (1UL << (MEC_GIRQ15_ID + 8)) -#define MEC_GIRQ16_BITMASK (1UL << (MEC_GIRQ16_ID + 8)) -#define MEC_GIRQ17_BITMASK (1UL << (MEC_GIRQ17_ID + 8)) -#define MEC_GIRQ18_BITMASK (1UL << (MEC_GIRQ18_ID + 8)) -#define MEC_GIRQ19_BITMASK (1UL << (MEC_GIRQ19_ID + 8)) -#define MEC_GIRQ20_BITMASK (1UL << (MEC_GIRQ20_ID + 8)) -#define MEC_GIRQ21_BITMASK (1UL << (MEC_GIRQ21_ID + 8)) -#define MEC_GIRQ22_BITMASK (1UL << (MEC_GIRQ22_ID + 8)) -#define MEC_GIRQ23_BITMASK (1UL << (MEC_GIRQ23_ID + 8)) - -#define INTERRUPT_MODE_ALL_AGGREGATED (0u) -#define INTERRUPT_MODE_DIRECT (1u) - -// Bit map of GIRQs whose sources can be directly connected to the NVIC -// GIRQs 12 - 18, 23 -#define ECIA_GIRQ_DIRECT_BITMAP (0x0087F000ul) - -/* - * n = b[7:0] = zero-based direct mapped NVIC ID - * m = b[15:8] = zero-based aggregated NVIC ID - * a = b[23:16] = block Aggregator register block ID - * b = b[31:24] = block bit position in Aggregator registers -*/ -#define IROUTE(b,a,m,n) (((uint32_t)(n)&0xFFul) + \ - (((uint32_t)(m)&0xFFul)<<8u) + \ - ((((uint32_t)(a)-8ul)&0x0F)<<16u) + \ - (((uint32_t)(b)&0x1Ful)<<24)) - -#define ECIA_NVIC_ID_BITPOS (0u) -#define ECIA_IA_NVIC_ID_BITPOS (8u) -#define ECIA_GIRQ_ID_BITPOS (16u) -#define ECIA_GIRQ_BIT_BITPOS (24u) - -// -// GIRQ08 -// -#define GPIO_0140_IROUTE IROUTE(0,8,57,57) -#define GPIO_0141_IROUTE IROUTE(1,8,57,57) -#define GPIO_0142_IROUTE IROUTE(2,8,57,57) -#define GPIO_0143_IROUTE IROUTE(3,8,57,57) -#define GPIO_0144_IROUTE IROUTE(4,8,57,57) -#define GPIO_0145_IROUTE IROUTE(5,8,57,57) -#define GPIO_0147_IROUTE IROUTE(7,8,57,57) -// -#define GPIO_0150_IROUTE IROUTE(8,8,57,57) -#define GPIO_0151_IROUTE IROUTE(9,8,57,57) -#define GPIO_0152_IROUTE IROUTE(10,8,57,57) -#define GPIO_0153_IROUTE IROUTE(11,8,57,57) -#define GPIO_0154_IROUTE IROUTE(12,8,57,57) -#define GPIO_0155_IROUTE IROUTE(13,8,57,57) -#define GPIO_0156_IROUTE IROUTE(14,8,57,57) -#define GPIO_0157_IROUTE IROUTE(15,8,57,57) -// -#define GPIO_0160_IROUTE IROUTE(16,8,57,57) -#define GPIO_0161_IROUTE IROUTE(17,8,57,57) -#define GPIO_0162_IROUTE IROUTE(18,8,57,57) -#define GPIO_0163_IROUTE IROUTE(19,8,57,57) -#define GPIO_0164_IROUTE IROUTE(20,8,57,57) -#define GPIO_0165_IROUTE IROUTE(21,8,57,57) -#define GPIO_0166_IROUTE IROUTE(22,8,57,57) -#define GPIO_0167_IROUTE IROUTE(23,8,57,57) - -// -// GIRQ09 -// -#define GPIO_0100_IROUTE IROUTE(0,9,58,58) -#define GPIO_0101_IROUTE IROUTE(1,9,58,58) -#define GPIO_0102_IROUTE IROUTE(2,9,58,58) -#define GPIO_0103_IROUTE IROUTE(3,9,58,58) -#define GPIO_0104_IROUTE IROUTE(4,9,58,58) -#define GPIO_0105_IROUTE IROUTE(5,9,58,58) -#define GPIO_0105_IROUTE IROUTE(5,9,58,58) -#define GPIO_0107_IROUTE IROUTE(7,9,58,58) -// -#define GPIO_0110_IROUTE IROUTE(8,9,58,58) -#define GPIO_0111_IROUTE IROUTE(9,9,58,58) -#define GPIO_0112_IROUTE IROUTE(10,9,58,58) -#define GPIO_0113_IROUTE IROUTE(11,9,58,58) -#define GPIO_0114_IROUTE IROUTE(12,9,58,58) -#define GPIO_0115_IROUTE IROUTE(13,9,58,58) -#define GPIO_0116_IROUTE IROUTE(14,9,58,58) -#define GPIO_0117_IROUTE IROUTE(15,9,58,58) -// -#define GPIO_0120_IROUTE IROUTE(16,9,58,58) -#define GPIO_0121_IROUTE IROUTE(17,9,58,58) -#define GPIO_0122_IROUTE IROUTE(18,9,58,58) -#define GPIO_0124_IROUTE IROUTE(20,9,58,58) -#define GPIO_0125_IROUTE IROUTE(21,9,58,58) -#define GPIO_0126_IROUTE IROUTE(22,9,58,58) -#define GPIO_0127_IROUTE IROUTE(23,9,58,58) -// -#define GPIO_0130_IROUTE IROUTE(24,9,58,58) -#define GPIO_0131_IROUTE IROUTE(25,9,58,58) -#define GPIO_0132_IROUTE IROUTE(26,9,58,58) -#define GPIO_0133_IROUTE IROUTE(27,9,58,58) -#define GPIO_0134_IROUTE IROUTE(28,9,58,58) -#define GPIO_0135_IROUTE IROUTE(29,9,58,58) -#define GPIO_0136_IROUTE IROUTE(30,9,58,58) - -// -// GIRQ10 -// -#define GPIO_0040_IROUTE IROUTE(0,10,59,59) -#define GPIO_0041_IROUTE IROUTE(1,10,59,59) -#define GPIO_0042_IROUTE IROUTE(2,10,59,59) -#define GPIO_0043_IROUTE IROUTE(3,10,59,59) -#define GPIO_0044_IROUTE IROUTE(4,10,59,59) -#define GPIO_0045_IROUTE IROUTE(5,10,59,59) -#define GPIO_0045_IROUTE IROUTE(5,10,59,59) -#define GPIO_0047_IROUTE IROUTE(7,10,59,59) -// -#define GPIO_0050_IROUTE IROUTE(8,10,59,59) -#define GPIO_0051_IROUTE IROUTE(9,10,59,59) -#define GPIO_0052_IROUTE IROUTE(10,10,59,59) -#define GPIO_0053_IROUTE IROUTE(11,10,59,59) -#define GPIO_0054_IROUTE IROUTE(12,10,59,59) -#define GPIO_0055_IROUTE IROUTE(13,10,59,59) -#define GPIO_0056_IROUTE IROUTE(14,10,59,59) -#define GPIO_0057_IROUTE IROUTE(15,10,59,59) -// -#define GPIO_0060_IROUTE IROUTE(16,10,59,59) -#define GPIO_0061_IROUTE IROUTE(17,10,59,59) -#define GPIO_0062_IROUTE IROUTE(18,10,59,59) -#define GPIO_0063_IROUTE IROUTE(19,10,59,59) -#define GPIO_0064_IROUTE IROUTE(20,10,59,59) -#define GPIO_0065_IROUTE IROUTE(21,10,59,59) -#define GPIO_0066_IROUTE IROUTE(22,10,59,59) -#define GPIO_0067_IROUTE IROUTE(23,10,59,59) -// -#define GPIO_0070_IROUTE IROUTE(24,10,59,59) -#define GPIO_0071_IROUTE IROUTE(25,10,59,59) -#define GPIO_0072_IROUTE IROUTE(26,10,59,59) -#define GPIO_0073_IROUTE IROUTE(27,10,59,59) -#define GPIO_0074_IROUTE IROUTE(28,10,59,59) -#define GPIO_0075_IROUTE IROUTE(29,10,59,59) -#define GPIO_0076_IROUTE IROUTE(30,10,59,59) - -// -// GIRQ11 -// -#define GPIO_0000_IROUTE IROUTE(0,11,60,60) -#define GPIO_0001_IROUTE IROUTE(1,11,60,60) -#define GPIO_0002_IROUTE IROUTE(2,11,60,60) -#define GPIO_0003_IROUTE IROUTE(3,11,60,60) -#define GPIO_0004_IROUTE IROUTE(4,11,60,60) -#define GPIO_0005_IROUTE IROUTE(5,11,60,60) -#define GPIO_0006_IROUTE IROUTE(6,11,60,60) -#define GPIO_0007_IROUTE IROUTE(7,11,60,60) -// -#define GPIO_0010_IROUTE IROUTE(8,11,60,60) -#define GPIO_0011_IROUTE IROUTE(9,11,60,60) -#define GPIO_0012_IROUTE IROUTE(10,11,60,60) -#define GPIO_0013_IROUTE IROUTE(11,11,60,60) -#define GPIO_0014_IROUTE IROUTE(12,11,60,60) -#define GPIO_0015_IROUTE IROUTE(13,11,60,60) -#define GPIO_0016_IROUTE IROUTE(14,11,60,60) -#define GPIO_0017_IROUTE IROUTE(15,11,60,60) -// -#define GPIO_0020_IROUTE IROUTE(16,11,60,60) -#define GPIO_0021_IROUTE IROUTE(17,11,60,60) -#define GPIO_0022_IROUTE IROUTE(18,11,60,60) -#define GPIO_0023_IROUTE IROUTE(19,11,60,60) -#define GPIO_0024_IROUTE IROUTE(20,11,60,60) -#define GPIO_0025_IROUTE IROUTE(21,11,60,60) -#define GPIO_0026_IROUTE IROUTE(22,11,60,60) -#define GPIO_0027_IROUTE IROUTE(23,11,60,60) -// -#define GPIO_0030_IROUTE IROUTE(24,11,60,60) -#define GPIO_0031_IROUTE IROUTE(25,11,60,60) -#define GPIO_0032_IROUTE IROUTE(26,11,60,60) -#define GPIO_0033_IROUTE IROUTE(27,11,60,60) -#define GPIO_0034_IROUTE IROUTE(28,11,60,60) -#define GPIO_0035_IROUTE IROUTE(29,11,60,60) -#define GPIO_0036_IROUTE IROUTE(30,11,60,60) - -// -// GIRQ12 -// -#define SMB0_IROUTE IROUTE(0,12,61,0) -#define SMB1_IROUTE IROUTE(1,12,61,1) -#define SMB2_IROUTE IROUTE(2,12,61,2) -#define SMB3_IROUTE IROUTE(3,12,61,3) -// SMB wakes have no direct connection to NVIC, always aggregated -#define SMB0_WAKE_IROUTE IROUTE(4,12,61,61) -#define SMB1_WAKE_IROUTE IROUTE(5,12,61,61) -#define SMB2_WAKE_IROUTE IROUTE(6,12,61,61) -#define SMB3_WAKE_IROUTE IROUTE(7,12,61,61) -#define SMB4_WAKE_IROUTE IROUTE(8,12,61,61) - -// -// GIRQ13 -// -#define DMA0_IROUTE IROUTE(16,13,62,4) -#define DMA1_IROUTE IROUTE(17,13,62,5) -#define DMA2_IROUTE IROUTE(18,13,62,6) -#define DMA3_IROUTE IROUTE(19,13,62,7) -#define DMA4_IROUTE IROUTE(20,13,62,8) -#define DMA5_IROUTE IROUTE(21,13,62,9) -#define DMA6_IROUTE IROUTE(22,13,62,10) -#define DMA7_IROUTE IROUTE(23,13,62,11) -#define DMA8_IROUTE IROUTE(24,13,62,81) -#define DMA9_IROUTE IROUTE(25,13,62,82) -#define DMA10_IROUTE IROUTE(26,13,62,83) -#define DMA11_IROUTE IROUTE(27,13,62,84) - -// -// GIRQ14 -// -#define LPC_BERR_IROUTE IROUTE(2,14,63,12) - -// -// GIRQ15 -// -#define UART0_IROUTE IROUTE(0,15,64,13) -#define EMI0_IROUTE IROUTE(2,15,64,14) -#define ACPI_EC0_IBF_IROUTE IROUTE(6,15,64,15) -#define ACPI_EC0_OBF_IROUTE IROUTE(7,15,64,16) -#define ACPI_EC1_IBF_IROUTE IROUTE(8,15,64,17) -#define ACPI_EC1_OBF_IROUTE IROUTE(9,15,64,18) -#define ACPI_PM1_CTL_IROUTE IROUTE(10,15,64,19) -#define ACPI_PM1_EN_IROUTE IROUTE(11,15,64,20) -#define ACPI_PM1_STS_IROUTE IROUTE(12,15,64,21) -#define EM8042_OBF_IROUTE IROUTE(13,15,64,22) -#define EM8042_IBF_IROUTE IROUTE(14,15,64,23) -#define MBOX_IROUTE IROUTE(15,15,64,24) -#define MBOX_DATA_IROUTE IROUTE(16,15,64,40) - -// -// GIRQ16 -// -#define PECI_IROUTE IROUTE(3,16,65,25) - -// -// GIRQ17 -// -#define TACH0_IROUTE IROUTE(0,17,66,26) -#define TACH1_IROUTE IROUTE(1,17,66,27) -#define PS2_0_WAKE_IROUTE IROUTE(2,17,66,66) -#define PS2_1_WAKE_IROUTE IROUTE(3,17,66,66) -#define PS2_2_WAKE_IROUTE IROUTE(4,17,66,66) -#define PS2_3_WAKE_IROUTE IROUTE(5,17,66,66) -#define BC_WAKE_IROUTE IROUTE(6,17,66,66) -#define ADC_SNGL_IROUTE IROUTE(10,17,66,28) -#define ADC_RPT_IROUTE IROUTE(11,17,66,29) -#define ADC2PWM1_IROUTE IROUTE(12,17,66,30) -#define ADC2PWM2_IROUTE IROUTE(13,17,66,31) -#define PS2_0_IROUTE IROUTE(14,17,66,32) -#define PS2_1_IROUTE IROUTE(15,17,66,33) -#define PS2_2_IROUTE IROUTE(16,17,66,34) -#define PS2_3_IROUTE IROUTE(17,17,66,35) -#define RTC_IROUTE IROUTE(18,17,66,91) -#define RTC_ALARM_IROUTE IROUTE(19,17,66,92) -#define HTIMER_IROUTE IROUTE(20,17,66,38) -#define KSC_IROUTE IROUTE(21,17,66,39) -#define KSC_WAKE_IROUTE IROUTE(22,17,66,66) -#define RPM_STALL_IROUTE IROUTE(23,17,66,41) -#define RPM_SPIN_IROUTE IROUTE(24,17,66,42) -#define PFR_IROUTE IROUTE(25,17,66,43) -#define LED0_IROUTE IROUTE(26,17,66,44) -#define LED1_IROUTE IROUTE(27,17,66,45) -#define LED2_IROUTE IROUTE(28,17,66,46) -#define BCM_ERR_IROUTE IROUTE(29,17,66,47) -#define BCM_BUSY_IROUTE IROUTE(30,17,66,48) - -// -// GIRQ18 -// -#define SPI0_TX_IROUTE IROUTE(0,18,67,36) -#define SPI0_RX_IROUTE IROUTE(1,18,67,37) -#define SPI1_TX_IROUTE IROUTE(2,18,67,55) -#define SPI1_RX_IROUTE IROUTE(3,18,67,56) -#define LED3_IROUTE IROUTE(4,18,67,85) -#define PKE_ERR_IROUTE IROUTE(5,18,67,86) -#define PKE_END_IROUTE IROUTE(6,18,67,87) -#define NDRNG_IROUTE IROUTE(7,18,67,88) -#define AES_IROUTE IROUTE(8,18,67,89) -#define HASH_IROUTE IROUTE(9,18,67,90) - -// -// GIRQ19, Aggregated only -// -#define LRESET_IROUTE IROUTE(0,19,68,68) -#define VCC_PWRGD_IROUTE IROUTE(1,19,68,68) - -// -// GIRQ20, Aggregated only -// -#define GPIO_0200_IROUTE IROUTE(0,20,69,69) -#define GPIO_0201_IROUTE IROUTE(1,20,69,69) -#define GPIO_0202_IROUTE IROUTE(2,20,69,69) -#define GPIO_0203_IROUTE IROUTE(3,20,69,69) -#define GPIO_0204_IROUTE IROUTE(4,20,69,69) -#define GPIO_0206_IROUTE IROUTE(6,20,69,69) -// -#define GPIO_0210_IROUTE IROUTE(8,20,69,69) -#define GPIO_0211_IROUTE IROUTE(9,20,69,69) -#define GPIO_0212_IROUTE IROUTE(10,20,69,69) -#define GPIO_0213_IROUTE IROUTE(11,20,69,69) - -// -// GIRQ21 -// -// No sources - -// -// GIRQ22 -// -// No sources - -// -// GIRQ23 -// -#define BTMR0_IROUTE IROUTE(0,23,72,49) -#define BTMR1_IROUTE IROUTE(1,23,72,50) -#define BTMR2_IROUTE IROUTE(2,23,72,51) -#define BTMR3_IROUTE IROUTE(3,23,72,52) -#define BTMR4_IROUTE IROUTE(4,23,72,53) -#define BTMR5_IROUTE IROUTE(5,23,72,54) - -// GIRQ08 Bit Positions -#define GIRQ08_GPIO_0140_BITPOS (0) -#define GIRQ08_GPIO_0141_BITPOS (1) -#define GIRQ08_GPIO_0142_BITPOS (2) -#define GIRQ08_GPIO_0143_BITPOS (3) -#define GIRQ08_GPIO_0144_BITPOS (4) -#define GIRQ08_GPIO_0145_BITPOS (5) -//#define GIRQ08_GPIO_0146_BITPOS (6) RESERVED -#define GIRQ08_GPIO_0147_BITPOS (7) -// -#define GIRQ08_GPIO_0150_BITPOS (8) -#define GIRQ08_GPIO_0151_BITPOS (9) -#define GIRQ08_GPIO_0152_BITPOS (10) -#define GIRQ08_GPIO_0153_BITPOS (11) -#define GIRQ08_GPIO_0154_BITPOS (12) -#define GIRQ08_GPIO_0155_BITPOS (13) -#define GIRQ08_GPIO_0156_BITPOS (14) -#define GIRQ08_GPIO_0157_BITPOS (15) -// -#define GIRQ08_GPIO_0160_BITPOS (16) -#define GIRQ08_GPIO_0161_BITPOS (17) -#define GIRQ08_GPIO_0162_BITPOS (18) -#define GIRQ08_GPIO_0163_BITPOS (19) -#define GIRQ08_GPIO_0164_BITPOS (20) -#define GIRQ08_GPIO_0165_BITPOS (21) -#define GIRQ08_GPIO_0166_BITPOS (22) -#define GIRQ08_GPIO_0167_BITPOS (23) -// -#define GIRQ08_MASK (0x00FFFFBFul) -#define GIRQ08_WAKE_CAPABLE_MASK (0x00FFFFBFul) -// - -// GIRQ09 Bit Positions -#define GIRQ09_GPIO_0100_BITPOS (0) -#define GIRQ09_GPIO_0101_BITPOS (1) -#define GIRQ09_GPIO_0102_BITPOS (2) -#define GIRQ09_GPIO_0103_BITPOS (3) -#define GIRQ09_GPIO_0104_BITPOS (4) -#define GIRQ09_GPIO_0105_BITPOS (5) -#define GIRQ09_GPIO_0106_BITPOS (6) -#define GIRQ09_GPIO_0107_BITPOS (7) -// -#define GIRQ09_GPIO_0110_BITPOS (8) -#define GIRQ09_GPIO_0111_BITPOS (9) -#define GIRQ09_GPIO_0112_BITPOS (10) -#define GIRQ09_GPIO_0113_BITPOS (11) -#define GIRQ09_GPIO_0114_BITPOS (12) -#define GIRQ09_GPIO_0115_BITPOS (13) -#define GIRQ09_GPIO_0116_BITPOS (14) -#define GIRQ09_GPIO_0117_BITPOS (15) -// -#define GIRQ09_GPIO_0120_BITPOS (16) -#define GIRQ09_GPIO_0121_BITPOS (17) -#define GIRQ09_GPIO_0122_BITPOS (18) -//#define GIRQ09_GPIO_0123_BITPOS (19) RESERVED -#define GIRQ09_GPIO_0124_BITPOS (20) -#define GIRQ09_GPIO_0125_BITPOS (21) -#define GIRQ09_GPIO_0126_BITPOS (22) -#define GIRQ09_GPIO_0127_BITPOS (23) -// -#define GIRQ09_GPIO_0130_BITPOS (24) -#define GIRQ09_GPIO_0131_BITPOS (25) -#define GIRQ09_GPIO_0132_BITPOS (26) -#define GIRQ09_GPIO_0133_BITPOS (27) -#define GIRQ09_GPIO_0134_BITPOS (28) -#define GIRQ09_GPIO_0135_BITPOS (29) -#define GIRQ09_GPIO_0136_BITPOS (30) -//#define GIRQ09_GPIO_0137_BITPOS (31) RESERVED -// -#define GIRQ09_MASK (0x7FF7FFFFul) -#define GIRQ09_WAKE_CAPABLE_MASK (0x7FF7FFFFul) -// - -// GIRQ10 Bit Positions -#define GIRQ10_GPIO_0040_BITPOS (0) -#define GIRQ10_GPIO_0041_BITPOS (1) -#define GIRQ10_GPIO_0042_BITPOS (2) -#define GIRQ10_GPIO_0043_BITPOS (3) -#define GIRQ10_GPIO_0044_BITPOS (4) -#define GIRQ10_GPIO_0045_BITPOS (5) -#define GIRQ10_GPIO_0046_BITPOS (6) -#define GIRQ10_GPIO_0047_BITPOS (7) -// -#define GIRQ10_GPIO_0050_BITPOS (8) -#define GIRQ10_GPIO_0051_BITPOS (9) -#define GIRQ10_GPIO_0052_BITPOS (10) -#define GIRQ10_GPIO_0053_BITPOS (11) -#define GIRQ10_GPIO_0054_BITPOS (12) -#define GIRQ10_GPIO_0055_BITPOS (13) -#define GIRQ10_GPIO_0056_BITPOS (14) -#define GIRQ10_GPIO_0057_BITPOS (15) -// -#define GIRQ10_GPIO_0060_BITPOS (16) -#define GIRQ10_GPIO_0061_BITPOS (17) -#define GIRQ10_GPIO_0062_BITPOS (18) -#define GIRQ10_GPIO_0063_BITPOS (19) -#define GIRQ10_GPIO_0064_BITPOS (20) -#define GIRQ10_GPIO_0065_BITPOS (21) -#define GIRQ10_GPIO_0066_BITPOS (22) -#define GIRQ10_GPIO_0067_BITPOS (23) -// -#define GIRQ10_GPIO_0070_BITPOS (24) -#define GIRQ10_GPIO_0071_BITPOS (25) -#define GIRQ10_GPIO_0072_BITPOS (26) -#define GIRQ10_GPIO_0073_BITPOS (27) -#define GIRQ10_GPIO_0074_BITPOS (28) -#define GIRQ10_GPIO_0075_BITPOS (29) -#define GIRQ10_GPIO_0076_BITPOS (30) -//#define GIRQ10_GPIO_0077_BITPOS (31) RESERVED -// -#define GIRQ10_MASK (0x7FFFFFFFul) -#define GIRQ10_WAKE_CAPABLE_MASK (0x7FFFFFFFul) -// - -// GIRQ11 Bit Positions -#define GIRQ11_GPIO_0000_BITPOS (0) -#define GIRQ11_GPIO_0001_BITPOS (1) -#define GIRQ11_GPIO_0002_BITPOS (2) -#define GIRQ11_GPIO_0003_BITPOS (3) -#define GIRQ11_GPIO_0004_BITPOS (4) -#define GIRQ11_GPIO_0005_BITPOS (5) -#define GIRQ11_GPIO_0006_BITPOS (6) -#define GIRQ11_GPIO_0007_BITPOS (7) -// -#define GIRQ11_GPIO_0010_BITPOS (8) -#define GIRQ11_GPIO_0011_BITPOS (9) -#define GIRQ11_GPIO_0012_BITPOS (10) -#define GIRQ11_GPIO_0013_BITPOS (11) -#define GIRQ11_GPIO_0014_BITPOS (12) -#define GIRQ11_GPIO_0015_BITPOS (13) -#define GIRQ11_GPIO_0016_BITPOS (14) -#define GIRQ11_GPIO_0017_BITPOS (15) -// -#define GIRQ11_GPIO_0020_BITPOS (16) -#define GIRQ11_GPIO_0021_BITPOS (17) -#define GIRQ11_GPIO_0022_BITPOS (18) -#define GIRQ11_GPIO_0023_BITPOS (19) -#define GIRQ11_GPIO_0024_BITPOS (20) -#define GIRQ11_GPIO_0025_BITPOS (21) -#define GIRQ11_GPIO_0026_BITPOS (22) -#define GIRQ11_GPIO_0027_BITPOS (23) -// -#define GIRQ11_GPIO_0030_BITPOS (24) -#define GIRQ11_GPIO_0031_BITPOS (25) -#define GIRQ11_GPIO_0032_BITPOS (26) -#define GIRQ11_GPIO_0033_BITPOS (27) -#define GIRQ11_GPIO_0034_BITPOS (28) -#define GIRQ11_GPIO_0035_BITPOS (29) -#define GIRQ11_GPIO_0036_BITPOS (30) -//#define GIRQ11_GPIO_0037_BITPOS (31) RESERVED -// -#define GIRQ11_MASK (0x7FFFFFFFul) -#define GIRQ11_WAKE_CAPABLE_MASK (0x7FFFFFFFul) -// - -// GIRQ12 Bit Positions -#define GIRQ12_SMBUS0_BITPOS (0) -#define GIRQ12_SMBUS1_BITPOS (1) -#define GIRQ12_SMBUS2_BITPOS (2) -#define GIRQ12_SMBUS3_BITPOS (3) -#define GIRQ12_SMBUS0_WAKE_BITPOS (4) -#define GIRQ12_SMBUS1_WAKE_BITPOS (5) -#define GIRQ12_SMBUS2_WAKE_BITPOS (6) -#define GIRQ12_SMBUS3_WAKE_BITPOS (7) -#define GIRQ12_SMBUS4_WAKE_BITPOS (8) -// RESERVED bits[31:9] -#define GIRQ12_MASK (0x01FFul) -#define GIRQ12_WAKE_CAPABLE_MASK (0x01F0ul) -// - -// GIRQ13 Bit Positions -#define GIRQ13_DMA0_BITPOS (16) -#define GIRQ13_DMA1_BITPOS (17) -#define GIRQ13_DMA2_BITPOS (18) -#define GIRQ13_DMA3_BITPOS (19) -#define GIRQ13_DMA4_BITPOS (20) -#define GIRQ13_DMA5_BITPOS (21) -#define GIRQ13_DMA6_BITPOS (22) -#define GIRQ13_DMA7_BITPOS (23) -#define GIRQ13_DMA8_BITPOS (24) -#define GIRQ13_DMA9_BITPOS (25) -#define GIRQ13_DMA10_BITPOS (26) -#define GIRQ13_DMA11_BITPOS (27) -// -#define GIRQ13_MASK (0x0FFF0000ul) -#define GIRQ13_WAKE_CAPABLE_MASK (0x00000000ul) -// - -// GIRQ14 Bit Positions -#define GIRQ14_LPC_BITPOS (2) -// -#define GIRQ14_MASK (0x04ul) -#define GIRQ14_WAKE_CAPABLE_MASK (0x00ul) -// - -// GIRQ15 Bit Positions -#define GIRQ15_UART0_BITPOS (0) -#define GIRQ15_IMAP_BITPOS (2) -#define GIRQ15_KBD_K_BITPOS (3) -#define GIRQ15_KBD_M_BITPOS (4) -#define GIRQ15_ACPI0_IBF_BITPOS (6) -#define GIRQ15_ACPI0_OBF_BITPOS (7) -#define GIRQ15_ACPI1_IBF_BITPOS (8) -#define GIRQ15_ACPI1_OBF_BITPOS (9) -#define GIRQ15_ACPI_PM1CTL_BITPOS (10) -#define GIRQ15_ACPI_PM1EN_BITPOS (11) -#define GIRQ15_ACPI_PM1STS_BITPOS (12) -#define GIRQ15_MF8042_OBF_BITPOS (13) -#define GIRQ15_MF8042_IBF_BITPOS (14) -#define GIRQ15_MAILBOX_BITPOS (15) -#define GIRQ15_MAILBOX_DATA_BITPOS (16) -// -#define GIRQ15_MASK (0x01FFDDul) -#define GIRQ15_WAKE_CAPABLE_MASK (0x000000ul) -// - -// GIRQ16 Bit Positions -#define GIRQ16_PECI_BITPOS (3) -// -#define GIRQ16_MASK (0x08ul) -#define GIRQ16_WAKE_CAPABLE_MASK (0x00ul) -// - -// GIRQ17 Bit Positions -#define GIRQ17_TACH0_BITPOS (0) -#define GIRQ17_TACH1_BITPOS (1) -#define GIRQ17_PS2_0_WAKE_BITPOS (2) -#define GIRQ17_PS2_1_WAKE_BITPOS (3) -#define GIRQ17_PS2_2_WAKE_BITPOS (4) -#define GIRQ17_PS2_3_WAKE_BITPOS (5) -#define GIRQ17_BC_WAKE_BITPOS (6) -// RESERVED b[9:7] -#define GIRQ17_ADC_INT0_BITPOS (10) -#define GIRQ17_ADC_INT1_BITPOS (11) -#define GIRQ17_V2P_INT0_BITPOS (12) -#define GIRQ17_V2P_INT1_BITPOS (13) -#define GIRQ17_PS2_0_BITPOS (14) -#define GIRQ17_PS2_1_BITPOS (15) -#define GIRQ17_PS2_2_BITPOS (16) -#define GIRQ17_PS2_3_BITPOS (17) -// RESERVED b[19:18] -#define GIRQ17_HIBTMR_BITPOS (20) -#define GIRQ17_KEY_INT_BITPOS (21) -#define GIRQ17_KEY_INT_WAKE_BITPOS (22) -#define GIRQ17_RPM_STALL_BITPOS (23) -#define GIRQ17_RPM_SPIN_BITPOS (24) -#define GIRQ17_VBAT_BITPOS (25) -#define GIRQ17_LED0_BITPOS (26) -#define GIRQ17_LED1_BITPOS (27) -#define GIRQ17_LED2_BITPOS (28) -#define GIRQ17_MBC_ERR_BITPOS (29) -#define GIRQ17_MBC_BUSY_BITPOS (30) -// -#define GIRQ17_MASK (0x7FF3FC7Ful) -#define GIRQ17_WAKE_CAPABLE_MASK (0x0230007Cul) -// - -// GIRQ18 Bit Positions -#define GIRQ18_SPI0_TX_BITPOS (0) -#define GIRQ18_SPI0_RX_BITPOS (1) -#define GIRQ18_SPI1_TX_BITPOS (2) -#define GIRQ18_SPI1_RX_BITPOS (3) -#define GIRQ18_LED3_BITPOS (4) // NVIC 85 -#define GIRQ18_PKE_ERR_BITPOS (5) // NVIC 86 -#define GIRQ18_PKE_END_BITPOS (6) // NVIC 87 -#define GIRQ18_TRNG_BITPOS (7) // NVIC 88 -#define GIRQ18_AES_BITPOS (8) // NVIC 89 -#define GIRQ18_HASH_BITPOS (9) // NVIC 90 -// -#define GIRQ18_MASK (0x0FFul) -#define GIRQ18_WAKE_CAPABLE_MASK (0x000ul) -// - -// GIRQ19 Bit Positions -#define GIRQ19_LRESET_BITPOS (0) -#define GIRQ19_VCC_PWRGD_BITPOS (1) -// -#define GIRQ19_MASK (0x03ul) -#define GIRQ19_WAKE_CAPABLE_MASK (0x03ul) -// - -// GIRQ20 Bit Positions -#define GIRQ20_GPIO_0200_BITPOS (0) -#define GIRQ20_GPIO_0201_BITPOS (1) -#define GIRQ20_GPIO_0202_BITPOS (2) -#define GIRQ20_GPIO_0203_BITPOS (3) -#define GIRQ20_GPIO_0204_BITPOS (4) -//#define GIRQ20_GPIO_0205_BITPOS (5) -#define GIRQ20_GPIO_0206_BITPOS (6) -//#define GIRQ20_GPIO_0207_BITPOS (7) -// -#define GIRQ20_GPIO_0210_BITPOS (8) -#define GIRQ20_GPIO_0211_BITPOS (9) -#define GIRQ20_GPIO_0212_BITPOS (10) -#define GIRQ20_GPIO_0213_BITPOS (11) -// -#define GIRQ20_MASK (0x0F5Ful) -#define GIRQ20_WAKE_CAPABLE_MASK (0x0F5Ful) -// - -// GIRQ21 Bit Positions -#define GIRQ21_MASK (0x00ul) -#define GIRQ21_WAKE_CAPABLE_MASK (0x00ul) - -// GIRQ22 Bit Positions -#define GIRQ22_MASK (0x00ul) -#define GIRQ22_WAKE_CAPABLE_MASK (0x00ul) - -// GIRQ23 Bit Positions -#define GIRQ23_TMR0_BITPOS (0) -#define GIRQ23_TMR1_BITPOS (1) -#define GIRQ23_TMR2_BITPOS (2) -#define GIRQ23_TMR3_BITPOS (3) -#define GIRQ23_TMR4_BITPOS (4) -#define GIRQ23_TMR5_BITPOS (5) -// -#define GIRQ23_MASK (0x03Ful) -#define GIRQ23_WAKE_CAPABLE_MASK (0x000ul) -// - -/* ------------------------------------------------------------------------------- */ -/* NVIC,ECIA Routing Policy for Direct Mode */ -/* ------------------------------------------------------------------------------- */ -/* In Direct Mode, some interrupts could be configured to be used as aggregated. - * Configuration: - * 1. Always set ECS Interrupt Direct enable bit. - * 2. If GIRQn aggregated set Block Enable bit. - * 3. If GIRQn direct then clear Block Enable bit and enable individual NVIC inputs. - * Switching issues: - * Aggregate enable/disable requires set/clear single GIRQn bit in GIRQ Block En/Clr registers. - * Also requires set/clear of individual NVIC Enables. - * - * Note: interrupt_is_girq_direct() internal function uses this policy to detect - * if any interrupt is configured as direct or aggregated -*/ - -/** Initialize EC Interrupt Aggregator - * @param mode 1 - Direct Map mode, 0 - Fully Aggregated Mode - * @param girq_bitmask - BitMask of GIRQ to be configured as aggregated - * This parameter is only applicable in direct mode. - * @note All GPIO's and wake capable sources are always - * aggregated! GPIO's interrupts will still work in direct mode. - * Block wakes are not be routed to the processor in direct - * mode. - * Note2: This function disables and enables global interrupt - */ -void interrupt_init(uint8_t mode, uint32_t girq_bitmask); - -/** Set interrupt routing mode to aggregated or direct. - * @param mode 1 = Direct (except GPIO & wake), 0 = All Aggregated - * @note In direct mode, one could enable certain GIRQs as aggregated using - * p_interrupt_ecia_block_enable_set function - */ -void interrupt_mode_set(uint8_t mode); - -/** Clears all individual interrupts Enables and Source in ECIA, - * and Clears all NVIC external enables and pending bits - */ -void interrupt_reset(void); - -/** Enables interrupt for a device - * @param dev_iroute - source IROUTING information - * @note This function disables and enables global interrupt - */ -void interrupt_device_enable(uint32_t dev_iroute); - -/** Disables interrupt for a device - * @param dev_iroute - source IROUTING information - * @note This function disables and enables global interrupt - */ -void interrupt_device_disable(uint32_t dev_iroute); - -/* ------------------------------------------------------------------------------- */ -/* ECIA APIs using device IROUTE() as input */ -/* ------------------------------------------------------------------------------- */ - -/** Clear Source in the ECIA for the device - * @param devi - device IROUTING value - */ -void interrupt_device_ecia_source_clear(const uint32_t dev_iroute); - -/** Get the Source bit in the ECIA for the device - * @param devi - device IROUTING value - * @return 0 if source bit not set; else non-zero value - */ -uint32_t interrupt_device_ecia_source_get(const uint32_t dev_iroute); - -/** Get the Result bit in the ECIA for the device - * @param devi - device IROUTING value - * @return 0 if result bit not set; else non-zero value - */ -uint32_t interrupt_device_ecia_result_get(const uint32_t dev_iroute); - -/* ------------------------------------------------------------------------------- */ -/* NVIC APIs using device IROUTE() as input */ -/* ------------------------------------------------------------------------------- */ -/* Note that if the device interrupt is aggregated, then these APIs would affect the - * NVIC corresponding to the aggregated GIRQ - */ - -/** Enable/Disable the NVIC (in the NVIC controller) for the device - * @param dev_iroute : source IROUTING information (encoded in a uint32_t) - * @param en_flag : 1 = Enable the NVIC IRQ, 0 = Disable the NVIC IRQ - * @note Recommended to use interrupt_device_enable, interrupt_device_disable - * to enable/disable interrupts for the device, since those APIs configure ECIA as well - */ -void interrupt_device_nvic_enable(uint32_t dev_iroute, uint8_t en_flag); - -/** Set NVIC priority for specified peripheral interrupt source - * @param dev_iroute - source IROUTING information (encoded in a uint32_t) - * @param nvic_pri - NVIC Priority - * @note 1. If ECIA is in aggregated mode, the priority affects all interrupt - * sources in the GIRQ. - * 2. This function disables and enables global interrupt - */ -void interrupt_device_nvic_priority_set(const uint32_t dev_iroute, const uint8_t nvic_pri); - -/** Return NVIC priority for interrupt source - * @param dev_iroute - source IROUTING information - * @return uint32_t NVIC priority - */ -uint32_t interrupt_device_nvic_priority_get(const uint32_t dev_iroute); - -/** Return NVIC pending for interrupt source - * @param dev_iroute - source IROUTING information - * @return uint8_t 0(not pending), 1 (pending in NVIC) - * - */ -uint8_t interrupt_device_nvic_pending_get(const uint32_t dev_iroute); - -/** Set NVIC pending for interrupt source - * @param dev_iroute - source IROUTING information - */ -void interrupt_device_nvic_pending_set(const uint32_t dev_iroute); - -/** Clears NVIC pending for interrupt source - * @param dev_iroute - source IROUTING information - * @return uint8_t 0(not pending), 1 (pending in NVIC) - before clear - * @note This function disables and enables global interrupt - */ -uint8_t interrupt_device_nvic_pending_clear(const uint32_t dev_iroute); - -/* ------------------------------------------------------------------------------- */ -/* Peripheral Functions - Operations on GIRQ Block Enable Set, Enable Clear * - * and Status Register */ -/* ------------------------------------------------------------------------------- */ - -/** Enable specified GIRQ in ECIA block - * @param girq_id - enum MEC_GIRQ_IDS - */ - void p_interrupt_ecia_block_enable_set(uint8_t girq_id); - - /** Enable GIRQs in ECIA Block - * @param girq_bitmask - Bitmask of GIRQs to be enabled in ECIA Block - */ -void p_interrupt_ecia_block_enable_bitmask_set(uint32_t girq_bitmask); - -/** Check if specified GIRQ block enabled or not - * @param girq_id - enum MEC_GIRQ_IDS - * @return retVal - 1 if the particular GIRQ block enabled, else 0 - */ -uint8_t p_interrupt_ecia_block_enable_get(uint8_t girq_id); - -/** Set all GIRQ block enables */ -void p_interrupt_ecia_block_enable_all_set(void); - -/** Clear specified GIRQ in ECIA Block - * @param girq_id - enum MEC_GIRQ_IDS - */ -void p_interrupt_ecia_block_enable_clr(uint8_t girq_id); - -/** Clear GIRQs in ECIA Block - * @param girq_bitmask - Bitmask of GIRQs to be cleared in ECIA Block - */ -void p_interrupt_ecia_block_enable_bitmask_clr(uint32_t girq_bitmask); - -/** p_interrupt_ecia_block_enable_all_clr - Clears all GIRQ block enables */ -void p_interrupt_ecia_block_enable_all_clr(void); - - /** Get status of GIRQ in ECIA Block - * @param girq_id - enum MEC_GIRQ_IDS - * @return 0 if status bit not set; else non-zero value - */ -uint32_t p_interrupt_ecia_block_irq_status_get(uint8_t girq_id); - -/** Reads the Block IRQ Vector Register - * @return 32-bit value - */ -uint32_t p_interrupt_ecia_block_irq_all_status_get(void); - -/* ---------------------------------------------------------------------------- */ -/* Peripheral Functions - Operations on GIRQx Source, Enable, Result * - * and Enable Registers */ -/* ---------------------------------------------------------------------------- */ - -/** Clear specified interrupt source bit in GIRQx - * @param girq_id - enum MEC_GIRQ_IDS - * @param bitnum -[0, 31] - */ -void p_interrupt_ecia_girq_source_clr(int16_t girq_id, uint8_t bitnum); - -/** Read the specified interrupt source bit in GIRQx - * @param girq_id - enum MEC_GIRQ_IDS - * @param bitnum -[0, 31] - * @return 0 if source bit not set; else non-zero value - */ -uint32_t p_interrupt_ecia_girq_source_get(int16_t girq_id, uint8_t bitnum); - -/** Enable the specified interrupt in GIRQx - * girq_id - enum MEC_GIRQ_IDS - * bitnum = [0, 31] - */ -void p_interrupt_ecia_girq_enable_set(uint16_t girq_id, uint8_t bitnum); - -/** Disable the specified interrupt in GIRQx - * girq_id - enum MEC_GIRQ_IDS - * bitnum = [0, 31] - */ -void p_interrupt_ecia_girq_enable_clr(uint16_t girq_id, uint8_t bitnum); - -/** Read the status of the specified interrupt in GIRQx - * girq_id - enum MEC_GIRQ_IDS - * bitnum = [0, 31] - * @return 0 if enable bit not set; else non-zero value - */ -uint32_t p_interrupt_ecia_girq_enable_get(uint16_t girq_id, uint8_t bitnum); - -/** Read the result bit of the interrupt in GIRQx - * @param girq_id - enum MEC_GIRQ_IDS - * @param bitnum -[0, 31] - * @return 0 if enable bit not set; else non-zero value - */ -uint32_t p_interrupt_ecia_girq_result_get(int16_t girq_id, uint8_t bitnum); - -/* ------------------------------------------------------------------------------- */ -/* Peripheral Function - Operations on all GIRQs */ -/* ------------------------------------------------------------------------------- */ - -/** Clear all aggregator GIRQn status registers */ -void p_interrupt_ecia_girqs_source_reset(void); - -/** Clear all aggregator GIRQn enables */ - void p_interrupt_ecia_girqs_enable_reset(void); - -/* ------------------------------------------------------------------------------- */ -/* Peripheral Function - Function to set interrupt control */ -/* ------------------------------------------------------------------------------- */ - -/** Set interrupt control - * @param nvic_en_flag : 0 = Alternate NVIC disabled, 1 = Alternate NVIC enabled - */ - void p_interrupt_control_set(uint8_t nvic_en_flag); - - /** Read interrupt control - * @return uint8_t - 0 = Alternate NVIC disabled, 1 = Alternate NVIC enabled - */ -uint8_t p_interrupt_control_get(void); - -/* ------------------------------------------------------------------------------- */ -/* Peripheral Functions - NVIC */ -/* ------------------------------------------------------------------------------- */ - -/** Enable/Disable the NVIC IRQ in the NVIC interrupt controller - * @param nvic_num : NVIC number (see enum IRQn_Type) - * @param en_flag : 1 = Enable the NVIC IRQ, 0 = Disable the NVIC IRQ - * @note Application should perform this operation - */ - void p_interrupt_nvic_enable(IRQn_Type nvic_num, uint8_t en_flag); - - /** ecia_nvic_clr_en - Clear all NVIC external enables */ -void p_interrupt_nvic_extEnables_clr(void); - -/** Clear all NVIC external enables and pending bits */ -void p_interrupt_nvic_enpend_clr(void); - -/** Set NVIC external priorities to POR value */ -void p_interrupt_nvic_priorities_default_set(void); - -/** Set NVIC external priorities to specified priority (0 - 7) - * @param zero-based 3-bit priority value: 0=highest, 7=lowest. - * @note NVIC highest priority is the value 0, lowest is all 1's. - * Each external interrupt has an 8-bit register and the priority - * is left justified in the registers. MECxxx implements 8 priority - * levels or bits [7:5] in the register. Lowest priority = 0xE0 - */ -void p_interrupt_nvic_priorities_set(uint8_t new_pri); - -#endif /*_INTERRUPT_H_*/ - -/** @} - */ - - - diff --git a/FreeRTOS/Demo/CORTEX_M4F_CEC1302_Keil/peripheral_library/interrupt/interrupt.h~RF1de521e.TMP b/FreeRTOS/Demo/CORTEX_M4F_CEC1302_Keil/peripheral_library/interrupt/interrupt.h~RF1de521e.TMP deleted file mode 100644 index d9d00b929..000000000 --- a/FreeRTOS/Demo/CORTEX_M4F_CEC1302_Keil/peripheral_library/interrupt/interrupt.h~RF1de521e.TMP +++ /dev/null @@ -1,1177 +0,0 @@ -/**************************************************************************** -* © 2013 Microchip Technology Inc. and its subsidiaries. -* You may use this software and any derivatives exclusively with -* Microchip products. -* THIS SOFTWARE IS SUPPLIED BY MICROCHIP "AS IS". -* NO WARRANTIES, WHETHER EXPRESS, IMPLIED OR STATUTORY, APPLY TO THIS SOFTWARE, -* INCLUDING ANY IMPLIED WARRANTIES OF NON-INFRINGEMENT, MERCHANTABILITY, -* AND FITNESS FOR A PARTICULAR PURPOSE, OR ITS INTERACTION WITH MICROCHIP -* PRODUCTS, COMBINATION WITH ANY OTHER PRODUCTS, OR USE IN ANY APPLICATION. -* IN NO EVENT WILL MICROCHIP BE LIABLE FOR ANY INDIRECT, SPECIAL, PUNITIVE, -* INCIDENTAL OR CONSEQUENTIAL LOSS, DAMAGE, COST OR EXPENSE OF ANY KIND -* WHATSOEVER RELATED TO THE SOFTWARE, HOWEVER CAUSED, EVEN IF MICROCHIP HAS -* BEEN ADVISED OF THE POSSIBILITY OR THE DAMAGES ARE FORESEEABLE. -* TO THE FULLEST EXTENT ALLOWED BY LAW, MICROCHIP'S TOTAL LIABILITY ON ALL -* CLAIMS IN ANY WAY RELATED TO THIS SOFTWARE WILL NOT EXCEED THE AMOUNT OF -* FEES, IF ANY, THAT YOU HAVE PAID DIRECTLY TO MICROCHIP FOR THIS SOFTWARE. -* MICROCHIP PROVIDES THIS SOFTWARE CONDITIONALLY UPON YOUR ACCEPTANCE -* OF THESE TERMS. -*/ - -/** @defgroup interrupt interrupt - * @{ - */ -/** @file interrupt.h - \brief This is the header file for interrupt.c - This program is designed to allow the other C programs to be able to use this component - - There are entry points for all C wrapper API implementation - -Platform: This is ARC-based component - -Toolset: Metaware IDE(8.5.1) -Reference: smsc_reusable_fw_requirement.doc */ - -/******************************************************************************* - * SMSC version control information (Perforce): - * - * FILE: $File: //depot_pcs/FWEng/Release/projects/CEC1302_CLIB/release2/Source/hw_blks/kernel/skern/source/interrupt/interrupt.h $ - * REVISION: $Revision: #1 $ - * DATETIME: $DateTime: 2015/12/23 15:37:58 $ - * AUTHOR: $Author: akrishnan $ - * - * Revision history (latest first): - * #xx - *********************************************************************************** - */ - -#ifndef _INTERRUPT_H_ -#define _INTERRUPT_H_ - - -/* public function prototypes */ -void interrupt_block_init(void); -void null_handler(void); -__irq void SysTick_Handler(void); - -/* macro for interrupt control */ -/* 16-bit timers interrupt control */ -#define sbit_TIMER0 b_bit0 -#define sbit_TIMER1 b_bit1 -#define sbit_TIMER2 b_bit2 -#define sbit_TIMER3 b_bit3 - -#define disable_timer0_irq() mCLR_BIT(sbit_TIMER0, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_timer0_irq() mSET_BIT(sbit_TIMER0, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_timer0_source() mCLR_SRC_BIT(sbit_TIMER0, MMCR_EC_GIRQ23_SOURCE) -#define get_timer0_source() mGET_BIT(sbit_TIMER0, MMCR_EC_GIRQ23_SOURCE) - -#define disable_timer1_irq() mCLR_BIT(sbit_TIMER1, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_timer1_irq() mSET_BIT(sbit_TIMER1, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_timer1_source() mCLR_SRC_BIT(sbit_TIMER1, MMCR_EC_GIRQ23_SOURCE) -#define get_timer1_source() mGET_BIT(sbit_TIMER1, MMCR_EC_GIRQ23_SOURCE) - -#define disable_timer2_irq() mCLR_BIT(sbit_TIMER2, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_timer2_irq() mSET_BIT(sbit_TIMER2, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_timer2_source() mCLR_SRC_BIT(sbit_TIMER2, MMCR_EC_GIRQ23_SOURCE) -#define get_timer2_source() mGET_BIT(sbit_TIMER2, MMCR_EC_GIRQ23_SOURCE) - -#define disable_timer3_irq() mCLR_BIT(sbit_TIMER3, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_timer3_irq() mSET_BIT(sbit_TIMER3, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_timer3_source() mCLR_SRC_BIT(sbit_TIMER3, MMCR_EC_GIRQ23_SOURCE) -#define get_timer3_source() mGET_BIT(sbit_TIMER3, MMCR_EC_GIRQ23_SOURCE) - - -/* hibernation timers interrupt control */ -#define sbit_HTIMER0 b_bit20 -#define sbit_HTIMER1 b_bit14 - -#define disable_htimer0_irq() mCLR_BIT(sbit_HTIMER0, MMCR_EC_GIRQ17_ENABLE_SET) -#define enable_htimer0_irq() mSET_BIT(sbit_HTIMER0, MMCR_EC_GIRQ17_ENABLE_SET) -#define clear_htimer0_source() mCLR_SRC_BIT(sbit_HTIMER0, MMCR_EC_GIRQ17_SOURCE) -#define get_htimer0_source() mGET_BIT(sbit_HTIMER0, MMCR_EC_GIRQ17_SOURCE) - -#define disable_htimer1_irq() mCLR_BIT(sbit_HTIMER1, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_htimer1_irq() mSET_BIT(sbit_HTIMER1, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_htimer1_source() mCLR_SRC_BIT(sbit_HTIMER1, MMCR_EC_GIRQ23_SOURCE) -#define get_htimer1_source() mGET_BIT(sbit_HTIMER1, MMCR_EC_GIRQ23_SOURCE) - -/* RTC interrupt control */ -#define b_bit18 (1 << 18) -#define b_bit19 (1 << 19) -#define sbit_RTC_INT b_bit18 -#define disable_rtc_irq() mCLR_BIT(sbit_RTC_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define enable_rtc_irq() mSET_BIT(sbit_RTC_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define clear_rtc_irq_source() mCLR_SRC_BIT(sbit_RTC_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define get_rtc_irq_source() mGET_BIT(sbit_RTC_INT, MMCR_EC_GIRQ17_ENABLE_SET) -/* RTC alarm interrupt control */ -#define sbit_RTC_ALM_INT b_bit19 -#define disable_rtc_alm_irq() mCLR_BIT(sbit_RTC_ALM_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define enable_rtc_alm_irq() mSET_BIT(sbit_RTC_ALM_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define clear_rtc_irq_alm_source() mCLR_SRC_BIT(sbit_RTC_ALM_INT, MMCR_EC_GIRQ17_ENABLE_SET) -#define get_rtc_irq_alm_source() mGET_BIT(sbit_RTC_ALM_INT, MMCR_EC_GIRQ17_ENABLE_SET) - -/* week timer interrupt control */ -#define sbit_WKTIMER b_bit7 - -#define disable_wktimer_irq() mCLR_BIT(sbit_WKTIMER, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_wktimer_irq() mSET_BIT(sbit_WKTIMER, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_wktimer_source() mCLR_SRC_BIT(sbit_WKTIMER, MMCR_EC_GIRQ23_SOURCE) -#define get_wktimer_source() mGET_BIT(sbit_WKTIMER, MMCR_EC_GIRQ23_SOURCE) - - -/* scan matrix interrupt control */ -#define sbit_SCANNER b_bit16 -#define disable_scanner_irq() mCLR_BIT(sbit_SCANNER, MMCR_EC_GIRQ18_ENABLE_SET) -#define enable_scanner_irq() mSET_BIT(sbit_SCANNER, MMCR_EC_GIRQ18_ENABLE_SET) -#define clear_scanner_source() mCLR_SRC_BIT(sbit_SCANNER, MMCR_EC_GIRQ18_SOURCE) -#define get_scanner_source() mGET_BIT(sbit_SCANNER, MMCR_EC_GIRQ18_SOURCE) - - -/* PS2 interrupt control */ -/* PS2 activity interrupt */ -#define sbit_PS2_ACT_0 b_bit13 -#define sbit_PS2_ACT_1 b_bit14 -#define sbit_PS2_ACT_2 b_bit15 -/* PS2 wakeup interrupt: detect start bit */ -#define sbit_PS2_WK_0A b_bit17 -#define sbit_PS2_WK_1B b_bit20 -#define sbit_PS2_WK_2 b_bit21 - -/* PS2 activity interrupt control */ -#define disable_ps2_act_0_irq() mCLR_BIT(sbit_PS2_ACT_0, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_act_0_irq() mSET_BIT(sbit_PS2_ACT_0, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_act_0_source() mCLR_SRC_BIT(sbit_PS2_ACT_0, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_act_0_source() mGET_BIT(sbit_PS2_ACT_0, MMCR_EC_GIRQ19_SOURCE) - -#define disable_ps2_act_1_irq() mCLR_BIT(sbit_PS2_ACT_1, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_act_1_irq() mSET_BIT(sbit_PS2_ACT_1, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_act_1_source() mCLR_SRC_BIT(sbit_PS2_ACT_1, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_act_1_source() mGET_BIT(sbit_PS2_ACT_1, MMCR_EC_GIRQ19_SOURCE) - -#define disable_ps2_act_2_irq() mCLR_BIT(sbit_PS2_ACT_2, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_act_2_irq() mSET_BIT(sbit_PS2_ACT_2, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_act_2_source() mCLR_SRC_BIT(sbit_PS2_ACT_2, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_act_2_source() mGET_BIT(sbit_PS2_ACT_2, MMCR_EC_GIRQ19_SOURCE) - -/* PS2 wakeup interrupt control */ -#define disable_ps2_wk_0_irq() mCLR_BIT(sbit_PS2_WK_0A, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_wk_0_irq() mSET_BIT(sbit_PS2_WK_0A, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_wk_0_source() mCLR_SRC_BIT(sbit_PS2_WK_0A, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_wk_0_source() mGET_BIT(sbit_PS2_WK_0A, MMCR_EC_GIRQ19_SOURCE) - -#define disable_ps2_wk_1_irq() mCLR_BIT(sbit_PS2_WK_1B, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_wk_1_irq() mSET_BIT(sbit_PS2_WK_1B, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_wk_1_source() mCLR_SRC_BIT(sbit_PS2_WK_1B, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_wk_1_source() mGET_BIT(sbit_PS2_WK_1B, MMCR_EC_GIRQ19_SOURCE) - -#define disable_ps2_wk_2_irq() mCLR_BIT(sbit_PS2_WK_2, MMCR_EC_GIRQ19_ENABLE_SET) -#define enable_ps2_wk_2_irq() mSET_BIT(sbit_PS2_WK_2, MMCR_EC_GIRQ19_ENABLE_SET) -#define clear_ps2_wk_2_source() mCLR_SRC_BIT(sbit_PS2_WK_2, MMCR_EC_GIRQ19_SOURCE) -#define get_ps2_wk_2_source() mGET_BIT(sbit_PS2_WK_2, MMCR_EC_GIRQ19_SOURCE) - - -/* ICT interrupt control */ -/* capture 0~5 interrupt */ -#define sbit_ICT_CAPTURE0 b_bit17 -#define sbit_ICT_CAPTURE1 b_bit18 -#define sbit_ICT_CAPTURE2 b_bit19 -#define sbit_ICT_CAPTURE3 b_bit20 -#define sbit_ICT_CAPTURE4 b_bit21 -#define sbit_ICT_CAPTURE5 b_bit22 - -/* capture 0 interrupt control */ -#define disable_capture0_irq() mCLR_BIT(sbit_ICT_CAPTURE0, MMCR_EC_GIRQ23_ENABLE_SET) -#define enable_capture0_irq() mSET_BIT(sbit_ICT_CAPTURE0, MMCR_EC_GIRQ23_ENABLE_SET) -#define clear_capture0_source() mCLR_SRC_BIT(sbit_ICT_CAPTURE0, MMCR_EC_GIRQ23_SOURCE) -#define get_capture0_source() mGET_BIT(sbit_ICT_CAPTURE0, MMCR_EC_GIRQ23_SOURCE) - - -/* SMBus interrupt control */ - - -/* GPIO interrupt control */ - - -/* BC link interrupt control */ -/* bclink A~D interrupt */ -#define sbit_BCLINK_A_BUSY b_bit0 -#define sbit_BCLINK_A_ERR b_bit1 -#define sbit_BCLINK_A_INT b_bit2 -#define sbit_BCLINK_B_BUSY b_bit3 -#define sbit_BCLINK_B_ERR b_bit4 -#define sbit_BCLINK_B_INT b_bit5 -#define sbit_BCLINK_C_BUSY b_bit6 -#define sbit_BCLINK_C_ERR b_bit7 -#define sbit_BCLINK_C_INT b_bit8 -#define sbit_BCLINK_D_BUSY b_bit9 -#define sbit_BCLINK_D_ERR b_bit10 -#define sbit_BCLINK_D_INT b_bit11 - -/* bclink B interrupt control */ -#define disable_bclink_b_busy_irq() mCLR_BIT(sbit_BCLINK_B_BUSY, MMCR_EC_GIRQ18_ENABLE_SET) -#define enable_bclink_b_busy_irq() mSET_BIT(sbit_BCLINK_B_BUSY, MMCR_EC_GIRQ18_ENABLE_SET) -#define clear_bclink_b_busy_source() mCLR_SRC_BIT(sbit_BCLINK_B_BUSY, MMCR_EC_GIRQ18_SOURCE) -#define get_bclink_b_busy_source() mGET_BIT(sbit_BCLINK_B_BUSY, MMCR_EC_GIRQ18_SOURCE) - -#define disable_bclink_b_err_irq() mCLR_BIT(sbit_BCLINK_B_ERR, MMCR_EC_GIRQ18_ENABLE_SET) -#define enable_bclink_b_err_irq() mSET_BIT(sbit_BCLINK_B_ERR, MMCR_EC_GIRQ18_ENABLE_SET) -#define clear_bclink_b_err_source() mCLR_SRC_BIT(sbit_BCLINK_B_ERR, MMCR_EC_GIRQ18_SOURCE) -#define get_bclink_b_err_source() mGET_BIT(sbit_BCLINK_B_ERR, MMCR_EC_GIRQ18_SOURCE) - -#define disable_bclink_b_int_irq() mCLR_BIT(sbit_BCLINK_B_INT, MMCR_EC_GIRQ18_ENABLE_SET) -#define enable_bclink_b_int_irq() mSET_BIT(sbit_BCLINK_B_INT, MMCR_EC_GIRQ18_ENABLE_SET) -#define clear_bclink_b_int_source() mCLR_SRC_BIT(sbit_BCLINK_B_INT, MMCR_EC_GIRQ18_SOURCE) -#define get_bclink_b_int_source() mGET_BIT(sbit_BCLINK_B_INT, MMCR_EC_GIRQ18_SOURCE) - -/* UART interrupt control */ -#define sbit_UART_INT b_bit0 - -#define disable_uart_irq() mCLR_BIT(sbit_UART_INT, MMCR_EC_GIRQ15_ENABLE_SET) -#define enable_uart_irq() mSET_BIT(sbit_UART_INT, MMCR_EC_GIRQ15_ENABLE_SET) -#define clear_uart_irq_source() mCLR_SRC_BIT(sbit_UART_INT, MMCR_EC_GIRQ15_SOURCE) -#define get_uart_irq_source() mGET_BIT(sbit_UART_INT, MMCR_EC_GIRQ15_SOURCE) - -// GIRQ IDs for EC Interrupt Aggregator -enum MEC_GIRQ_IDS -{ - MEC_GIRQ08_ID = 0, - MEC_GIRQ09_ID, - MEC_GIRQ10_ID, - MEC_GIRQ11_ID, - MEC_GIRQ12_ID, - MEC_GIRQ13_ID, - MEC_GIRQ14_ID, - MEC_GIRQ15_ID, - MEC_GIRQ16_ID, - MEC_GIRQ17_ID, - MEC_GIRQ18_ID, - MEC_GIRQ19_ID, - MEC_GIRQ20_ID, - MEC_GIRQ21_ID, - MEC_GIRQ22_ID, - MEC_GIRQ23_ID, - MEC_GIRQ_ID_MAX -}; - -//Bitmask of GIRQ in ECIA Block Registers -#define MEC_GIRQ08_BITMASK (1UL << (MEC_GIRQ08_ID + 8)) -#define MEC_GIRQ09_BITMASK (1UL << (MEC_GIRQ09_ID + 8)) -#define MEC_GIRQ10_BITMASK (1UL << (MEC_GIRQ10_ID + 8)) -#define MEC_GIRQ11_BITMASK (1UL << (MEC_GIRQ11_ID + 8)) -#define MEC_GIRQ12_BITMASK (1UL << (MEC_GIRQ12_ID + 8)) -#define MEC_GIRQ13_BITMASK (1UL << (MEC_GIRQ13_ID + 8)) -#define MEC_GIRQ14_BITMASK (1UL << (MEC_GIRQ14_ID + 8)) -#define MEC_GIRQ15_BITMASK (1UL << (MEC_GIRQ15_ID + 8)) -#define MEC_GIRQ16_BITMASK (1UL << (MEC_GIRQ16_ID + 8)) -#define MEC_GIRQ17_BITMASK (1UL << (MEC_GIRQ17_ID + 8)) -#define MEC_GIRQ18_BITMASK (1UL << (MEC_GIRQ18_ID + 8)) -#define MEC_GIRQ19_BITMASK (1UL << (MEC_GIRQ19_ID + 8)) -#define MEC_GIRQ20_BITMASK (1UL << (MEC_GIRQ20_ID + 8)) -#define MEC_GIRQ21_BITMASK (1UL << (MEC_GIRQ21_ID + 8)) -#define MEC_GIRQ22_BITMASK (1UL << (MEC_GIRQ22_ID + 8)) -#define MEC_GIRQ23_BITMASK (1UL << (MEC_GIRQ23_ID + 8)) - -#define INTERRUPT_MODE_ALL_AGGREGATED (0u) -#define INTERRUPT_MODE_DIRECT (1u) - -// Bit map of GIRQs whose sources can be directly connected to the NVIC -// GIRQs 12 - 18, 23 -#define ECIA_GIRQ_DIRECT_BITMAP (0x0087F000ul) - -/* - * n = b[7:0] = zero-based direct mapped NVIC ID - * m = b[15:8] = zero-based aggregated NVIC ID - * a = b[23:16] = block Aggregator register block ID - * b = b[31:24] = block bit position in Aggregator registers -*/ -#define IROUTE(b,a,m,n) (((uint32_t)(n)&0xFFul) + \ - (((uint32_t)(m)&0xFFul)<<8u) + \ - ((((uint32_t)(a)-8ul)&0x0F)<<16u) + \ - (((uint32_t)(b)&0x1Ful)<<24)) - -#define ECIA_NVIC_ID_BITPOS (0u) -#define ECIA_IA_NVIC_ID_BITPOS (8u) -#define ECIA_GIRQ_ID_BITPOS (16u) -#define ECIA_GIRQ_BIT_BITPOS (24u) - -// -// GIRQ08 -// -#define GPIO_0140_IROUTE IROUTE(0,8,57,57) -#define GPIO_0141_IROUTE IROUTE(1,8,57,57) -#define GPIO_0142_IROUTE IROUTE(2,8,57,57) -#define GPIO_0143_IROUTE IROUTE(3,8,57,57) -#define GPIO_0144_IROUTE IROUTE(4,8,57,57) -#define GPIO_0145_IROUTE IROUTE(5,8,57,57) -#define GPIO_0147_IROUTE IROUTE(7,8,57,57) -// -#define GPIO_0150_IROUTE IROUTE(8,8,57,57) -#define GPIO_0151_IROUTE IROUTE(9,8,57,57) -#define GPIO_0152_IROUTE IROUTE(10,8,57,57) -#define GPIO_0153_IROUTE IROUTE(11,8,57,57) -#define GPIO_0154_IROUTE IROUTE(12,8,57,57) -#define GPIO_0155_IROUTE IROUTE(13,8,57,57) -#define GPIO_0156_IROUTE IROUTE(14,8,57,57) -#define GPIO_0157_IROUTE IROUTE(15,8,57,57) -// -#define GPIO_0160_IROUTE IROUTE(16,8,57,57) -#define GPIO_0161_IROUTE IROUTE(17,8,57,57) -#define GPIO_0162_IROUTE IROUTE(18,8,57,57) -#define GPIO_0163_IROUTE IROUTE(19,8,57,57) -#define GPIO_0164_IROUTE IROUTE(20,8,57,57) -#define GPIO_0165_IROUTE IROUTE(21,8,57,57) -#define GPIO_0166_IROUTE IROUTE(22,8,57,57) -#define GPIO_0167_IROUTE IROUTE(23,8,57,57) - -// -// GIRQ09 -// -#define GPIO_0100_IROUTE IROUTE(0,9,58,58) -#define GPIO_0101_IROUTE IROUTE(1,9,58,58) -#define GPIO_0102_IROUTE IROUTE(2,9,58,58) -#define GPIO_0103_IROUTE IROUTE(3,9,58,58) -#define GPIO_0104_IROUTE IROUTE(4,9,58,58) -#define GPIO_0105_IROUTE IROUTE(5,9,58,58) -#define GPIO_0105_IROUTE IROUTE(5,9,58,58) -#define GPIO_0107_IROUTE IROUTE(7,9,58,58) -// -#define GPIO_0110_IROUTE IROUTE(8,9,58,58) -#define GPIO_0111_IROUTE IROUTE(9,9,58,58) -#define GPIO_0112_IROUTE IROUTE(10,9,58,58) -#define GPIO_0113_IROUTE IROUTE(11,9,58,58) -#define GPIO_0114_IROUTE IROUTE(12,9,58,58) -#define GPIO_0115_IROUTE IROUTE(13,9,58,58) -#define GPIO_0116_IROUTE IROUTE(14,9,58,58) -#define GPIO_0117_IROUTE IROUTE(15,9,58,58) -// -#define GPIO_0120_IROUTE IROUTE(16,9,58,58) -#define GPIO_0121_IROUTE IROUTE(17,9,58,58) -#define GPIO_0122_IROUTE IROUTE(18,9,58,58) -#define GPIO_0124_IROUTE IROUTE(20,9,58,58) -#define GPIO_0125_IROUTE IROUTE(21,9,58,58) -#define GPIO_0126_IROUTE IROUTE(22,9,58,58) -#define GPIO_0127_IROUTE IROUTE(23,9,58,58) -// -#define GPIO_0130_IROUTE IROUTE(24,9,58,58) -#define GPIO_0131_IROUTE IROUTE(25,9,58,58) -#define GPIO_0132_IROUTE IROUTE(26,9,58,58) -#define GPIO_0133_IROUTE IROUTE(27,9,58,58) -#define GPIO_0134_IROUTE IROUTE(28,9,58,58) -#define GPIO_0135_IROUTE IROUTE(29,9,58,58) -#define GPIO_0136_IROUTE IROUTE(30,9,58,58) - -// -// GIRQ10 -// -#define GPIO_0040_IROUTE IROUTE(0,10,59,59) -#define GPIO_0041_IROUTE IROUTE(1,10,59,59) -#define GPIO_0042_IROUTE IROUTE(2,10,59,59) -#define GPIO_0043_IROUTE IROUTE(3,10,59,59) -#define GPIO_0044_IROUTE IROUTE(4,10,59,59) -#define GPIO_0045_IROUTE IROUTE(5,10,59,59) -#define GPIO_0045_IROUTE IROUTE(5,10,59,59) -#define GPIO_0047_IROUTE IROUTE(7,10,59,59) -// -#define GPIO_0050_IROUTE IROUTE(8,10,59,59) -#define GPIO_0051_IROUTE IROUTE(9,10,59,59) -#define GPIO_0052_IROUTE IROUTE(10,10,59,59) -#define GPIO_0053_IROUTE IROUTE(11,10,59,59) -#define GPIO_0054_IROUTE IROUTE(12,10,59,59) -#define GPIO_0055_IROUTE IROUTE(13,10,59,59) -#define GPIO_0056_IROUTE IROUTE(14,10,59,59) -#define GPIO_0057_IROUTE IROUTE(15,10,59,59) -// -#define GPIO_0060_IROUTE IROUTE(16,10,59,59) -#define GPIO_0061_IROUTE IROUTE(17,10,59,59) -#define GPIO_0062_IROUTE IROUTE(18,10,59,59) -#define GPIO_0063_IROUTE IROUTE(19,10,59,59) -#define GPIO_0064_IROUTE IROUTE(20,10,59,59) -#define GPIO_0065_IROUTE IROUTE(21,10,59,59) -#define GPIO_0066_IROUTE IROUTE(22,10,59,59) -#define GPIO_0067_IROUTE IROUTE(23,10,59,59) -// -#define GPIO_0070_IROUTE IROUTE(24,10,59,59) -#define GPIO_0071_IROUTE IROUTE(25,10,59,59) -#define GPIO_0072_IROUTE IROUTE(26,10,59,59) -#define GPIO_0073_IROUTE IROUTE(27,10,59,59) -#define GPIO_0074_IROUTE IROUTE(28,10,59,59) -#define GPIO_0075_IROUTE IROUTE(29,10,59,59) -#define GPIO_0076_IROUTE IROUTE(30,10,59,59) - -// -// GIRQ11 -// -#define GPIO_0000_IROUTE IROUTE(0,11,60,60) -#define GPIO_0001_IROUTE IROUTE(1,11,60,60) -#define GPIO_0002_IROUTE IROUTE(2,11,60,60) -#define GPIO_0003_IROUTE IROUTE(3,11,60,60) -#define GPIO_0004_IROUTE IROUTE(4,11,60,60) -#define GPIO_0005_IROUTE IROUTE(5,11,60,60) -#define GPIO_0006_IROUTE IROUTE(6,11,60,60) -#define GPIO_0007_IROUTE IROUTE(7,11,60,60) -// -#define GPIO_0010_IROUTE IROUTE(8,11,60,60) -#define GPIO_0011_IROUTE IROUTE(9,11,60,60) -#define GPIO_0012_IROUTE IROUTE(10,11,60,60) -#define GPIO_0013_IROUTE IROUTE(11,11,60,60) -#define GPIO_0014_IROUTE IROUTE(12,11,60,60) -#define GPIO_0015_IROUTE IROUTE(13,11,60,60) -#define GPIO_0016_IROUTE IROUTE(14,11,60,60) -#define GPIO_0017_IROUTE IROUTE(15,11,60,60) -// -#define GPIO_0020_IROUTE IROUTE(16,11,60,60) -#define GPIO_0021_IROUTE IROUTE(17,11,60,60) -#define GPIO_0022_IROUTE IROUTE(18,11,60,60) -#define GPIO_0023_IROUTE IROUTE(19,11,60,60) -#define GPIO_0024_IROUTE IROUTE(20,11,60,60) -#define GPIO_0025_IROUTE IROUTE(21,11,60,60) -#define GPIO_0026_IROUTE IROUTE(22,11,60,60) -#define GPIO_0027_IROUTE IROUTE(23,11,60,60) -// -#define GPIO_0030_IROUTE IROUTE(24,11,60,60) -#define GPIO_0031_IROUTE IROUTE(25,11,60,60) -#define GPIO_0032_IROUTE IROUTE(26,11,60,60) -#define GPIO_0033_IROUTE IROUTE(27,11,60,60) -#define GPIO_0034_IROUTE IROUTE(28,11,60,60) -#define GPIO_0035_IROUTE IROUTE(29,11,60,60) -#define GPIO_0036_IROUTE IROUTE(30,11,60,60) - -// -// GIRQ12 -// -#define SMB0_IROUTE IROUTE(0,12,61,0) -#define SMB1_IROUTE IROUTE(1,12,61,1) -#define SMB2_IROUTE IROUTE(2,12,61,2) -#define SMB3_IROUTE IROUTE(3,12,61,3) -// SMB wakes have no direct connection to NVIC, always aggregated -#define SMB0_WAKE_IROUTE IROUTE(4,12,61,61) -#define SMB1_WAKE_IROUTE IROUTE(5,12,61,61) -#define SMB2_WAKE_IROUTE IROUTE(6,12,61,61) -#define SMB3_WAKE_IROUTE IROUTE(7,12,61,61) -#define SMB4_WAKE_IROUTE IROUTE(8,12,61,61) - -// -// GIRQ13 -// -#define DMA0_IROUTE IROUTE(16,13,62,4) -#define DMA1_IROUTE IROUTE(17,13,62,5) -#define DMA2_IROUTE IROUTE(18,13,62,6) -#define DMA3_IROUTE IROUTE(19,13,62,7) -#define DMA4_IROUTE IROUTE(20,13,62,8) -#define DMA5_IROUTE IROUTE(21,13,62,9) -#define DMA6_IROUTE IROUTE(22,13,62,10) -#define DMA7_IROUTE IROUTE(23,13,62,11) -#define DMA8_IROUTE IROUTE(24,13,62,81) -#define DMA9_IROUTE IROUTE(25,13,62,82) -#define DMA10_IROUTE IROUTE(26,13,62,83) -#define DMA11_IROUTE IROUTE(27,13,62,84) - -// -// GIRQ14 -// -#define LPC_BERR_IROUTE IROUTE(2,14,63,12) - -// -// GIRQ15 -// -#define UART0_IROUTE IROUTE(0,15,64,13) -#define EMI0_IROUTE IROUTE(2,15,64,14) -#define ACPI_EC0_IBF_IROUTE IROUTE(6,15,64,15) -#define ACPI_EC0_OBF_IROUTE IROUTE(7,15,64,16) -#define ACPI_EC1_IBF_IROUTE IROUTE(8,15,64,17) -#define ACPI_EC1_OBF_IROUTE IROUTE(9,15,64,18) -#define ACPI_PM1_CTL_IROUTE IROUTE(10,15,64,19) -#define ACPI_PM1_EN_IROUTE IROUTE(11,15,64,20) -#define ACPI_PM1_STS_IROUTE IROUTE(12,15,64,21) -#define EM8042_OBF_IROUTE IROUTE(13,15,64,22) -#define EM8042_IBF_IROUTE IROUTE(14,15,64,23) -#define MBOX_IROUTE IROUTE(15,15,64,24) -#define MBOX_DATA_IROUTE IROUTE(16,15,64,40) - -// -// GIRQ16 -// -#define PECI_IROUTE IROUTE(3,16,65,25) - -// -// GIRQ17 -// -#define TACH0_IROUTE IROUTE(0,17,66,26) -#define TACH1_IROUTE IROUTE(1,17,66,27) -#define PS2_0_WAKE_IROUTE IROUTE(2,17,66,66) -#define PS2_1_WAKE_IROUTE IROUTE(3,17,66,66) -#define PS2_2_WAKE_IROUTE IROUTE(4,17,66,66) -#define PS2_3_WAKE_IROUTE IROUTE(5,17,66,66) -#define BC_WAKE_IROUTE IROUTE(6,17,66,66) -#define ADC_SNGL_IROUTE IROUTE(10,17,66,28) -#define ADC_RPT_IROUTE IROUTE(11,17,66,29) -#define ADC2PWM1_IROUTE IROUTE(12,17,66,30) -#define ADC2PWM2_IROUTE IROUTE(13,17,66,31) -#define PS2_0_IROUTE IROUTE(14,17,66,32) -#define PS2_1_IROUTE IROUTE(15,17,66,33) -#define PS2_2_IROUTE IROUTE(16,17,66,34) -#define PS2_3_IROUTE IROUTE(17,17,66,35) -#define RTC_IROUTE IROUTE(18,17,66,91) -#define RTC_ALARM_IROUTE IROUTE(19,17,66,92) -#define HTIMER_IROUTE IROUTE(20,17,66,38) -#define KSC_IROUTE IROUTE(21,17,66,39) -#define KSC_WAKE_IROUTE IROUTE(22,17,66,66) -#define RPM_STALL_IROUTE IROUTE(23,17,66,41) -#define RPM_SPIN_IROUTE IROUTE(24,17,66,42) -#define PFR_IROUTE IROUTE(25,17,66,43) -#define LED0_IROUTE IROUTE(26,17,66,44) -#define LED1_IROUTE IROUTE(27,17,66,45) -#define LED2_IROUTE IROUTE(28,17,66,46) -#define BCM_ERR_IROUTE IROUTE(29,17,66,47) -#define BCM_BUSY_IROUTE IROUTE(30,17,66,48) - -// -// GIRQ18 -// -#define SPI0_TX_IROUTE IROUTE(0,18,67,36) -#define SPI0_RX_IROUTE IROUTE(1,18,67,37) -#define SPI1_TX_IROUTE IROUTE(2,18,67,55) -#define SPI1_RX_IROUTE IROUTE(3,18,67,56) -#define LED3_IROUTE IROUTE(4,18,67,85) -#define PKE_ERR_IROUTE IROUTE(5,18,67,86) -#define PKE_END_IROUTE IROUTE(6,18,67,87) -#define NDRNG_IROUTE IROUTE(7,18,67,88) -#define AES_IROUTE IROUTE(8,18,67,89) -#define HASH_IROUTE IROUTE(9,18,67,90) - -// -// GIRQ19, Aggregated only -// -#define LRESET_IROUTE IROUTE(0,19,68,68) -#define VCC_PWRGD_IROUTE IROUTE(1,19,68,68) - -// -// GIRQ20, Aggregated only -// -#define GPIO_0200_IROUTE IROUTE(0,20,69,69) -#define GPIO_0201_IROUTE IROUTE(1,20,69,69) -#define GPIO_0202_IROUTE IROUTE(2,20,69,69) -#define GPIO_0203_IROUTE IROUTE(3,20,69,69) -#define GPIO_0204_IROUTE IROUTE(4,20,69,69) -#define GPIO_0206_IROUTE IROUTE(6,20,69,69) -// -#define GPIO_0210_IROUTE IROUTE(8,20,69,69) -#define GPIO_0211_IROUTE IROUTE(9,20,69,69) -#define GPIO_0212_IROUTE IROUTE(10,20,69,69) -#define GPIO_0213_IROUTE IROUTE(11,20,69,69) - -// -// GIRQ21 -// -// No sources - -// -// GIRQ22 -// -// No sources - -// -// GIRQ23 -// -#define BTMR0_IROUTE IROUTE(0,23,72,49) -#define BTMR1_IROUTE IROUTE(1,23,72,50) -#define BTMR2_IROUTE IROUTE(2,23,72,51) -#define BTMR3_IROUTE IROUTE(3,23,72,52) -#define BTMR4_IROUTE IROUTE(4,23,72,53) -#define BTMR5_IROUTE IROUTE(5,23,72,54) - -// GIRQ08 Bit Positions -#define GIRQ08_GPIO_0140_BITPOS (0) -#define GIRQ08_GPIO_0141_BITPOS (1) -#define GIRQ08_GPIO_0142_BITPOS (2) -#define GIRQ08_GPIO_0143_BITPOS (3) -#define GIRQ08_GPIO_0144_BITPOS (4) -#define GIRQ08_GPIO_0145_BITPOS (5) -//#define GIRQ08_GPIO_0146_BITPOS (6) RESERVED -#define GIRQ08_GPIO_0147_BITPOS (7) -// -#define GIRQ08_GPIO_0150_BITPOS (8) -#define GIRQ08_GPIO_0151_BITPOS (9) -#define GIRQ08_GPIO_0152_BITPOS (10) -#define GIRQ08_GPIO_0153_BITPOS (11) -#define GIRQ08_GPIO_0154_BITPOS (12) -#define GIRQ08_GPIO_0155_BITPOS (13) -#define GIRQ08_GPIO_0156_BITPOS (14) -#define GIRQ08_GPIO_0157_BITPOS (15) -// -#define GIRQ08_GPIO_0160_BITPOS (16) -#define GIRQ08_GPIO_0161_BITPOS (17) -#define GIRQ08_GPIO_0162_BITPOS (18) -#define GIRQ08_GPIO_0163_BITPOS (19) -#define GIRQ08_GPIO_0164_BITPOS (20) -#define GIRQ08_GPIO_0165_BITPOS (21) -#define GIRQ08_GPIO_0166_BITPOS (22) -#define GIRQ08_GPIO_0167_BITPOS (23) -// -#define GIRQ08_MASK (0x00FFFFBFul) -#define GIRQ08_WAKE_CAPABLE_MASK (0x00FFFFBFul) -// - -// GIRQ09 Bit Positions -#define GIRQ09_GPIO_0100_BITPOS (0) -#define GIRQ09_GPIO_0101_BITPOS (1) -#define GIRQ09_GPIO_0102_BITPOS (2) -#define GIRQ09_GPIO_0103_BITPOS (3) -#define GIRQ09_GPIO_0104_BITPOS (4) -#define GIRQ09_GPIO_0105_BITPOS (5) -#define GIRQ09_GPIO_0106_BITPOS (6) -#define GIRQ09_GPIO_0107_BITPOS (7) -// -#define GIRQ09_GPIO_0110_BITPOS (8) -#define GIRQ09_GPIO_0111_BITPOS (9) -#define GIRQ09_GPIO_0112_BITPOS (10) -#define GIRQ09_GPIO_0113_BITPOS (11) -#define GIRQ09_GPIO_0114_BITPOS (12) -#define GIRQ09_GPIO_0115_BITPOS (13) -#define GIRQ09_GPIO_0116_BITPOS (14) -#define GIRQ09_GPIO_0117_BITPOS (15) -// -#define GIRQ09_GPIO_0120_BITPOS (16) -#define GIRQ09_GPIO_0121_BITPOS (17) -#define GIRQ09_GPIO_0122_BITPOS (18) -//#define GIRQ09_GPIO_0123_BITPOS (19) RESERVED -#define GIRQ09_GPIO_0124_BITPOS (20) -#define GIRQ09_GPIO_0125_BITPOS (21) -#define GIRQ09_GPIO_0126_BITPOS (22) -#define GIRQ09_GPIO_0127_BITPOS (23) -// -#define GIRQ09_GPIO_0130_BITPOS (24) -#define GIRQ09_GPIO_0131_BITPOS (25) -#define GIRQ09_GPIO_0132_BITPOS (26) -#define GIRQ09_GPIO_0133_BITPOS (27) -#define GIRQ09_GPIO_0134_BITPOS (28) -#define GIRQ09_GPIO_0135_BITPOS (29) -#define GIRQ09_GPIO_0136_BITPOS (30) -//#define GIRQ09_GPIO_0137_BITPOS (31) RESERVED -// -#define GIRQ09_MASK (0x7FF7FFFFul) -#define GIRQ09_WAKE_CAPABLE_MASK (0x7FF7FFFFul) -// - -// GIRQ10 Bit Positions -#define GIRQ10_GPIO_0040_BITPOS (0) -#define GIRQ10_GPIO_0041_BITPOS (1) -#define GIRQ10_GPIO_0042_BITPOS (2) -#define GIRQ10_GPIO_0043_BITPOS (3) -#define GIRQ10_GPIO_0044_BITPOS (4) -#define GIRQ10_GPIO_0045_BITPOS (5) -#define GIRQ10_GPIO_0046_BITPOS (6) -#define GIRQ10_GPIO_0047_BITPOS (7) -// -#define GIRQ10_GPIO_0050_BITPOS (8) -#define GIRQ10_GPIO_0051_BITPOS (9) -#define GIRQ10_GPIO_0052_BITPOS (10) -#define GIRQ10_GPIO_0053_BITPOS (11) -#define GIRQ10_GPIO_0054_BITPOS (12) -#define GIRQ10_GPIO_0055_BITPOS (13) -#define GIRQ10_GPIO_0056_BITPOS (14) -#define GIRQ10_GPIO_0057_BITPOS (15) -// -#define GIRQ10_GPIO_0060_BITPOS (16) -#define GIRQ10_GPIO_0061_BITPOS (17) -#define GIRQ10_GPIO_0062_BITPOS (18) -#define GIRQ10_GPIO_0063_BITPOS (19) -#define GIRQ10_GPIO_0064_BITPOS (20) -#define GIRQ10_GPIO_0065_BITPOS (21) -#define GIRQ10_GPIO_0066_BITPOS (22) -#define GIRQ10_GPIO_0067_BITPOS (23) -// -#define GIRQ10_GPIO_0070_BITPOS (24) -#define GIRQ10_GPIO_0071_BITPOS (25) -#define GIRQ10_GPIO_0072_BITPOS (26) -#define GIRQ10_GPIO_0073_BITPOS (27) -#define GIRQ10_GPIO_0074_BITPOS (28) -#define GIRQ10_GPIO_0075_BITPOS (29) -#define GIRQ10_GPIO_0076_BITPOS (30) -//#define GIRQ10_GPIO_0077_BITPOS (31) RESERVED -// -#define GIRQ10_MASK (0x7FFFFFFFul) -#define GIRQ10_WAKE_CAPABLE_MASK (0x7FFFFFFFul) -// - -// GIRQ11 Bit Positions -#define GIRQ11_GPIO_0000_BITPOS (0) -#define GIRQ11_GPIO_0001_BITPOS (1) -#define GIRQ11_GPIO_0002_BITPOS (2) -#define GIRQ11_GPIO_0003_BITPOS (3) -#define GIRQ11_GPIO_0004_BITPOS (4) -#define GIRQ11_GPIO_0005_BITPOS (5) -#define GIRQ11_GPIO_0006_BITPOS (6) -#define GIRQ11_GPIO_0007_BITPOS (7) -// -#define GIRQ11_GPIO_0010_BITPOS (8) -#define GIRQ11_GPIO_0011_BITPOS (9) -#define GIRQ11_GPIO_0012_BITPOS (10) -#define GIRQ11_GPIO_0013_BITPOS (11) -#define GIRQ11_GPIO_0014_BITPOS (12) -#define GIRQ11_GPIO_0015_BITPOS (13) -#define GIRQ11_GPIO_0016_BITPOS (14) -#define GIRQ11_GPIO_0017_BITPOS (15) -// -#define GIRQ11_GPIO_0020_BITPOS (16) -#define GIRQ11_GPIO_0021_BITPOS (17) -#define GIRQ11_GPIO_0022_BITPOS (18) -#define GIRQ11_GPIO_0023_BITPOS (19) -#define GIRQ11_GPIO_0024_BITPOS (20) -#define GIRQ11_GPIO_0025_BITPOS (21) -#define GIRQ11_GPIO_0026_BITPOS (22) -#define GIRQ11_GPIO_0027_BITPOS (23) -// -#define GIRQ11_GPIO_0030_BITPOS (24) -#define GIRQ11_GPIO_0031_BITPOS (25) -#define GIRQ11_GPIO_0032_BITPOS (26) -#define GIRQ11_GPIO_0033_BITPOS (27) -#define GIRQ11_GPIO_0034_BITPOS (28) -#define GIRQ11_GPIO_0035_BITPOS (29) -#define GIRQ11_GPIO_0036_BITPOS (30) -//#define GIRQ11_GPIO_0037_BITPOS (31) RESERVED -// -#define GIRQ11_MASK (0x7FFFFFFFul) -#define GIRQ11_WAKE_CAPABLE_MASK (0x7FFFFFFFul) -// - -// GIRQ12 Bit Positions -#define GIRQ12_SMBUS0_BITPOS (0) -#define GIRQ12_SMBUS1_BITPOS (1) -#define GIRQ12_SMBUS2_BITPOS (2) -#define GIRQ12_SMBUS3_BITPOS (3) -#define GIRQ12_SMBUS0_WAKE_BITPOS (4) -#define GIRQ12_SMBUS1_WAKE_BITPOS (5) -#define GIRQ12_SMBUS2_WAKE_BITPOS (6) -#define GIRQ12_SMBUS3_WAKE_BITPOS (7) -#define GIRQ12_SMBUS4_WAKE_BITPOS (8) -// RESERVED bits[31:9] -#define GIRQ12_MASK (0x01FFul) -#define GIRQ12_WAKE_CAPABLE_MASK (0x01F0ul) -// - -// GIRQ13 Bit Positions -#define GIRQ13_DMA0_BITPOS (16) -#define GIRQ13_DMA1_BITPOS (17) -#define GIRQ13_DMA2_BITPOS (18) -#define GIRQ13_DMA3_BITPOS (19) -#define GIRQ13_DMA4_BITPOS (20) -#define GIRQ13_DMA5_BITPOS (21) -#define GIRQ13_DMA6_BITPOS (22) -#define GIRQ13_DMA7_BITPOS (23) -#define GIRQ13_DMA8_BITPOS (24) -#define GIRQ13_DMA9_BITPOS (25) -#define GIRQ13_DMA10_BITPOS (26) -#define GIRQ13_DMA11_BITPOS (27) -// -#define GIRQ13_MASK (0x0FFF0000ul) -#define GIRQ13_WAKE_CAPABLE_MASK (0x00000000ul) -// - -// GIRQ14 Bit Positions -#define GIRQ14_LPC_BITPOS (2) -// -#define GIRQ14_MASK (0x04ul) -#define GIRQ14_WAKE_CAPABLE_MASK (0x00ul) -// - -// GIRQ15 Bit Positions -#define GIRQ15_UART0_BITPOS (0) -#define GIRQ15_IMAP_BITPOS (2) -#define GIRQ15_KBD_K_BITPOS (3) -#define GIRQ15_KBD_M_BITPOS (4) -#define GIRQ15_ACPI0_IBF_BITPOS (6) -#define GIRQ15_ACPI0_OBF_BITPOS (7) -#define GIRQ15_ACPI1_IBF_BITPOS (8) -#define GIRQ15_ACPI1_OBF_BITPOS (9) -#define GIRQ15_ACPI_PM1CTL_BITPOS (10) -#define GIRQ15_ACPI_PM1EN_BITPOS (11) -#define GIRQ15_ACPI_PM1STS_BITPOS (12) -#define GIRQ15_MF8042_OBF_BITPOS (13) -#define GIRQ15_MF8042_IBF_BITPOS (14) -#define GIRQ15_MAILBOX_BITPOS (15) -#define GIRQ15_MAILBOX_DATA_BITPOS (16) -// -#define GIRQ15_MASK (0x01FFDDul) -#define GIRQ15_WAKE_CAPABLE_MASK (0x000000ul) -// - -// GIRQ16 Bit Positions -#define GIRQ16_PECI_BITPOS (3) -// -#define GIRQ16_MASK (0x08ul) -#define GIRQ16_WAKE_CAPABLE_MASK (0x00ul) -// - -// GIRQ17 Bit Positions -#define GIRQ17_TACH0_BITPOS (0) -#define GIRQ17_TACH1_BITPOS (1) -#define GIRQ17_PS2_0_WAKE_BITPOS (2) -#define GIRQ17_PS2_1_WAKE_BITPOS (3) -#define GIRQ17_PS2_2_WAKE_BITPOS (4) -#define GIRQ17_PS2_3_WAKE_BITPOS (5) -#define GIRQ17_BC_WAKE_BITPOS (6) -// RESERVED b[9:7] -#define GIRQ17_ADC_INT0_BITPOS (10) -#define GIRQ17_ADC_INT1_BITPOS (11) -#define GIRQ17_V2P_INT0_BITPOS (12) -#define GIRQ17_V2P_INT1_BITPOS (13) -#define GIRQ17_PS2_0_BITPOS (14) -#define GIRQ17_PS2_1_BITPOS (15) -#define GIRQ17_PS2_2_BITPOS (16) -#define GIRQ17_PS2_3_BITPOS (17) -// RESERVED b[19:18] -#define GIRQ17_HIBTMR_BITPOS (20) -#define GIRQ17_KEY_INT_BITPOS (21) -#define GIRQ17_KEY_INT_WAKE_BITPOS (22) -#define GIRQ17_RPM_STALL_BITPOS (23) -#define GIRQ17_RPM_SPIN_BITPOS (24) -#define GIRQ17_VBAT_BITPOS (25) -#define GIRQ17_LED0_BITPOS (26) -#define GIRQ17_LED1_BITPOS (27) -#define GIRQ17_LED2_BITPOS (28) -#define GIRQ17_MBC_ERR_BITPOS (29) -#define GIRQ17_MBC_BUSY_BITPOS (30) -// -#define GIRQ17_MASK (0x7FF3FC7Ful) -#define GIRQ17_WAKE_CAPABLE_MASK (0x0230007Cul) -// - -// GIRQ18 Bit Positions -#define GIRQ18_SPI0_TX_BITPOS (0) -#define GIRQ18_SPI0_RX_BITPOS (1) -#define GIRQ18_SPI1_TX_BITPOS (2) -#define GIRQ18_SPI1_RX_BITPOS (3) -#define GIRQ18_LED3_BITPOS (4) // NVIC 85 -#define GIRQ18_PKE_ERR_BITPOS (5) // NVIC 86 -#define GIRQ18_PKE_END_BITPOS (6) // NVIC 87 -#define GIRQ18_TRNG_BITPOS (7) // NVIC 88 -#define GIRQ18_AES_BITPOS (8) // NVIC 89 -#define GIRQ18_HASH_BITPOS (9) // NVIC 90 -// -#define GIRQ18_MASK (0x0FFul) -#define GIRQ18_WAKE_CAPABLE_MASK (0x000ul) -// - -// GIRQ19 Bit Positions -#define GIRQ19_LRESET_BITPOS (0) -#define GIRQ19_VCC_PWRGD_BITPOS (1) -// -#define GIRQ19_MASK (0x03ul) -#define GIRQ19_WAKE_CAPABLE_MASK (0x03ul) -// - -// GIRQ20 Bit Positions -#define GIRQ20_GPIO_0200_BITPOS (0) -#define GIRQ20_GPIO_0201_BITPOS (1) -#define GIRQ20_GPIO_0202_BITPOS (2) -#define GIRQ20_GPIO_0203_BITPOS (3) -#define GIRQ20_GPIO_0204_BITPOS (4) -//#define GIRQ20_GPIO_0205_BITPOS (5) -#define GIRQ20_GPIO_0206_BITPOS (6) -//#define GIRQ20_GPIO_0207_BITPOS (7) -// -#define GIRQ20_GPIO_0210_BITPOS (8) -#define GIRQ20_GPIO_0211_BITPOS (9) -#define GIRQ20_GPIO_0212_BITPOS (10) -#define GIRQ20_GPIO_0213_BITPOS (11) -// -#define GIRQ20_MASK (0x0F5Ful) -#define GIRQ20_WAKE_CAPABLE_MASK (0x0F5Ful) -// - -// GIRQ21 Bit Positions -#define GIRQ21_MASK (0x00ul) -#define GIRQ21_WAKE_CAPABLE_MASK (0x00ul) - -// GIRQ22 Bit Positions -#define GIRQ22_MASK (0x00ul) -#define GIRQ22_WAKE_CAPABLE_MASK (0x00ul) - -// GIRQ23 Bit Positions -#define GIRQ23_TMR0_BITPOS (0) -#define GIRQ23_TMR1_BITPOS (1) -#define GIRQ23_TMR2_BITPOS (2) -#define GIRQ23_TMR3_BITPOS (3) -#define GIRQ23_TMR4_BITPOS (4) -#define GIRQ23_TMR5_BITPOS (5) -// -#define GIRQ23_MASK (0x03Ful) -#define GIRQ23_WAKE_CAPABLE_MASK (0x000ul) -// - -/* ------------------------------------------------------------------------------- */ -/* NVIC,ECIA Routing Policy for Direct Mode */ -/* ------------------------------------------------------------------------------- */ -/* In Direct Mode, some interrupts could be configured to be used as aggregated. - * Configuration: - * 1. Always set ECS Interrupt Direct enable bit. - * 2. If GIRQn aggregated set Block Enable bit. - * 3. If GIRQn direct then clear Block Enable bit and enable individual NVIC inputs. - * Switching issues: - * Aggregate enable/disable requires set/clear single GIRQn bit in GIRQ Block En/Clr registers. - * Also requires set/clear of individual NVIC Enables. - * - * Note: interrupt_is_girq_direct() internal function uses this policy to detect - * if any interrupt is configured as direct or aggregated -*/ - -/** Initialize EC Interrupt Aggregator - * @param mode 1 - Direct Map mode, 0 - Fully Aggregated Mode - * @param girq_bitmask - BitMask of GIRQ to be configured as aggregated - * This parameter is only applicable in direct mode. - * @note All GPIO's and wake capable sources are always - * aggregated! GPIO's interrupts will still work in direct mode. - * Block wakes are not be routed to the processor in direct - * mode. - * Note2: This function disables and enables global interrupt - */ -void interrupt_init(uint8_t mode, uint32_t girq_bitmask); - -/** Set interrupt routing mode to aggregated or direct. - * @param mode 1 = Direct (except GPIO & wake), 0 = All Aggregated - * @note In direct mode, one could enable certain GIRQs as aggregated using - * p_interrupt_ecia_block_enable_set function - */ -void interrupt_mode_set(uint8_t mode); - -/** Clears all individual interrupts Enables and Source in ECIA, - * and Clears all NVIC external enables and pending bits - */ -void interrupt_reset(void); - -/** Enables interrupt for a device - * @param dev_iroute - source IROUTING information - * @note This function disables and enables global interrupt - */ -void interrupt_device_enable(uint32_t dev_iroute); - -/** Disables interrupt for a device - * @param dev_iroute - source IROUTING information - * @note This function disables and enables global interrupt - */ -void interrupt_device_disable(uint32_t dev_iroute); - -/* ------------------------------------------------------------------------------- */ -/* ECIA APIs using device IROUTE() as input */ -/* ------------------------------------------------------------------------------- */ - -/** Clear Source in the ECIA for the device - * @param devi - device IROUTING value - */ -void interrupt_device_ecia_source_clear(const uint32_t dev_iroute); - -/** Get the Source bit in the ECIA for the device - * @param devi - device IROUTING value - * @return 0 if source bit not set; else non-zero value - */ -uint32_t interrupt_device_ecia_source_get(const uint32_t dev_iroute); - -/** Get the Result bit in the ECIA for the device - * @param devi - device IROUTING value - * @return 0 if result bit not set; else non-zero value - */ -uint32_t interrupt_device_ecia_result_get(const uint32_t dev_iroute); - -/* ------------------------------------------------------------------------------- */ -/* NVIC APIs using device IROUTE() as input */ -/* ------------------------------------------------------------------------------- */ -/* Note that if the device interrupt is aggregated, then these APIs would affect the - * NVIC corresponding to the aggregated GIRQ - */ - -/** Enable/Disable the NVIC (in the NVIC controller) for the device - * @param dev_iroute : source IROUTING information (encoded in a uint32_t) - * @param en_flag : 1 = Enable the NVIC IRQ, 0 = Disable the NVIC IRQ - * @note Recommended to use interrupt_device_enable, interrupt_device_disable - * to enable/disable interrupts for the device, since those APIs configure ECIA as well - */ -void interrupt_device_nvic_enable(uint32_t dev_iroute, uint8_t en_flag); - -/** Set NVIC priority for specified peripheral interrupt source - * @param dev_iroute - source IROUTING information (encoded in a uint32_t) - * @param nvic_pri - NVIC Priority - * @note 1. If ECIA is in aggregated mode, the priority affects all interrupt - * sources in the GIRQ. - * 2. This function disables and enables global interrupt - */ -void interrupt_device_nvic_priority_set(const uint32_t dev_iroute, const uint8_t nvic_pri); - -/** Return NVIC priority for interrupt source - * @param dev_iroute - source IROUTING information - * @return uint32_t NVIC priority - */ -uint32_t interrupt_device_nvic_priority_get(const uint32_t dev_iroute); - -/** Return NVIC pending for interrupt source - * @param dev_iroute - source IROUTING information - * @return uint8_t 0(not pending), 1 (pending in NVIC) - * - */ -uint8_t interrupt_device_nvic_pending_get(const uint32_t dev_iroute); - -/** Set NVIC pending for interrupt source - * @param dev_iroute - source IROUTING information - */ -void interrupt_device_nvic_pending_set(const uint32_t dev_iroute); - -/** Clears NVIC pending for interrupt source - * @param dev_iroute - source IROUTING information - * @return uint8_t 0(not pending), 1 (pending in NVIC) - before clear - * @note This function disables and enables global interrupt - */ -uint8_t interrupt_device_nvic_pending_clear(const uint32_t dev_iroute); - -/* ------------------------------------------------------------------------------- */ -/* Peripheral Functions - Operations on GIRQ Block Enable Set, Enable Clear * - * and Status Register */ -/* ------------------------------------------------------------------------------- */ - -/** Enable specified GIRQ in ECIA block - * @param girq_id - enum MEC_GIRQ_IDS - */ - void p_interrupt_ecia_block_enable_set(uint8_t girq_id); - - /** Enable GIRQs in ECIA Block - * @param girq_bitmask - Bitmask of GIRQs to be enabled in ECIA Block - */ -void p_interrupt_ecia_block_enable_bitmask_set(uint32_t girq_bitmask); - -/** Check if specified GIRQ block enabled or not - * @param girq_id - enum MEC_GIRQ_IDS - * @return retVal - 1 if the particular GIRQ block enabled, else 0 - */ -uint8_t p_interrupt_ecia_block_enable_get(uint8_t girq_id); - -/** Set all GIRQ block enables */ -void p_interrupt_ecia_block_enable_all_set(void); - -/** Clear specified GIRQ in ECIA Block - * @param girq_id - enum MEC_GIRQ_IDS - */ -void p_interrupt_ecia_block_enable_clr(uint8_t girq_id); - -/** Clear GIRQs in ECIA Block - * @param girq_bitmask - Bitmask of GIRQs to be cleared in ECIA Block - */ -void p_interrupt_ecia_block_enable_bitmask_clr(uint32_t girq_bitmask); - -/** p_interrupt_ecia_block_enable_all_clr - Clears all GIRQ block enables */ -void p_interrupt_ecia_block_enable_all_clr(void); - - /** Get status of GIRQ in ECIA Block - * @param girq_id - enum MEC_GIRQ_IDS - * @return 0 if status bit not set; else non-zero value - */ -uint32_t p_interrupt_ecia_block_irq_status_get(uint8_t girq_id); - -/** Reads the Block IRQ Vector Register - * @return 32-bit value - */ -uint32_t p_interrupt_ecia_block_irq_all_status_get(void); - -/* ---------------------------------------------------------------------------- */ -/* Peripheral Functions - Operations on GIRQx Source, Enable, Result * - * and Enable Registers */ -/* ---------------------------------------------------------------------------- */ - -/** Clear specified interrupt source bit in GIRQx - * @param girq_id - enum MEC_GIRQ_IDS - * @param bitnum -[0, 31] - */ -void p_interrupt_ecia_girq_source_clr(int16_t girq_id, uint8_t bitnum); - -/** Read the specified interrupt source bit in GIRQx - * @param girq_id - enum MEC_GIRQ_IDS - * @param bitnum -[0, 31] - * @return 0 if source bit not set; else non-zero value - */ -uint32_t p_interrupt_ecia_girq_source_get(int16_t girq_id, uint8_t bitnum); - -/** Enable the specified interrupt in GIRQx - * girq_id - enum MEC_GIRQ_IDS - * bitnum = [0, 31] - */ -void p_interrupt_ecia_girq_enable_set(uint16_t girq_id, uint8_t bitnum); - -/** Disable the specified interrupt in GIRQx - * girq_id - enum MEC_GIRQ_IDS - * bitnum = [0, 31] - */ -void p_interrupt_ecia_girq_enable_clr(uint16_t girq_id, uint8_t bitnum); - -/** Read the status of the specified interrupt in GIRQx - * girq_id - enum MEC_GIRQ_IDS - * bitnum = [0, 31] - * @return 0 if enable bit not set; else non-zero value - */ -uint32_t p_interrupt_ecia_girq_enable_get(uint16_t girq_id, uint8_t bitnum); - -/** Read the result bit of the interrupt in GIRQx - * @param girq_id - enum MEC_GIRQ_IDS - * @param bitnum -[0, 31] - * @return 0 if enable bit not set; else non-zero value - */ -uint32_t p_interrupt_ecia_girq_result_get(int16_t girq_id, uint8_t bitnum); - -/* ------------------------------------------------------------------------------- */ -/* Peripheral Function - Operations on all GIRQs */ -/* ------------------------------------------------------------------------------- */ - -/** Clear all aggregator GIRQn status registers */ -void p_interrupt_ecia_girqs_source_reset(void); - -/** Clear all aggregator GIRQn enables */ - void p_interrupt_ecia_girqs_enable_reset(void); - -/* ------------------------------------------------------------------------------- */ -/* Peripheral Function - Function to set interrupt control */ -/* ------------------------------------------------------------------------------- */ - -/** Set interrupt control - * @param nvic_en_flag : 0 = Alternate NVIC disabled, 1 = Alternate NVIC enabled - */ - void p_interrupt_control_set(uint8_t nvic_en_flag); - - /** Read interrupt control - * @return uint8_t - 0 = Alternate NVIC disabled, 1 = Alternate NVIC enabled - */ -uint8_t p_interrupt_control_get(void); - -/* ------------------------------------------------------------------------------- */ -/* Peripheral Functions - NVIC */ -/* ------------------------------------------------------------------------------- */ - -/** Enable/Disable the NVIC IRQ in the NVIC interrupt controller - * @param nvic_num : NVIC number (see enum IRQn_Type) - * @param en_flag : 1 = Enable the NVIC IRQ, 0 = Disable the NVIC IRQ - * @note Application should perform this operation - */ - void p_interrupt_nvic_enable(IRQn_Type nvic_num, uint8_t en_flag); - - /** ecia_nvic_clr_en - Clear all NVIC external enables */ -void p_interrupt_nvic_extEnables_clr(void); - -/** Clear all NVIC external enables and pending bits */ -void p_interrupt_nvic_enpend_clr(void); - -/** Set NVIC external priorities to POR value */ -void p_interrupt_nvic_priorities_default_set(void); - -/** Set NVIC external priorities to specified priority (0 - 7) - * @param zero-based 3-bit priority value: 0=highest, 7=lowest. - * @note NVIC highest priority is the value 0, lowest is all 1's. - * Each external interrupt has an 8-bit register and the priority - * is left justified in the registers. MECxxx implements 8 priority - * levels or bits [7:5] in the register. Lowest priority = 0xE0 - */ -void p_interrupt_nvic_priorities_set(uint8_t new_pri); - -#endif /*_INTERRUPT_H_*/ - -/** @} - */ - - - diff --git a/FreeRTOS/Demo/Common/Minimal/AbortDelay.c b/FreeRTOS/Demo/Common/Minimal/AbortDelay.c index ffef52174..b38e94464 100644 --- a/FreeRTOS/Demo/Common/Minimal/AbortDelay.c +++ b/FreeRTOS/Demo/Common/Minimal/AbortDelay.c @@ -398,13 +398,23 @@ uint32_t ulReturn; static void prvTestAbortingEventGroupWait( void ) { TickType_t xTimeAtStart; -static StaticEventGroup_t xEventGroupBuffer; EventGroupHandle_t xEventGroup; EventBits_t xBitsToWaitFor = ( EventBits_t ) 0x01, xReturn; - /* Create the event group. Statically allocated memory is used so the - creation cannot fail. */ - xEventGroup = xEventGroupCreateStatic( &xEventGroupBuffer ); + #if( configSUPPORT_STATIC_ALLOCATION == 1 ) + { + static StaticEventGroup_t xEventGroupBuffer; + + /* Create the event group. Statically allocated memory is used so the + creation cannot fail. */ + xEventGroup = xEventGroupCreateStatic( &xEventGroupBuffer ); + } + #else + { + xEventGroup = xEventGroupCreate(); + configASSERT( xEventGroup ); + } + #endif /* Note the time before the delay so the length of the delay is known. */ xTimeAtStart = xTaskGetTickCount(); @@ -449,14 +459,25 @@ static void prvTestAbortingQueueSend( void ) { TickType_t xTimeAtStart; BaseType_t xReturn; -static StaticQueue_t xQueueBuffer; -static uint8_t ucQueueStorage[ sizeof( uint8_t ) ], ucItemToQueue; const UBaseType_t xQueueLength = ( UBaseType_t ) 1; QueueHandle_t xQueue; +uint8_t ucItemToQueue; - /* Create the queue. Statically allocated memory is used so the - creation cannot fail. */ - xQueue = xQueueCreateStatic( xQueueLength, sizeof( uint8_t ), ucQueueStorage, &xQueueBuffer ); + #if( configSUPPORT_STATIC_ALLOCATION == 1 ) + { + static StaticQueue_t xQueueBuffer; + static uint8_t ucQueueStorage[ sizeof( uint8_t ) ]; + + /* Create the queue. Statically allocated memory is used so the + creation cannot fail. */ + xQueue = xQueueCreateStatic( xQueueLength, sizeof( uint8_t ), ucQueueStorage, &xQueueBuffer ); + } + #else + { + xQueue = xQueueCreate( xQueueLength, sizeof( uint8_t ) ); + configASSERT( xQueue ); + } + #endif /* This function tests aborting when in the blocked state waiting to send, so the queue must be full. There is only one space in the queue. */ @@ -509,12 +530,21 @@ static void prvTestAbortingSemaphoreTake( void ) { TickType_t xTimeAtStart; BaseType_t xReturn; -static StaticSemaphore_t xSemaphoreBuffer; SemaphoreHandle_t xSemaphore; - /* Create the semaphore. Statically allocated memory is used so the - creation cannot fail. */ - xSemaphore = xSemaphoreCreateBinaryStatic( &xSemaphoreBuffer ); + #if( configSUPPORT_STATIC_ALLOCATION == 1 ) + { + static StaticSemaphore_t xSemaphoreBuffer; + + /* Create the semaphore. Statically allocated memory is used so the + creation cannot fail. */ + xSemaphore = xSemaphoreCreateBinaryStatic( &xSemaphoreBuffer ); + } + #else + { + xSemaphore = xSemaphoreCreateBinary(); + } + #endif /* Note the time before the delay so the length of the delay is known. */ xTimeAtStart = xTaskGetTickCount(); diff --git a/FreeRTOS/Demo/Common/Minimal/BlockQ.c b/FreeRTOS/Demo/Common/Minimal/BlockQ.c index 65b5a6e74..912ce3a38 100644 --- a/FreeRTOS/Demo/Common/Minimal/BlockQ.c +++ b/FreeRTOS/Demo/Common/Minimal/BlockQ.c @@ -104,6 +104,10 @@ #define blckqSTACK_SIZE configMINIMAL_STACK_SIZE #define blckqNUM_TASK_SETS ( 3 ) +#if( configSUPPORT_DYNAMIC_ALLOCATION == 0 ) + #error This example cannot be used if dynamic allocation is not allowed. +#endif + /* Structure used to pass parameters to the blocking queue tasks. */ typedef struct BLOCKING_QUEUE_PARAMETERS { diff --git a/FreeRTOS/Demo/Common/Minimal/GenQTest.c b/FreeRTOS/Demo/Common/Minimal/GenQTest.c index 12fc5b218..7391000c1 100644 --- a/FreeRTOS/Demo/Common/Minimal/GenQTest.c +++ b/FreeRTOS/Demo/Common/Minimal/GenQTest.c @@ -154,36 +154,42 @@ SemaphoreHandle_t xMutex; prvSendFrontAndBackTest demo. */ xQueue = xQueueCreate( genqQUEUE_LENGTH, sizeof( uint32_t ) ); - /* vQueueAddToRegistry() adds the queue to the queue registry, if one is - in use. The queue registry is provided as a means for kernel aware - debuggers to locate queues and has no purpose if a kernel aware debugger - is not being used. The call to vQueueAddToRegistry() will be removed - by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is - defined to be less than 1. */ - vQueueAddToRegistry( xQueue, "Gen_Queue_Test" ); - - /* Create the demo task and pass it the queue just created. We are - passing the queue handle by value so it does not matter that it is - declared on the stack here. */ - xTaskCreate( prvSendFrontAndBackTest, "GenQ", configMINIMAL_STACK_SIZE, ( void * ) xQueue, uxPriority, NULL ); + if( xQueue != NULL ) + { + /* vQueueAddToRegistry() adds the queue to the queue registry, if one + is in use. The queue registry is provided as a means for kernel aware + debuggers to locate queues and has no purpose if a kernel aware debugger + is not being used. The call to vQueueAddToRegistry() will be removed + by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is + defined to be less than 1. */ + vQueueAddToRegistry( xQueue, "Gen_Queue_Test" ); + + /* Create the demo task and pass it the queue just created. We are + passing the queue handle by value so it does not matter that it is + declared on the stack here. */ + xTaskCreate( prvSendFrontAndBackTest, "GenQ", configMINIMAL_STACK_SIZE, ( void * ) xQueue, uxPriority, NULL ); + } /* Create the mutex used by the prvMutexTest task. */ xMutex = xSemaphoreCreateMutex(); - /* vQueueAddToRegistry() adds the mutex to the registry, if one is - in use. The registry is provided as a means for kernel aware - debuggers to locate mutexes and has no purpose if a kernel aware debugger - is not being used. The call to vQueueAddToRegistry() will be removed - by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is - defined to be less than 1. */ - vQueueAddToRegistry( ( QueueHandle_t ) xMutex, "Gen_Queue_Mutex" ); - - /* Create the mutex demo tasks and pass it the mutex just created. We are - passing the mutex handle by value so it does not matter that it is declared - on the stack here. */ - xTaskCreate( prvLowPriorityMutexTask, "MuLow", configMINIMAL_STACK_SIZE, ( void * ) xMutex, genqMUTEX_LOW_PRIORITY, NULL ); - xTaskCreate( prvMediumPriorityMutexTask, "MuMed", configMINIMAL_STACK_SIZE, NULL, genqMUTEX_MEDIUM_PRIORITY, &xMediumPriorityMutexTask ); - xTaskCreate( prvHighPriorityMutexTask, "MuHigh", configMINIMAL_STACK_SIZE, ( void * ) xMutex, genqMUTEX_HIGH_PRIORITY, &xHighPriorityMutexTask ); + if( xMutex != NULL ) + { + /* vQueueAddToRegistry() adds the mutex to the registry, if one is + in use. The registry is provided as a means for kernel aware + debuggers to locate mutexes and has no purpose if a kernel aware + debugger is not being used. The call to vQueueAddToRegistry() will be + removed by the pre-processor if configQUEUE_REGISTRY_SIZE is not + defined or is defined to be less than 1. */ + vQueueAddToRegistry( ( QueueHandle_t ) xMutex, "Gen_Queue_Mutex" ); + + /* Create the mutex demo tasks and pass it the mutex just created. We + are passing the mutex handle by value so it does not matter that it is + declared on the stack here. */ + xTaskCreate( prvLowPriorityMutexTask, "MuLow", configMINIMAL_STACK_SIZE, ( void * ) xMutex, genqMUTEX_LOW_PRIORITY, NULL ); + xTaskCreate( prvMediumPriorityMutexTask, "MuMed", configMINIMAL_STACK_SIZE, NULL, genqMUTEX_MEDIUM_PRIORITY, &xMediumPriorityMutexTask ); + xTaskCreate( prvHighPriorityMutexTask, "MuHigh", configMINIMAL_STACK_SIZE, ( void * ) xMutex, genqMUTEX_HIGH_PRIORITY, &xHighPriorityMutexTask ); + } } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Demo/Common/Minimal/PollQ.c b/FreeRTOS/Demo/Common/Minimal/PollQ.c index 802b1023c..a8bf5d640 100644 --- a/FreeRTOS/Demo/Common/Minimal/PollQ.c +++ b/FreeRTOS/Demo/Common/Minimal/PollQ.c @@ -134,17 +134,20 @@ static QueueHandle_t xPolledQueue; /* Create the queue used by the producer and consumer. */ xPolledQueue = xQueueCreate( pollqQUEUE_SIZE, ( UBaseType_t ) sizeof( uint16_t ) ); - /* vQueueAddToRegistry() adds the queue to the queue registry, if one is - in use. The queue registry is provided as a means for kernel aware - debuggers to locate queues and has no purpose if a kernel aware debugger - is not being used. The call to vQueueAddToRegistry() will be removed - by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is - defined to be less than 1. */ - vQueueAddToRegistry( xPolledQueue, "Poll_Test_Queue" ); - - /* Spawn the producer and consumer. */ - xTaskCreate( vPolledQueueConsumer, "QConsNB", pollqSTACK_SIZE, ( void * ) &xPolledQueue, uxPriority, ( TaskHandle_t * ) NULL ); - xTaskCreate( vPolledQueueProducer, "QProdNB", pollqSTACK_SIZE, ( void * ) &xPolledQueue, uxPriority, ( TaskHandle_t * ) NULL ); + if( xPolledQueue != NULL ) + { + /* vQueueAddToRegistry() adds the queue to the queue registry, if one is + in use. The queue registry is provided as a means for kernel aware + debuggers to locate queues and has no purpose if a kernel aware debugger + is not being used. The call to vQueueAddToRegistry() will be removed + by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is + defined to be less than 1. */ + vQueueAddToRegistry( xPolledQueue, "Poll_Test_Queue" ); + + /* Spawn the producer and consumer. */ + xTaskCreate( vPolledQueueConsumer, "QConsNB", pollqSTACK_SIZE, ( void * ) &xPolledQueue, uxPriority, ( TaskHandle_t * ) NULL ); + xTaskCreate( vPolledQueueProducer, "QProdNB", pollqSTACK_SIZE, ( void * ) &xPolledQueue, uxPriority, ( TaskHandle_t * ) NULL ); + } } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Demo/Common/Minimal/QPeek.c b/FreeRTOS/Demo/Common/Minimal/QPeek.c index 1749203fa..a60d8f0d8 100644 --- a/FreeRTOS/Demo/Common/Minimal/QPeek.c +++ b/FreeRTOS/Demo/Common/Minimal/QPeek.c @@ -127,21 +127,24 @@ QueueHandle_t xQueue; /* Create the queue that we are going to use for the test/demo. */ xQueue = xQueueCreate( qpeekQUEUE_LENGTH, sizeof( uint32_t ) ); - /* vQueueAddToRegistry() adds the queue to the queue registry, if one is - in use. The queue registry is provided as a means for kernel aware - debuggers to locate queues and has no purpose if a kernel aware debugger - is not being used. The call to vQueueAddToRegistry() will be removed - by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is - defined to be less than 1. */ - vQueueAddToRegistry( xQueue, "QPeek_Test_Queue" ); - - /* Create the demo tasks and pass it the queue just created. We are - passing the queue handle by value so it does not matter that it is declared - on the stack here. */ - xTaskCreate( prvLowPriorityPeekTask, "PeekL", configMINIMAL_STACK_SIZE, ( void * ) xQueue, qpeekLOW_PRIORITY, NULL ); - xTaskCreate( prvMediumPriorityPeekTask, "PeekM", configMINIMAL_STACK_SIZE, ( void * ) xQueue, qpeekMEDIUM_PRIORITY, &xMediumPriorityTask ); - xTaskCreate( prvHighPriorityPeekTask, "PeekH1", configMINIMAL_STACK_SIZE, ( void * ) xQueue, qpeekHIGH_PRIORITY, &xHighPriorityTask ); - xTaskCreate( prvHighestPriorityPeekTask, "PeekH2", configMINIMAL_STACK_SIZE, ( void * ) xQueue, qpeekHIGHEST_PRIORITY, &xHighestPriorityTask ); + if( xQueue != NULL ) + { + /* vQueueAddToRegistry() adds the queue to the queue registry, if one is + in use. The queue registry is provided as a means for kernel aware + debuggers to locate queues and has no purpose if a kernel aware debugger + is not being used. The call to vQueueAddToRegistry() will be removed + by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is + defined to be less than 1. */ + vQueueAddToRegistry( xQueue, "QPeek_Test_Queue" ); + + /* Create the demo tasks and pass it the queue just created. We are + passing the queue handle by value so it does not matter that it is declared + on the stack here. */ + xTaskCreate( prvLowPriorityPeekTask, "PeekL", configMINIMAL_STACK_SIZE, ( void * ) xQueue, qpeekLOW_PRIORITY, NULL ); + xTaskCreate( prvMediumPriorityPeekTask, "PeekM", configMINIMAL_STACK_SIZE, ( void * ) xQueue, qpeekMEDIUM_PRIORITY, &xMediumPriorityTask ); + xTaskCreate( prvHighPriorityPeekTask, "PeekH1", configMINIMAL_STACK_SIZE, ( void * ) xQueue, qpeekHIGH_PRIORITY, &xHighPriorityTask ); + xTaskCreate( prvHighestPriorityPeekTask, "PeekH2", configMINIMAL_STACK_SIZE, ( void * ) xQueue, qpeekHIGHEST_PRIORITY, &xHighestPriorityTask ); + } } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Demo/Common/Minimal/QueueSet.c b/FreeRTOS/Demo/Common/Minimal/QueueSet.c index c97c5d4ab..495e54b25 100644 --- a/FreeRTOS/Demo/Common/Minimal/QueueSet.c +++ b/FreeRTOS/Demo/Common/Minimal/QueueSet.c @@ -234,14 +234,18 @@ void vStartQueueSetTasks( void ) { /* Create the tasks. */ xTaskCreate( prvQueueSetSendingTask, "SetTx", configMINIMAL_STACK_SIZE, NULL, queuesetMEDIUM_PRIORITY, &xQueueSetSendingTask ); - xTaskCreate( prvQueueSetReceivingTask, "SetRx", configMINIMAL_STACK_SIZE, ( void * ) xQueueSetSendingTask, queuesetMEDIUM_PRIORITY, &xQueueSetReceivingTask ); - - /* It is important that the sending task does not attempt to write to a - queue before the queue has been created. It is therefore placed into the - suspended state before the scheduler has started. It is resumed by the - receiving task after the receiving task has created the queues and added the - queues to the queue set. */ - vTaskSuspend( xQueueSetSendingTask ); + + if( xQueueSetSendingTask != NULL ) + { + xTaskCreate( prvQueueSetReceivingTask, "SetRx", configMINIMAL_STACK_SIZE, ( void * ) xQueueSetSendingTask, queuesetMEDIUM_PRIORITY, &xQueueSetReceivingTask ); + + /* It is important that the sending task does not attempt to write to a + queue before the queue has been created. It is therefore placed into + the suspended state before the scheduler has started. It is resumed by + the receiving task after the receiving task has created the queues and + added the queues to the queue set. */ + vTaskSuspend( xQueueSetSendingTask ); + } } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Demo/Common/Minimal/QueueSetPolling.c b/FreeRTOS/Demo/Common/Minimal/QueueSetPolling.c index a4752bed3..9a40cabf7 100644 --- a/FreeRTOS/Demo/Common/Minimal/QueueSetPolling.c +++ b/FreeRTOS/Demo/Common/Minimal/QueueSetPolling.c @@ -130,10 +130,14 @@ void vStartQueueSetPollingTask( void ) the set. */ xQueue = xQueueCreate( setpollQUEUE_LENGTH, sizeof( uint32_t ) ); xQueueSet = xQueueCreateSet( setpollQUEUE_LENGTH ); - xQueueAddToSet( xQueue, xQueueSet ); - /* Create the task. */ - xTaskCreate( prvQueueSetReceivingTask, "SetPoll", configMINIMAL_STACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); + if( ( xQueue != NULL ) && ( xQueueSet != NULL ) ) + { + xQueueAddToSet( xQueue, xQueueSet ); + + /* Create the task. */ + xTaskCreate( prvQueueSetReceivingTask, "SetPoll", configMINIMAL_STACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); + } } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Demo/Common/Minimal/StaticAllocation.c b/FreeRTOS/Demo/Common/Minimal/StaticAllocation.c index 588299ee7..1433476f2 100644 --- a/FreeRTOS/Demo/Common/Minimal/StaticAllocation.c +++ b/FreeRTOS/Demo/Common/Minimal/StaticAllocation.c @@ -279,10 +279,25 @@ static void prvStaticallyAllocatedCreator( void *pvParameters ) allocation. */ prvCreateAndDeleteStaticallyAllocatedTasks(); prvCreateAndDeleteStaticallyAllocatedQueues(); + + /* Ensure lower priority tasks get CPU time. */ + vTaskDelay( prvGetNextDelayTime() ); + + /* Just to show the check task that this task is still executing. */ + uxCycleCounter++; + prvCreateAndDeleteStaticallyAllocatedBinarySemaphores(); prvCreateAndDeleteStaticallyAllocatedCountingSemaphores(); + + vTaskDelay( prvGetNextDelayTime() ); + uxCycleCounter++; + prvCreateAndDeleteStaticallyAllocatedMutexes(); prvCreateAndDeleteStaticallyAllocatedRecursiveMutexes(); + + vTaskDelay( prvGetNextDelayTime() ); + uxCycleCounter++; + prvCreateAndDeleteStaticallyAllocatedEventGroups(); prvCreateAndDeleteStaticallyAllocatedTimers(); } @@ -553,25 +568,6 @@ StaticSemaphore_t xSemaphoreBuffer; /* Delete the semaphore again so the buffers can be reused. */ vSemaphoreDelete( xSemaphore ); - - - /* The semaphore created above had a statically allocated semaphore - structure. Repeat the above using NULL as the third - xSemaphoreCreateCountingStatic() parameter so the semaphore structure is - instead allocated dynamically. */ - xSemaphore = xSemaphoreCreateCountingStatic( uxMaxCount, 0, NULL ); - - /* Ensure the semaphore passes a few sanity checks as a valid semaphore. */ - prvSanityCheckCreatedSemaphore( xSemaphore, uxMaxCount ); - - /* Delete the semaphore again so the buffers can be reused. */ - vSemaphoreDelete( xSemaphore ); - - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); - - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; } /*-----------------------------------------------------------*/ @@ -606,25 +602,6 @@ StaticSemaphore_t xSemaphoreBuffer; /* Delete the semaphore again so the buffers can be reused. */ vSemaphoreDelete( xSemaphore ); - - - /* The semaphore created above had a statically allocated semaphore - structure. Repeat the above using NULL as the - xSemaphoreCreateRecursiveMutexStatic() parameter so the semaphore structure - is instead allocated dynamically. */ - xSemaphore = xSemaphoreCreateRecursiveMutexStatic( NULL ); - - /* Ensure the semaphore passes a few sanity checks as a valid semaphore. */ - prvSanityCheckCreatedRecursiveMutex( xSemaphore ); - - /* Delete the semaphore again so the buffers can be reused. */ - vSemaphoreDelete( xSemaphore ); - - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); - - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; } /*-----------------------------------------------------------*/ @@ -649,11 +626,11 @@ http://www.freertos.org/Embedded-RTOS-Queues.html */ static uint8_t ucQueueStorageArea[ staticQUEUE_LENGTH_IN_ITEMS * sizeof( uint64_t ) ]; /* Create the queue. xQueueCreateStatic() has two more parameters than the - usual xQueueCreate() function. The first new paraemter is a pointer to the + usual xQueueCreate() function. The first new parameter is a pointer to the pre-allocated queue storage area. The second new parameter is a pointer to the StaticQueue_t structure that will hold the queue state information in - an anonymous way. If either pointer is passed as NULL then the respective - data will be allocated dynamically as if xQueueCreate() had been called. */ + an anonymous way. If the two pointers are passed as NULL then the data + will be allocated dynamically as if xQueueCreate() had been called. */ xQueue = xQueueCreateStatic( staticQUEUE_LENGTH_IN_ITEMS, /* The maximum number of items the queue can hold. */ sizeof( uint64_t ), /* The size of each item. */ ucQueueStorageArea, /* The buffer used to hold items within the queue. */ @@ -668,48 +645,6 @@ static uint8_t ucQueueStorageArea[ staticQUEUE_LENGTH_IN_ITEMS * sizeof( uint64_ /* Delete the queue again so the buffers can be reused. */ vQueueDelete( xQueue ); - - - /* The queue created above had a statically allocated queue storage area and - queue structure. Repeat the above with three more times - with different - combinations of static and dynamic allocation. */ - - xQueue = xQueueCreateStatic( staticQUEUE_LENGTH_IN_ITEMS, /* The maximum number of items the queue can hold. */ - sizeof( uint64_t ), /* The size of each item. */ - NULL, /* Allocate the buffer used to hold items within the queue dynamically. */ - &xStaticQueue ); /* The static queue structure that will hold the state of the queue. */ - - configASSERT( xQueue == ( QueueHandle_t ) &xStaticQueue ); - prvSanityCheckCreatedQueue( xQueue ); - vQueueDelete( xQueue ); - - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); - - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; - - xQueue = xQueueCreateStatic( staticQUEUE_LENGTH_IN_ITEMS, /* The maximum number of items the queue can hold. */ - sizeof( uint64_t ), /* The size of each item. */ - ucQueueStorageArea, /* The buffer used to hold items within the queue. */ - NULL ); /* The queue structure is allocated dynamically. */ - - prvSanityCheckCreatedQueue( xQueue ); - vQueueDelete( xQueue ); - - xQueue = xQueueCreateStatic( staticQUEUE_LENGTH_IN_ITEMS, /* The maximum number of items the queue can hold. */ - sizeof( uint64_t ), /* The size of each item. */ - NULL, /* Allocate the buffer used to hold items within the queue dynamically. */ - NULL ); /* The queue structure is allocated dynamically. */ - - prvSanityCheckCreatedQueue( xQueue ); - vQueueDelete( xQueue ); - - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); - - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; } /*-----------------------------------------------------------*/ @@ -753,33 +688,6 @@ StaticSemaphore_t xSemaphoreBuffer; /* Delete the semaphore again so the buffers can be reused. */ vSemaphoreDelete( xSemaphore ); - - - /* The semaphore created above had a statically allocated semaphore - structure. Repeat the above using NULL as the xSemaphoreCreateMutexStatic() - parameter so the semaphore structure is instead allocated dynamically. */ - xSemaphore = xSemaphoreCreateMutexStatic( NULL ); - - /* Take the mutex so the mutex is in the state expected by the - prvSanityCheckCreatedSemaphore() function. */ - xReturned = xSemaphoreTake( xSemaphore, staticDONT_BLOCK ); - - if( xReturned != pdPASS ) - { - xErrorOccurred = pdTRUE; - } - - /* Ensure the semaphore passes a few sanity checks as a valid semaphore. */ - prvSanityCheckCreatedSemaphore( xSemaphore, staticBINARY_SEMAPHORE_MAX_COUNT ); - - /* Delete the semaphore again so the buffers can be reused. */ - vSemaphoreDelete( xSemaphore ); - - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); - - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; } /*-----------------------------------------------------------*/ @@ -817,40 +725,25 @@ StaticSemaphore_t xSemaphoreBuffer; vSemaphoreDelete( xSemaphore ); - /* The semaphore created above had a statically allocated semaphore - structure. Repeat the above using NULL as the xSemaphoreCreateBinaryStatic() - parameter so the semaphore structure is instead allocated dynamically. */ - xSemaphore = xSemaphoreCreateBinaryStatic( NULL ); - - /* Ensure the semaphore passes a few sanity checks as a valid semaphore. */ - prvSanityCheckCreatedSemaphore( xSemaphore, staticBINARY_SEMAPHORE_MAX_COUNT ); - - /* Delete the semaphore again so the buffers can be reused. */ - vSemaphoreDelete( xSemaphore ); - - - /* There isn't a static version of the old and deprecated vSemaphoreCreateBinary() macro (because its deprecated!), but check it is still functioning correctly when configSUPPORT_STATIC_ALLOCATION is set to 1. */ - vSemaphoreCreateBinary( xSemaphore ); - - /* The macro starts with the binary semaphore available, but the test - function expects it to be unavailable. */ - if( xSemaphoreTake( xSemaphore, staticDONT_BLOCK ) == pdFAIL ) + #if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) { - xErrorOccurred = pdTRUE; - } - - prvSanityCheckCreatedSemaphore( xSemaphore, staticBINARY_SEMAPHORE_MAX_COUNT ); - vSemaphoreDelete( xSemaphore ); + vSemaphoreCreateBinary( xSemaphore ); - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); + /* The macro starts with the binary semaphore available, but the test + function expects it to be unavailable. */ + if( xSemaphoreTake( xSemaphore, staticDONT_BLOCK ) == pdFAIL ) + { + xErrorOccurred = pdTRUE; + } - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; + prvSanityCheckCreatedSemaphore( xSemaphore, staticBINARY_SEMAPHORE_MAX_COUNT ); + vSemaphoreDelete( xSemaphore ); + } + #endif } /*-----------------------------------------------------------*/ @@ -945,43 +838,6 @@ StaticTimer_t xTimerBuffer; /* Just to show the check task that this task is still executing. */ uxCycleCounter++; - - /* The software timer created above had a statically allocated timer - structure. Repeat the above using NULL as the xTimerCreateStatic() - parameter so the timer structure is instead allocated dynamically. */ - xTimer = xTimerCreateStatic( "T1", /* Text name for the task. Helps debugging only. Not used by FreeRTOS. */ - xTimerPeriod, /* The period of the timer in ticks. */ - pdTRUE, /* This is an auto-reload timer. */ - ( void * ) &uxVariableToIncrement, /* The variable incremented by the test is passed into the timer callback using the timer ID. */ - prvTimerCallback, /* The function to execute when the timer expires. */ - NULL ); /* A buffer is not passed this time, so the timer should be allocated dynamically. */ - uxVariableToIncrement = 0; - xReturned = xTimerStart( xTimer, staticDONT_BLOCK ); - - if( xReturned != pdPASS ) - { - xErrorOccurred = pdTRUE; - } - - vTaskDelay( xTimerPeriod * staticMAX_TIMER_CALLBACK_EXECUTIONS ); - - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; - - if( uxVariableToIncrement != staticMAX_TIMER_CALLBACK_EXECUTIONS ) - { - xErrorOccurred = pdTRUE; - } - - xReturned = xTimerDelete( xTimer, staticDONT_BLOCK ); - - if( xReturned != pdPASS ) - { - xErrorOccurred = pdTRUE; - } - - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; } /*-----------------------------------------------------------*/ @@ -1015,25 +871,6 @@ StaticEventGroup_t xEventGroupBuffer; /* Delete the event group again so the buffers can be reused. */ vEventGroupDelete( xEventGroup ); - - - /* The event group created above had a statically allocated event group - structure. Repeat the above using NULL as the xEventGroupCreateStatic() - parameter so the event group structure is instead allocated dynamically. */ - xEventGroup = xEventGroupCreateStatic( NULL ); - - /* Ensure the event group passes a few sanity checks as a valid event - group. */ - prvSanityCheckCreatedEventGroup( xEventGroup ); - - /* Delete the event group again so the buffers can be reused. */ - vEventGroupDelete( xEventGroup ); - - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); - - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; } /*-----------------------------------------------------------*/ @@ -1055,7 +892,7 @@ static StackType_t uxStackBuffer[ configMINIMAL_STACK_SIZE ]; /* Create the task. xTaskCreateStatic() has two more parameters than the usual xTaskCreate() function. The first new parameter is a pointer to the pre-allocated stack. The second new parameter is a pointer to the - StaticTask_t structure that will hold the task's TCB. If either pointer is + StaticTask_t structure that will hold the task's TCB. If both pointers are passed as NULL then the respective object will be allocated dynamically as if xTaskCreate() had been called. */ xReturned = xTaskCreateStatic( @@ -1075,77 +912,6 @@ static StackType_t uxStackBuffer[ configMINIMAL_STACK_SIZE ]; xErrorOccurred = pdTRUE; } vTaskDelete( xCreatedTask ); - - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); - - /* Create and delete the task a few times again - testing both static and - dynamic allocation for the stack and TCB. */ - xReturned = xTaskCreateStatic( - prvStaticallyAllocatedTask, /* Function that implements the task. */ - "Static", /* Human readable name for the task. */ - configMINIMAL_STACK_SIZE, /* Task's stack size, in words (not bytes!). */ - NULL, /* Parameter to pass into the task. */ - staticTASK_PRIORITY + 1, /* The priority of the task. */ - &xCreatedTask, /* Handle of the task being created. */ - NULL, /* This time, dynamically allocate the stack. */ - &xTCBBuffer ); /* The variable that will hold that task's TCB. */ - - configASSERT( xReturned == pdPASS ); - if( xReturned != pdPASS ) - { - xErrorOccurred = pdTRUE; - } - vTaskDelete( xCreatedTask ); - - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; - - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); - - xReturned = xTaskCreateStatic( - prvStaticallyAllocatedTask, /* Function that implements the task. */ - "Static", /* Human readable name for the task. */ - configMINIMAL_STACK_SIZE, /* Task's stack size, in words (not bytes!). */ - NULL, /* Parameter to pass into the task. */ - staticTASK_PRIORITY - 1, /* The priority of the task. */ - &xCreatedTask, /* Handle of the task being created. */ - &( uxStackBuffer[ 0 ] ), /* The buffer to use as the task's stack. */ - NULL ); /* This time dynamically allocate the TCB. */ - - configASSERT( xReturned == pdPASS ); - if( xReturned != pdPASS ) - { - xErrorOccurred = pdTRUE; - } - vTaskDelete( xCreatedTask ); - - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); - - xReturned = xTaskCreateStatic( - prvStaticallyAllocatedTask, /* Function that implements the task. */ - "Static", /* Human readable name for the task. */ - configMINIMAL_STACK_SIZE, /* Task's stack size, in words (not bytes!). */ - NULL, /* Parameter to pass into the task. */ - staticTASK_PRIORITY, /* The priority of the task. */ - &xCreatedTask, /* Handle of the task being created. */ - NULL, /* This time dynamically allocate the stack and TCB. */ - NULL ); /* This time dynamically allocate the stack and TCB. */ - - configASSERT( xReturned == pdPASS ); - if( xReturned != pdPASS ) - { - xErrorOccurred = pdTRUE; - } - vTaskDelete( xCreatedTask ); - - /* Ensure lower priority tasks get CPU time. */ - vTaskDelay( prvGetNextDelayTime() ); - - /* Just to show the check task that this task is still executing. */ - uxCycleCounter++; } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Demo/Common/Minimal/TimerDemo.c b/FreeRTOS/Demo/Common/Minimal/TimerDemo.c index 46b8c03a4..c7b4c521c 100644 --- a/FreeRTOS/Demo/Common/Minimal/TimerDemo.c +++ b/FreeRTOS/Demo/Common/Minimal/TimerDemo.c @@ -285,18 +285,16 @@ TickType_t xTimer; for( xTimer = 0; xTimer < configTIMER_QUEUE_LENGTH; xTimer++ ) { - /* As the timer queue is not yet full, it should be possible to both create - and start a timer. These timers are being started before the scheduler has - been started, so their block times should get set to zero within the timer - API itself. */ + /* As the timer queue is not yet full, it should be possible to both + create and start a timer. These timers are being started before the + scheduler has been started, so their block times should get set to zero + within the timer API itself. */ xAutoReloadTimers[ xTimer ] = xTimerCreate( "FR Timer", /* Text name to facilitate debugging. The kernel does not use this itself. */ ( ( xTimer + ( TickType_t ) 1 ) * xBasePeriod ),/* The period for the timer. The plus 1 ensures a period of zero is not specified. */ pdTRUE, /* Auto-reload is set to true. */ ( void * ) xTimer, /* An identifier for the timer as all the auto reload timers use the same callback. */ prvAutoReloadTimerCallback ); /* The callback to be called when the timer expires. */ - configASSERT( strcmp( pcTimerGetTimerName( xAutoReloadTimers[ xTimer ] ), "FR Timer" ) == 0 ); - if( xAutoReloadTimers[ xTimer ] == NULL ) { xTestStatus = pdFAIL; @@ -304,6 +302,8 @@ TickType_t xTimer; } else { + configASSERT( strcmp( pcTimerGetTimerName( xAutoReloadTimers[ xTimer ] ), "FR Timer" ) == 0 ); + /* The scheduler has not yet started, so the block period of portMAX_DELAY should just get set to zero in xTimerStart(). Also, the timer queue is not yet full so xTimerStart() should return @@ -402,7 +402,7 @@ UBaseType_t uxOriginalPriority; in the Blocked state. */ uxOriginalPriority = uxTaskPriorityGet( NULL ); vTaskPrioritySet( NULL, ( configMAX_PRIORITIES - 1 ) ); - + /* Delaying for configTIMER_QUEUE_LENGTH * xBasePeriod ticks should allow all the auto reload timers to expire at least once. */ xBlockPeriod = ( ( TickType_t ) configTIMER_QUEUE_LENGTH ) * xBasePeriod; diff --git a/FreeRTOS/Demo/Common/Minimal/blocktim.c b/FreeRTOS/Demo/Common/Minimal/blocktim.c index 92a28c8eb..20d0783eb 100644 --- a/FreeRTOS/Demo/Common/Minimal/blocktim.c +++ b/FreeRTOS/Demo/Common/Minimal/blocktim.c @@ -134,19 +134,22 @@ static volatile UBaseType_t xRunIndicator; void vCreateBlockTimeTasks( void ) { /* Create the queue on which the two tasks block. */ - xTestQueue = xQueueCreate( bktQUEUE_LENGTH, sizeof( BaseType_t ) ); - - /* vQueueAddToRegistry() adds the queue to the queue registry, if one is - in use. The queue registry is provided as a means for kernel aware - debuggers to locate queues and has no purpose if a kernel aware debugger - is not being used. The call to vQueueAddToRegistry() will be removed - by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is - defined to be less than 1. */ - vQueueAddToRegistry( xTestQueue, "Block_Time_Queue" ); - - /* Create the two test tasks. */ - xTaskCreate( vPrimaryBlockTimeTestTask, "BTest1", configMINIMAL_STACK_SIZE, NULL, bktPRIMARY_PRIORITY, NULL ); - xTaskCreate( vSecondaryBlockTimeTestTask, "BTest2", configMINIMAL_STACK_SIZE, NULL, bktSECONDARY_PRIORITY, &xSecondary ); + xTestQueue = xQueueCreate( bktQUEUE_LENGTH, sizeof( BaseType_t ) ); + + if( xTestQueue != NULL ) + { + /* vQueueAddToRegistry() adds the queue to the queue registry, if one + is in use. The queue registry is provided as a means for kernel aware + debuggers to locate queues and has no purpose if a kernel aware + debugger is not being used. The call to vQueueAddToRegistry() will be + removed by the pre-processor if configQUEUE_REGISTRY_SIZE is not + defined or is defined to be less than 1. */ + vQueueAddToRegistry( xTestQueue, "Block_Time_Queue" ); + + /* Create the two test tasks. */ + xTaskCreate( vPrimaryBlockTimeTestTask, "BTest1", configMINIMAL_STACK_SIZE, NULL, bktPRIMARY_PRIORITY, NULL ); + xTaskCreate( vSecondaryBlockTimeTestTask, "BTest2", configMINIMAL_STACK_SIZE, NULL, bktSECONDARY_PRIORITY, &xSecondary ); + } } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Demo/Common/Minimal/countsem.c b/FreeRTOS/Demo/Common/Minimal/countsem.c index fb76218a2..81a72451e 100644 --- a/FreeRTOS/Demo/Common/Minimal/countsem.c +++ b/FreeRTOS/Demo/Common/Minimal/countsem.c @@ -159,19 +159,18 @@ void vStartCountingSemaphoreTasks( void ) xParameters[ 1 ].uxExpectedStartCount = 0; xParameters[ 1 ].uxLoopCounter = 0; - /* vQueueAddToRegistry() adds the semaphore to the registry, if one is - in use. The registry is provided as a means for kernel aware - debuggers to locate semaphores and has no purpose if a kernel aware debugger - is not being used. The call to vQueueAddToRegistry() will be removed - by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is - defined to be less than 1. */ - vQueueAddToRegistry( ( QueueHandle_t ) xParameters[ 0 ].xSemaphore, "Counting_Sem_1" ); - vQueueAddToRegistry( ( QueueHandle_t ) xParameters[ 1 ].xSemaphore, "Counting_Sem_2" ); - - /* Were the semaphores created? */ if( ( xParameters[ 0 ].xSemaphore != NULL ) || ( xParameters[ 1 ].xSemaphore != NULL ) ) { + /* vQueueAddToRegistry() adds the semaphore to the registry, if one is + in use. The registry is provided as a means for kernel aware + debuggers to locate semaphores and has no purpose if a kernel aware + debugger is not being used. The call to vQueueAddToRegistry() will be + removed by the pre-processor if configQUEUE_REGISTRY_SIZE is not + defined or is defined to be less than 1. */ + vQueueAddToRegistry( ( QueueHandle_t ) xParameters[ 0 ].xSemaphore, "Counting_Sem_1" ); + vQueueAddToRegistry( ( QueueHandle_t ) xParameters[ 1 ].xSemaphore, "Counting_Sem_2" ); + /* Create the demo tasks, passing in the semaphore to use as the parameter. */ xTaskCreate( prvCountingSemaphoreTask, "CNT1", configMINIMAL_STACK_SIZE, ( void * ) &( xParameters[ 0 ] ), tskIDLE_PRIORITY, NULL ); xTaskCreate( prvCountingSemaphoreTask, "CNT2", configMINIMAL_STACK_SIZE, ( void * ) &( xParameters[ 1 ] ), tskIDLE_PRIORITY, NULL ); diff --git a/FreeRTOS/Demo/Common/Minimal/death.c b/FreeRTOS/Demo/Common/Minimal/death.c index 03558130c..d343b42fd 100644 --- a/FreeRTOS/Demo/Common/Minimal/death.c +++ b/FreeRTOS/Demo/Common/Minimal/death.c @@ -129,14 +129,7 @@ TaskHandle_t xCreatedTask; void vCreateSuicidalTasks( UBaseType_t uxPriority ) { -UBaseType_t *puxPriority; - - /* Create the Creator tasks - passing in as a parameter the priority at which - the suicidal tasks should be created. */ - puxPriority = ( UBaseType_t * ) pvPortMalloc( sizeof( UBaseType_t ) ); - *puxPriority = uxPriority; - - xTaskCreate( vCreateTasks, "CREATOR", deathSTACK_SIZE, ( void * ) puxPriority, uxPriority, NULL ); + xTaskCreate( vCreateTasks, "CREATOR", deathSTACK_SIZE, ( void * ) NULL, uxPriority, NULL ); /* Record the number of tasks that are running now so we know if any of the suicidal tasks have failed to be killed. */ @@ -206,8 +199,10 @@ static portTASK_FUNCTION( vCreateTasks, pvParameters ) const TickType_t xDelay = pdMS_TO_TICKS( ( TickType_t ) 1000 ); UBaseType_t uxPriority; - uxPriority = *( UBaseType_t * ) pvParameters; - vPortFree( pvParameters ); + /* Remove compiler warning about unused parameter. */ + ( void ) pvParameters; + + uxPriority = uxTaskPriorityGet( NULL ); for( ;; ) { diff --git a/FreeRTOS/Demo/Common/Minimal/dynamic.c b/FreeRTOS/Demo/Common/Minimal/dynamic.c index 25baef3af..8180c89f7 100644 --- a/FreeRTOS/Demo/Common/Minimal/dynamic.c +++ b/FreeRTOS/Demo/Common/Minimal/dynamic.c @@ -189,19 +189,22 @@ void vStartDynamicPriorityTasks( void ) { xSuspendedTestQueue = xQueueCreate( priSUSPENDED_QUEUE_LENGTH, sizeof( uint32_t ) ); - /* vQueueAddToRegistry() adds the queue to the queue registry, if one is - in use. The queue registry is provided as a means for kernel aware - debuggers to locate queues and has no purpose if a kernel aware debugger - is not being used. The call to vQueueAddToRegistry() will be removed - by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is - defined to be less than 1. */ - vQueueAddToRegistry( xSuspendedTestQueue, "Suspended_Test_Queue" ); - - xTaskCreate( vContinuousIncrementTask, "CNT_INC", priSTACK_SIZE, ( void * ) &ulCounter, tskIDLE_PRIORITY, &xContinuousIncrementHandle ); - xTaskCreate( vLimitedIncrementTask, "LIM_INC", priSTACK_SIZE, ( void * ) &ulCounter, tskIDLE_PRIORITY + 1, &xLimitedIncrementHandle ); - xTaskCreate( vCounterControlTask, "C_CTRL", priSTACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); - xTaskCreate( vQueueSendWhenSuspendedTask, "SUSP_TX", priSTACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); - xTaskCreate( vQueueReceiveWhenSuspendedTask, "SUSP_RX", priSTACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); + if( xSuspendedTestQueue != NULL ) + { + /* vQueueAddToRegistry() adds the queue to the queue registry, if one is + in use. The queue registry is provided as a means for kernel aware + debuggers to locate queues and has no purpose if a kernel aware debugger + is not being used. The call to vQueueAddToRegistry() will be removed + by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is + defined to be less than 1. */ + vQueueAddToRegistry( xSuspendedTestQueue, "Suspended_Test_Queue" ); + + xTaskCreate( vContinuousIncrementTask, "CNT_INC", priSTACK_SIZE, ( void * ) &ulCounter, tskIDLE_PRIORITY, &xContinuousIncrementHandle ); + xTaskCreate( vLimitedIncrementTask, "LIM_INC", priSTACK_SIZE, ( void * ) &ulCounter, tskIDLE_PRIORITY + 1, &xLimitedIncrementHandle ); + xTaskCreate( vCounterControlTask, "C_CTRL", priSTACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); + xTaskCreate( vQueueSendWhenSuspendedTask, "SUSP_TX", priSTACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); + xTaskCreate( vQueueReceiveWhenSuspendedTask, "SUSP_RX", priSTACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); + } } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Demo/Common/Minimal/recmutex.c b/FreeRTOS/Demo/Common/Minimal/recmutex.c index 9e3fcac2e..e5926e217 100644 --- a/FreeRTOS/Demo/Common/Minimal/recmutex.c +++ b/FreeRTOS/Demo/Common/Minimal/recmutex.c @@ -151,20 +151,19 @@ void vStartRecursiveMutexTasks( void ) xMutex = xSemaphoreCreateRecursiveMutex(); - /* vQueueAddToRegistry() adds the mutex to the registry, if one is - in use. The registry is provided as a means for kernel aware - debuggers to locate mutex and has no purpose if a kernel aware debugger - is not being used. The call to vQueueAddToRegistry() will be removed - by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is - defined to be less than 1. */ - vQueueAddToRegistry( ( QueueHandle_t ) xMutex, "Recursive_Mutex" ); - - if( xMutex != NULL ) { + /* vQueueAddToRegistry() adds the mutex to the registry, if one is + in use. The registry is provided as a means for kernel aware + debuggers to locate mutex and has no purpose if a kernel aware debugger + is not being used. The call to vQueueAddToRegistry() will be removed + by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is + defined to be less than 1. */ + vQueueAddToRegistry( ( QueueHandle_t ) xMutex, "Recursive_Mutex" ); + xTaskCreate( prvRecursiveMutexControllingTask, "Rec1", configMINIMAL_STACK_SIZE, NULL, recmuCONTROLLING_TASK_PRIORITY, &xControllingTaskHandle ); - xTaskCreate( prvRecursiveMutexBlockingTask, "Rec2", configMINIMAL_STACK_SIZE, NULL, recmuBLOCKING_TASK_PRIORITY, &xBlockingTaskHandle ); - xTaskCreate( prvRecursiveMutexPollingTask, "Rec3", configMINIMAL_STACK_SIZE, NULL, recmuPOLLING_TASK_PRIORITY, NULL ); + xTaskCreate( prvRecursiveMutexBlockingTask, "Rec2", configMINIMAL_STACK_SIZE, NULL, recmuBLOCKING_TASK_PRIORITY, &xBlockingTaskHandle ); + xTaskCreate( prvRecursiveMutexPollingTask, "Rec3", configMINIMAL_STACK_SIZE, NULL, recmuPOLLING_TASK_PRIORITY, NULL ); } } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Demo/Common/Minimal/semtest.c b/FreeRTOS/Demo/Common/Minimal/semtest.c index fb0fa6c86..7a1f330f4 100644 --- a/FreeRTOS/Demo/Common/Minimal/semtest.c +++ b/FreeRTOS/Demo/Common/Minimal/semtest.c @@ -68,24 +68,24 @@ */ /* - * Creates two sets of two tasks. The tasks within a set share a variable, access + * Creates two sets of two tasks. The tasks within a set share a variable, access * to which is guarded by a semaphore. - * - * Each task starts by attempting to obtain the semaphore. On obtaining a - * semaphore a task checks to ensure that the guarded variable has an expected - * value. It then clears the variable to zero before counting it back up to the - * expected value in increments of 1. After each increment the variable is checked - * to ensure it contains the value to which it was just set. When the starting - * value is again reached the task releases the semaphore giving the other task in - * the set a chance to do exactly the same thing. The starting value is high + * + * Each task starts by attempting to obtain the semaphore. On obtaining a + * semaphore a task checks to ensure that the guarded variable has an expected + * value. It then clears the variable to zero before counting it back up to the + * expected value in increments of 1. After each increment the variable is checked + * to ensure it contains the value to which it was just set. When the starting + * value is again reached the task releases the semaphore giving the other task in + * the set a chance to do exactly the same thing. The starting value is high * enough to ensure that a tick is likely to occur during the incrementing loop. * - * An error is flagged if at any time during the process a shared variable is - * found to have a value other than that expected. Such an occurrence would - * suggest an error in the mutual exclusion mechanism by which access to the + * An error is flagged if at any time during the process a shared variable is + * found to have a value other than that expected. Such an occurrence would + * suggest an error in the mutual exclusion mechanism by which access to the * variable is restricted. * - * The first set of two tasks poll their semaphore. The second set use blocking + * The first set of two tasks poll their semaphore. The second set use blocking * calls. * */ @@ -139,11 +139,12 @@ const TickType_t xBlockTime = ( TickType_t ) 100; if( pxFirstSemaphoreParameters != NULL ) { /* Create the semaphore used by the first two tasks. */ - pxFirstSemaphoreParameters->xSemaphore = xSemaphoreCreateBinary(); - xSemaphoreGive( pxFirstSemaphoreParameters->xSemaphore ); + pxFirstSemaphoreParameters->xSemaphore = xSemaphoreCreateBinary(); if( pxFirstSemaphoreParameters->xSemaphore != NULL ) { + xSemaphoreGive( pxFirstSemaphoreParameters->xSemaphore ); + /* Create the variable which is to be shared by the first two tasks. */ pxFirstSemaphoreParameters->pulSharedVariable = ( uint32_t * ) pvPortMalloc( sizeof( uint32_t ) ); @@ -156,36 +157,44 @@ const TickType_t xBlockTime = ( TickType_t ) 100; /* Spawn the first two tasks. As they poll they operate at the idle priority. */ xTaskCreate( prvSemaphoreTest, "PolSEM1", semtstSTACK_SIZE, ( void * ) pxFirstSemaphoreParameters, tskIDLE_PRIORITY, ( TaskHandle_t * ) NULL ); xTaskCreate( prvSemaphoreTest, "PolSEM2", semtstSTACK_SIZE, ( void * ) pxFirstSemaphoreParameters, tskIDLE_PRIORITY, ( TaskHandle_t * ) NULL ); + + /* vQueueAddToRegistry() adds the semaphore to the registry, if one + is in use. The registry is provided as a means for kernel aware + debuggers to locate semaphores and has no purpose if a kernel aware + debugger is not being used. The call to vQueueAddToRegistry() will + be removed by the pre-processor if configQUEUE_REGISTRY_SIZE is not + defined or is defined to be less than 1. */ + vQueueAddToRegistry( ( QueueHandle_t ) pxFirstSemaphoreParameters->xSemaphore, "Counting_Sem_1" ); } } - /* Do exactly the same to create the second set of tasks, only this time + /* Do exactly the same to create the second set of tasks, only this time provide a block time for the semaphore calls. */ pxSecondSemaphoreParameters = ( xSemaphoreParameters * ) pvPortMalloc( sizeof( xSemaphoreParameters ) ); if( pxSecondSemaphoreParameters != NULL ) { - pxSecondSemaphoreParameters->xSemaphore = xSemaphoreCreateBinary(); - xSemaphoreGive( pxSecondSemaphoreParameters->xSemaphore ); + pxSecondSemaphoreParameters->xSemaphore = xSemaphoreCreateBinary(); if( pxSecondSemaphoreParameters->xSemaphore != NULL ) { + xSemaphoreGive( pxSecondSemaphoreParameters->xSemaphore ); + pxSecondSemaphoreParameters->pulSharedVariable = ( uint32_t * ) pvPortMalloc( sizeof( uint32_t ) ); *( pxSecondSemaphoreParameters->pulSharedVariable ) = semtstBLOCKING_EXPECTED_VALUE; pxSecondSemaphoreParameters->xBlockTime = xBlockTime / portTICK_PERIOD_MS; xTaskCreate( prvSemaphoreTest, "BlkSEM1", semtstSTACK_SIZE, ( void * ) pxSecondSemaphoreParameters, uxPriority, ( TaskHandle_t * ) NULL ); xTaskCreate( prvSemaphoreTest, "BlkSEM2", semtstSTACK_SIZE, ( void * ) pxSecondSemaphoreParameters, uxPriority, ( TaskHandle_t * ) NULL ); + + /* vQueueAddToRegistry() adds the semaphore to the registry, if one + is in use. The registry is provided as a means for kernel aware + debuggers to locate semaphores and has no purpose if a kernel aware + debugger is not being used. The call to vQueueAddToRegistry() will + be removed by the pre-processor if configQUEUE_REGISTRY_SIZE is not + defined or is defined to be less than 1. */ + vQueueAddToRegistry( ( QueueHandle_t ) pxSecondSemaphoreParameters->xSemaphore, "Counting_Sem_2" ); } } - - /* vQueueAddToRegistry() adds the semaphore to the registry, if one is - in use. The registry is provided as a means for kernel aware - debuggers to locate semaphores and has no purpose if a kernel aware debugger - is not being used. The call to vQueueAddToRegistry() will be removed - by the pre-processor if configQUEUE_REGISTRY_SIZE is not defined or is - defined to be less than 1. */ - vQueueAddToRegistry( ( QueueHandle_t ) pxFirstSemaphoreParameters->xSemaphore, "Counting_Sem_1" ); - vQueueAddToRegistry( ( QueueHandle_t ) pxSecondSemaphoreParameters->xSemaphore, "Counting_Sem_2" ); } /*-----------------------------------------------------------*/ @@ -196,14 +205,14 @@ volatile uint32_t *pulSharedVariable, ulExpectedValue; uint32_t ulCounter; short sError = pdFALSE, sCheckVariableToUse; - /* See which check variable to use. sNextCheckVariable is not semaphore + /* See which check variable to use. sNextCheckVariable is not semaphore protected! */ portENTER_CRITICAL(); sCheckVariableToUse = sNextCheckVariable; sNextCheckVariable++; portEXIT_CRITICAL(); - /* A structure is passed in as the parameter. This contains the shared + /* A structure is passed in as the parameter. This contains the shared variable being guarded. */ pxParameters = ( xSemaphoreParameters * ) pvParameters; pulSharedVariable = pxParameters->pulSharedVariable; @@ -231,7 +240,7 @@ short sError = pdFALSE, sCheckVariableToUse; { sError = pdTRUE; } - + /* Clear the variable, then count it back up to the expected value before releasing the semaphore. Would expect a context switch or two during this time. */ diff --git a/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/FreeRTOSConfig.h b/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/FreeRTOSConfig.h new file mode 100644 index 000000000..9e478bf3c --- /dev/null +++ b/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/FreeRTOSConfig.h @@ -0,0 +1,170 @@ +/* + FreeRTOS V9.0.0rc1 - Copyright (C) 2016 Real Time Engineers Ltd. + All rights reserved + + VISIT http://www.FreeRTOS.org TO ENSURE YOU ARE USING THE LATEST VERSION. + + This file is part of the FreeRTOS distribution. + + FreeRTOS is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License (version 2) as published by the + Free Software Foundation >>>> AND MODIFIED BY <<<< the FreeRTOS exception. + + *************************************************************************** + >>! NOTE: The modification to the GPL is included to allow you to !<< + >>! distribute a combined work that includes FreeRTOS without being !<< + >>! obliged to provide the source code for proprietary components !<< + >>! outside of the FreeRTOS kernel. !<< + *************************************************************************** + + FreeRTOS 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. Full license text is available on the following + link: http://www.freertos.org/a00114.html + + *************************************************************************** + * * + * FreeRTOS provides completely free yet professionally developed, * + * robust, strictly quality controlled, supported, and cross * + * platform software that is more than just the market leader, it * + * is the industry's de facto standard. * + * * + * Help yourself get started quickly while simultaneously helping * + * to support the FreeRTOS project by purchasing a FreeRTOS * + * tutorial book, reference manual, or both: * + * http://www.FreeRTOS.org/Documentation * + * * + *************************************************************************** + + http://www.FreeRTOS.org/FAQHelp.html - Having a problem? Start by reading + the FAQ page "My application does not run, what could be wrong?". Have you + defined configASSERT()? + + http://www.FreeRTOS.org/support - In return for receiving this top quality + embedded software for free we request you assist our global community by + participating in the support forum. + + http://www.FreeRTOS.org/training - Investing in training allows your team to + be as productive as possible as early as possible. Now you can receive + FreeRTOS training directly from Richard Barry, CEO of Real Time Engineers + Ltd, and the world's leading authority on the world's leading RTOS. + + http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products, + including FreeRTOS+Trace - an indispensable productivity tool, a DOS + compatible FAT file system, and our tiny thread aware UDP/IP stack. + + http://www.FreeRTOS.org/labs - Where new FreeRTOS products go to incubate. + Come and try FreeRTOS+TCP, our new open source TCP/IP stack for FreeRTOS. + + http://www.OpenRTOS.com - Real Time Engineers ltd. license FreeRTOS to High + Integrity Systems ltd. to sell under the OpenRTOS brand. Low cost OpenRTOS + licenses offer ticketed support, indemnification and commercial middleware. + + http://www.SafeRTOS.com - High Integrity Systems also provide a safety + engineered and independently SIL3 certified version for use in safety and + mission critical applications that require provable dependability. + + 1 tab == 4 spaces! +*/ + + +#ifndef FREERTOS_CONFIG_H +#define FREERTOS_CONFIG_H + +/*----------------------------------------------------------- + * Application specific definitions. + * + * These definitions should be adjusted for your particular hardware and + * application requirements. + * + * THESE PARAMETERS ARE DESCRIBED WITHIN THE 'CONFIGURATION' SECTION OF THE + * FreeRTOS API DOCUMENTATION AVAILABLE ON THE FreeRTOS.org WEB SITE. See + * http://www.freertos.org/a00110.html + *----------------------------------------------------------*/ + +/* Setting configSUPPORT_STATIC_ALLOCATION to 1 allows RTOS objects to be +created using only application supplied memory. No dynamic memory allocation +will be performed. */ +#define configSUPPORT_STATIC_ALLOCATION 1 + +/* Setting configSUPPORT_DYNAMIC_ALLOCATION to 0 results in all calls to +pvPortMalloc() returning NULL, and all calls to vPortFree() being ignored. +Therefore the application can be built without providing an implementation of +either of these functions (so none of the normal heap_n.c files described on +http://www.freertos.org/a00111.html are required). Note that +configTOTAL_HEAP_SIZE is not defined. */ +#define configSUPPORT_DYNAMIC_ALLOCATION 0 + +/* Other constants as described on http://www.freertos.org/a00110.html */ +#define configUSE_PREEMPTION 1 +#define configUSE_PORT_OPTIMISED_TASK_SELECTION 1 +#define configUSE_IDLE_HOOK 0 +#define configUSE_TICK_HOOK 0 +#define configUSE_DAEMON_TASK_STARTUP_HOOK 0 +#define configTICK_RATE_HZ ( 1000 ) /* In this non-real time simulated environment the tick frequency has to be at least a multiple of the Win32 tick frequency, and therefore very slow. */ +#define configMINIMAL_STACK_SIZE ( ( unsigned short ) 50 ) /* In this simulated case, the stack only has to hold one small structure as the real stack is part of the win32 thread. */ +#define configMAX_TASK_NAME_LEN ( 12 ) +#define configUSE_TRACE_FACILITY 1 +#define configUSE_16_BIT_TICKS 0 +#define configIDLE_SHOULD_YIELD 1 +#define configUSE_MUTEXES 1 +#define configCHECK_FOR_STACK_OVERFLOW 0 +#define configUSE_RECURSIVE_MUTEXES 1 +#define configQUEUE_REGISTRY_SIZE 20 +#define configUSE_MALLOC_FAILED_HOOK 0 /* pvPortMalloc() is not used. */ +#define configUSE_APPLICATION_TASK_TAG 1 +#define configUSE_COUNTING_SEMAPHORES 1 +#define configUSE_ALTERNATIVE_API 0 +#define configUSE_QUEUE_SETS 1 +#define configUSE_TASK_NOTIFICATIONS 1 + +/* Software timer related configuration options. */ +#define configUSE_TIMERS 1 +#define configTIMER_TASK_PRIORITY ( configMAX_PRIORITIES - 1 ) +#define configTIMER_QUEUE_LENGTH 20 +#define configTIMER_TASK_STACK_DEPTH ( configMINIMAL_STACK_SIZE * 2 ) + +#define configMAX_PRIORITIES ( 7 ) + +/* Run time stats gathering configuration options. */ +#define configGENERATE_RUN_TIME_STATS 0 +#define portCONFIGURE_TIMER_FOR_RUN_TIME_STATS() +#define portGET_RUN_TIME_COUNTER_VALUE() + +/* Co-routine related configuration options. */ +#define configUSE_CO_ROUTINES 0 + +/* This demo makes use of one or more example stats formatting functions. These +format the raw data provided by the uxTaskGetSystemState() function in to human +readable ASCII form. See the notes in the implementation of vTaskList() within +FreeRTOS/Source/tasks.c for limitations. */ +#define configUSE_STATS_FORMATTING_FUNCTIONS 0 + +/* Set the following definitions to 1 to include the API function, or zero +to exclude the API function. In most cases the linker will remove unused +functions anyway. */ +#define INCLUDE_vTaskPrioritySet 1 +#define INCLUDE_uxTaskPriorityGet 1 +#define INCLUDE_vTaskDelete 1 +#define INCLUDE_vTaskCleanUpResources 0 +#define INCLUDE_vTaskSuspend 1 +#define INCLUDE_vTaskDelayUntil 1 +#define INCLUDE_vTaskDelay 1 +#define INCLUDE_uxTaskGetStackHighWaterMark 1 +#define INCLUDE_xTaskGetSchedulerState 1 +#define INCLUDE_xTimerGetTimerDaemonTaskHandle 1 +#define INCLUDE_xTaskGetIdleTaskHandle 1 +#define INCLUDE_pcTaskGetTaskName 1 +#define INCLUDE_xTaskGetTaskHandle 1 +#define INCLUDE_eTaskGetState 1 +#define INCLUDE_xSemaphoreGetMutexHolder 1 +#define INCLUDE_xTimerPendFunctionCall 1 +#define INCLUDE_xTaskAbortDelay 1 + +/* It is a good idea to define configASSERT() while developing. configASSERT() +uses the same semantics as the standard C assert() macro. */ +extern void vAssertCalled( unsigned long ulLine, const char * const pcFileName ); +#define configASSERT( x ) if( ( x ) == 0 ) vAssertCalled( __LINE__, __FILE__ ) + + +#endif /* FREERTOS_CONFIG_H */ diff --git a/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/WIN32.sln b/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/WIN32.sln new file mode 100644 index 000000000..6afed9a6f --- /dev/null +++ b/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/WIN32.sln @@ -0,0 +1,25 @@ + +Microsoft Visual Studio Solution File, Format Version 12.00 +# Visual Studio 14 +VisualStudioVersion = 14.0.24720.0 +MinimumVisualStudioVersion = 10.0.40219.1 +Project("{8BC9CEB8-8B4A-11D0-8D11-00A0C91BC942}") = "RTOSDemo", "WIN32.vcxproj", "{C686325E-3261-42F7-AEB1-DDE5280E1CEB}" +EndProject +Global + GlobalSection(SolutionConfigurationPlatforms) = preSolution + Debug|Win32 = Debug|Win32 + Optimised|Win32 = Optimised|Win32 + Release|Win32 = Release|Win32 + EndGlobalSection + GlobalSection(ProjectConfigurationPlatforms) = postSolution + {C686325E-3261-42F7-AEB1-DDE5280E1CEB}.Debug|Win32.ActiveCfg = Debug|Win32 + {C686325E-3261-42F7-AEB1-DDE5280E1CEB}.Debug|Win32.Build.0 = Debug|Win32 + {C686325E-3261-42F7-AEB1-DDE5280E1CEB}.Optimised|Win32.ActiveCfg = Optimised|Win32 + {C686325E-3261-42F7-AEB1-DDE5280E1CEB}.Optimised|Win32.Build.0 = Optimised|Win32 + {C686325E-3261-42F7-AEB1-DDE5280E1CEB}.Release|Win32.ActiveCfg = Release|Win32 + {C686325E-3261-42F7-AEB1-DDE5280E1CEB}.Release|Win32.Build.0 = Release|Win32 + EndGlobalSection + GlobalSection(SolutionProperties) = preSolution + HideSolutionNode = FALSE + EndGlobalSection +EndGlobal diff --git a/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/WIN32.vcxproj b/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/WIN32.vcxproj new file mode 100644 index 000000000..1a0b3d069 --- /dev/null +++ b/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/WIN32.vcxproj @@ -0,0 +1,246 @@ + + + + + Debug + Win32 + + + Optimised + Win32 + + + Release + Win32 + + + + {C686325E-3261-42F7-AEB1-DDE5280E1CEB} + RTOSDemo + + + + Application + false + MultiByte + v140 + + + Application + false + MultiByte + v140 + + + Application + false + MultiByte + v140 + + + + + + + + + + + + + + + + + + + <_ProjectFileVersion>10.0.30319.1 + .\Debug\ + .\Debug\ + .\Debug\ + .\Debug\ + true + true + .\Release\ + .\Release\ + false + + + + .\Debug/WIN32.tlb + + + + + Disabled + ..\..\Source\include;..\..\Source\portable\MSVC-MingW;..\Common\Include;..\..\..\FreeRTOS-Plus\Source\FreeRTOS-Plus-Trace\Include;.\Trace_Recorder_Configuration;.;%(AdditionalIncludeDirectories) + WIN32;_DEBUG;_CONSOLE;_WIN32_WINNT=0x0500;WINVER=0x400;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) + true + EnableFastChecks + MultiThreadedDebug + .\Debug/WIN32.pch + .\Debug/ + .\Debug/ + .\Debug/ + Level4 + true + EditAndContinue + false + /wd4210 %(AdditionalOptions) + + + _DEBUG;%(PreprocessorDefinitions) + 0x0c09 + + + .\Debug/RTOSDemo.exe + true + true + .\Debug/WIN32.pdb + Console + MachineX86 + %(AdditionalDependencies) + false + + + true + .\Debug/WIN32.bsc + + + + + .\Debug/WIN32.tlb + + + + + Full + ..\..\Source\include;..\..\Source\portable\MSVC-MingW;..\Common\Include;..\..\..\FreeRTOS-Plus\Source\FreeRTOS-Plus-Trace\Include;.\Trace_Recorder_Configuration;.;%(AdditionalIncludeDirectories) + WIN32;_DEBUG;_CONSOLE;_WIN32_WINNT=0x0500;WINVER=0x400;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) + true + Default + MultiThreadedDebug + .\Debug/WIN32.pch + .\Debug/ + .\Debug/ + .\Debug/ + Level4 + true + EditAndContinue + false + /wd4210 %(AdditionalOptions) + + + _DEBUG;%(PreprocessorDefinitions) + 0x0c09 + + + .\Debug/RTOSDemo.exe + true + true + .\Debug/WIN32.pdb + Console + MachineX86 + %(AdditionalDependencies) + false + + + true + .\Debug/WIN32.bsc + + + + + .\Release/WIN32.tlb + + + + + MaxSpeed + OnlyExplicitInline + WIN32;NDEBUG;_CONSOLE;_CRT_SECURE_NO_WARNINGS;%(PreprocessorDefinitions) + true + MultiThreaded + true + .\Release/WIN32.pch + .\Release/ + .\Release/ + .\Release/ + Level3 + true + ..\..\Source\include;..\..\Source\portable\MSVC-MingW;..\Common\Include;.;%(AdditionalIncludeDirectories) + + + NDEBUG;%(PreprocessorDefinitions) + 0x0c09 + + + .\Release/RTOSDemo.exe + true + .\Release/WIN32.pdb + Console + MachineX86 + + + true + .\Release/WIN32.bsc + + + + + + + + %(AdditionalIncludeDirectories) + %(AdditionalIncludeDirectories) + %(PreprocessorDefinitions) + %(PreprocessorDefinitions) + %(PreprocessorDefinitions) + + + %(AdditionalIncludeDirectories) + %(AdditionalIncludeDirectories) + %(PreprocessorDefinitions) + %(PreprocessorDefinitions) + %(PreprocessorDefinitions) + + + %(AdditionalIncludeDirectories) + %(AdditionalIncludeDirectories) + %(PreprocessorDefinitions) + %(PreprocessorDefinitions) + %(PreprocessorDefinitions) + + + %(AdditionalIncludeDirectories) + %(AdditionalIncludeDirectories) + %(PreprocessorDefinitions) + %(PreprocessorDefinitions) + %(PreprocessorDefinitions) + + + %(AdditionalIncludeDirectories) + %(AdditionalIncludeDirectories) + %(PreprocessorDefinitions) + %(PreprocessorDefinitions) + %(PreprocessorDefinitions) + + + + + + + + + + + + + + + + + + + + \ No newline at end of file diff --git a/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/WIN32.vcxproj.filters b/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/WIN32.vcxproj.filters new file mode 100644 index 000000000..3c3f9f3cc --- /dev/null +++ b/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/WIN32.vcxproj.filters @@ -0,0 +1,80 @@ + + + + + {38712199-cebf-4124-bf15-398f7c3419ea} + ico;cur;bmp;dlg;rc2;rct;bin;rgs;gif;jpg;jpeg;jpe + + + {af3445a1-4908-4170-89ed-39345d90d30c} + + + {f32be356-4763-4cae-9020-974a2638cb08} + *.c + + + {a60060e3-3949-4f60-b025-cb84164ae9ed} + + + {88f409e6-d396-4ac5-94bd-7a99c914be46} + + + + + FreeRTOS Source\Source + + + FreeRTOS Source\Source + + + FreeRTOS Source\Source + + + FreeRTOS Source\Source\Portable + + + FreeRTOS Source\Source + + + FreeRTOS Source\Source + + + + + + + FreeRTOS Source\Include + + + FreeRTOS Source\Include + + + FreeRTOS Source\Include + + + FreeRTOS Source\Include + + + FreeRTOS Source\Include + + + FreeRTOS Source\Include + + + FreeRTOS Source\Include + + + FreeRTOS Source\Include + + + FreeRTOS Source\Include + + + FreeRTOS Source\Include + + + FreeRTOS Source\Include + + + + \ No newline at end of file diff --git a/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/main.c b/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/main.c new file mode 100644 index 000000000..c3a7d1be3 --- /dev/null +++ b/FreeRTOS/Demo/WIN32-MSVC-Static-Allocation-Only/main.c @@ -0,0 +1,275 @@ +/* + FreeRTOS V9.0.0rc1 - Copyright (C) 2016 Real Time Engineers Ltd. + All rights reserved + + VISIT http://www.FreeRTOS.org TO ENSURE YOU ARE USING THE LATEST VERSION. + + This file is part of the FreeRTOS distribution. + + FreeRTOS is free software; you can redistribute it and/or modify it under + the terms of the GNU General Public License (version 2) as published by the + Free Software Foundation >>>> AND MODIFIED BY <<<< the FreeRTOS exception. + + *************************************************************************** + >>! NOTE: The modification to the GPL is included to allow you to !<< + >>! distribute a combined work that includes FreeRTOS without being !<< + >>! obliged to provide the source code for proprietary components !<< + >>! outside of the FreeRTOS kernel. !<< + *************************************************************************** + + FreeRTOS 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. Full license text is available on the following + link: http://www.freertos.org/a00114.html + + *************************************************************************** + * * + * FreeRTOS provides completely free yet professionally developed, * + * robust, strictly quality controlled, supported, and cross * + * platform software that is more than just the market leader, it * + * is the industry's de facto standard. * + * * + * Help yourself get started quickly while simultaneously helping * + * to support the FreeRTOS project by purchasing a FreeRTOS * + * tutorial book, reference manual, or both: * + * http://www.FreeRTOS.org/Documentation * + * * + *************************************************************************** + + http://www.FreeRTOS.org/FAQHelp.html - Having a problem? Start by reading + the FAQ page "My application does not run, what could be wrong?". Have you + defined configASSERT()? + + http://www.FreeRTOS.org/support - In return for receiving this top quality + embedded software for free we request you assist our global community by + participating in the support forum. + + http://www.FreeRTOS.org/training - Investing in training allows your team to + be as productive as possible as early as possible. Now you can receive + FreeRTOS training directly from Richard Barry, CEO of Real Time Engineers + Ltd, and the world's leading authority on the world's leading RTOS. + + http://www.FreeRTOS.org/plus - A selection of FreeRTOS ecosystem products, + including FreeRTOS+Trace - an indispensable productivity tool, a DOS + compatible FAT file system, and our tiny thread aware UDP/IP stack. + + http://www.FreeRTOS.org/labs - Where new FreeRTOS products go to incubate. + Come and try FreeRTOS+TCP, our new open source TCP/IP stack for FreeRTOS. + + http://www.OpenRTOS.com - Real Time Engineers ltd. license FreeRTOS to High + Integrity Systems ltd. to sell under the OpenRTOS brand. Low cost OpenRTOS + licenses offer ticketed support, indemnification and commercial middleware. + + http://www.SafeRTOS.com - High Integrity Systems also provide a safety + engineered and independently SIL3 certified version for use in safety and + mission critical applications that require provable dependability. + + 1 tab == 4 spaces! +*/ + +/****************************************************************************** + * + * This project is provided as an example of how to create a FreeRTOS project + * that does not need a heap. configSUPPORT_STATIC_ALLOCATION is set to 1 to + * allow RTOS objects to be created using statically allocated RAM, and + * configSUPPORT_DYNAMIC_ALLOCATION is set to 0 to remove any build dependency + * on the FreeRTOS heap. When configSUPPORT_DYNAMIC_ALLOCATION is set to 0 + * pvPortMalloc() just equates to NULL, and calls to vPortFree() have no + * effect. See: + * + * http://www.freertos.org/a00111.html and + * http://www.freertos.org/Static_Vs_Dynamic_Memory_Allocation.html + * + ******************************************************************************* + */ + +/* Standard includes. */ +#include +#include +#include + +/* FreeRTOS kernel includes. */ +#include "FreeRTOS.h" +#include "task.h" + +/* Standard demo includes. */ +#include "StaticAllocation.h" + + +/*-----------------------------------------------------------*/ + +/* + * Prototypes for the standard FreeRTOS stack overflow hook (callback) + * function. http://www.freertos.org/Stacks-and-stack-overflow-checking.html + */ +void vApplicationStackOverflowHook( TaskHandle_t pxTask, char *pcTaskName ); + +/* + * This demo has configSUPPORT_STATIC_ALLOCATION set to 1 so the following + * application callback function must be provided to supply the RAM that will + * get used for the Idle task data structures and stack. + */ +void vApplicationGetIdleTaskMemory( StaticTask_t **ppxIdleTaskTCBBuffer, StackType_t **ppxIdleTaskStackBuffer, uint16_t *pusIdleTaskStackSize ); + +/* +* This demo has configSUPPORT_STATIC_ALLOCATION set to 1 and configUSE_TIMERS +* set to 1 so the following application callback function must be provided to +* supply the RAM that will get used for the Timer task data structures and +* stack. +*/ +void vApplicationGetTimerTaskMemory( StaticTask_t **ppxTimerTaskTCBBuffer, StackType_t **ppxTimerTaskStackBuffer, uint16_t *pusTimerTaskStackSize ); + +/* This demo only uses the standard demo tasks that use statically allocated +RAM. A 'check' task is also created to periodically inspect the demo tasks to +ensure they are still running, and that no errors have been detected. */ +static void prvStartCheckTask( void ); +static void prvCheckTask( void *pvParameters ); + +/*-----------------------------------------------------------*/ + +int main( void ) +{ + /* This demo has configSUPPORT_STATIC_ALLOCATION set to 1 and + configSUPPORT_DYNAMIC_ALLOCATION set to 0, so the only standard temo tasks + created are the ones that only use static allocation. This allow the + application to be built without including a FreeRTOS heap file (without one + of the heap files described on http://www.freertos.org/a00111.html */ + vStartStaticallyAllocatedTasks(); + + /* Start a task that periodically inspects the tasks created by + vStartStaticallyAllocatedTasks() to ensure they are still running, and not + reporting any errors. */ + prvStartCheckTask(); + + /* Start the scheduler so the demo tasks start to execute. */ + vTaskStartScheduler(); + + /* vTaskStartScheduler() would only return if RAM required by the Idle and + Timer tasks could not be allocated. As this demo uses statically allocated + RAM only, there are no allocations that could fail, and + vTaskStartScheduler() cannot return - so there is no need to put the normal + infinite loop after the call to vTaskStartScheduler(). */ + + return 0; +} +/*-----------------------------------------------------------*/ + +static void prvStartCheckTask( void ) +{ +/* Allocate the data structure that will hold the task's TCB. NOTE: This is +declared static so it still exists after this function has returned. */ +static StaticTask_t xCheckTask; + +/* Allocate the stack that will be used by the task. NOTE: This is declared +static so it still exists after this function has returned. */ +static StackType_t ucTaskStack[ configMINIMAL_STACK_SIZE * sizeof( StackType_t ) ]; + + /* Create the task, which will use the RAM allocated by the linker to the + variables declared in this function. */ + xTaskCreateStatic( prvCheckTask, "Check", configMINIMAL_STACK_SIZE, NULL, configMAX_PRIORITIES - 1, NULL, ucTaskStack, &xCheckTask ); +} +/*-----------------------------------------------------------*/ + +static void prvCheckTask( void *pvParameters ) +{ +const TickType_t xCycleFrequency = pdMS_TO_TICKS( 2500UL ); +static char *pcStatusMessage = "No errors"; + + /* Just to remove compiler warning. */ + ( void ) pvParameters; + + for( ;; ) + { + /* Place this task in the blocked state until it is time to run again. */ + vTaskDelay( xCycleFrequency ); + + /* Check the tasks that use static allocation are still executing. */ + if( xAreStaticAllocationTasksStillRunning() != pdPASS ) + { + pcStatusMessage = "Error: Static allocation"; + } + + /* This is the only task that uses stdout so its ok to call printf() + directly. */ + printf( "%s - tick count %d - number of tasks executing %d\r\n", + pcStatusMessage, + xTaskGetTickCount(), + uxTaskGetNumberOfTasks() ); + } +} + +/*-----------------------------------------------------------*/ +void vApplicationStackOverflowHook( TaskHandle_t pxTask, char *pcTaskName ) +{ + ( void ) pcTaskName; + ( void ) pxTask; + + /* Run time stack overflow checking is performed if + configCHECK_FOR_STACK_OVERFLOW is defined to 1 or 2. This hook + function is called if a stack overflow is detected. This function is + provided as an example only as stack overflow checking does not function + when running the FreeRTOS Windows port. */ + vAssertCalled( __LINE__, __FILE__ ); +} +/*-----------------------------------------------------------*/ + +void vAssertCalled( unsigned long ulLine, const char * const pcFileName ) +{ +volatile uint32_t ulSetToNonZeroInDebuggerToContinue = 0; + + /* Called if an assertion passed to configASSERT() fails. See + http://www.freertos.org/a00110.html#configASSERT for more information. */ + + /* Parameters are not used. */ + ( void ) ulLine; + ( void ) pcFileName; + + printf( "ASSERT! Line %d, file %s\r\n", ulLine, pcFileName ); + + taskENTER_CRITICAL(); + { + /* You can step out of this function to debug the assertion by using + the debugger to set ulSetToNonZeroInDebuggerToContinue to a non-zero + value. */ + while( ulSetToNonZeroInDebuggerToContinue == 0 ) + { + __asm{ NOP }; + __asm{ NOP }; + } + } + taskEXIT_CRITICAL(); +} +/*-----------------------------------------------------------*/ + +void vApplicationGetIdleTaskMemory( StaticTask_t **ppxIdleTaskTCBBuffer, StackType_t **ppxIdleTaskStackBuffer, uint16_t *pusIdleTaskStackSize ) +{ +/* The buffers used by the idle task must be static so they are persistent, and +so exist after this function returns. */ +static StaticTask_t xIdleTaskTCB; +static StackType_t uxIdleTaskStack[ configMINIMAL_STACK_SIZE ]; + + /* configSUPORT_STATIC_ALLOCATION is set to 1 and + configSUPPORT_DYNAMIC_ALLOCATION is 0, so the application must supply the + buffers that will be used to hold the Idle task data structure and stack. */ + *ppxIdleTaskTCBBuffer = &xIdleTaskTCB; + *ppxIdleTaskStackBuffer = uxIdleTaskStack; + *pusIdleTaskStackSize = configMINIMAL_STACK_SIZE; /* In words. NOT in bytes! */ +} +/*-----------------------------------------------------------*/ + +void vApplicationGetTimerTaskMemory( StaticTask_t **ppxTimerTaskTCBBuffer, StackType_t **ppxTimerTaskStackBuffer, uint16_t *pusTimerTaskStackSize ) +{ +/* The buffers used by the Timer/Daemon task must be static so they are +persistent, and so exist after this function returns. */ +static StaticTask_t xTimerTaskTCB; +static StackType_t uxTimerTaskStack[ configTIMER_TASK_STACK_DEPTH ]; + + /* configSUPPORT_STATIC_ALLOCATION is set to 1, + configSUPPORT_DYNAMIC_ALLOCATION is set to 1, and configUSE_TIMERS is set + to 1, so the application must supply the buffers that will be used to hold + the Timer task data structure and stack. */ + *ppxTimerTaskTCBBuffer = &xTimerTaskTCB; + *ppxTimerTaskStackBuffer = uxTimerTaskStack; + *pusTimerTaskStackSize = configTIMER_TASK_STACK_DEPTH; /* In words. NOT in bytes! */ +} + diff --git a/FreeRTOS/Demo/WIN32-MSVC/main_full.c b/FreeRTOS/Demo/WIN32-MSVC/main_full.c index d3894b15c..724c55cfe 100644 --- a/FreeRTOS/Demo/WIN32-MSVC/main_full.c +++ b/FreeRTOS/Demo/WIN32-MSVC/main_full.c @@ -697,6 +697,10 @@ static void prvPermanentlyBlockingSemaphoreTask( void *pvParameters ) { SemaphoreHandle_t xSemaphore; + /* Prevent compiler warning about unused parameter in the case that + configASSERT() is not defined. */ + ( void ) pvParameters; + /* This task should block on a semaphore, and never return. */ xSemaphore = xSemaphoreCreateBinary(); configASSERT( xSemaphore ); @@ -712,6 +716,10 @@ SemaphoreHandle_t xSemaphore; static void prvPermanentlyBlockingNotificationTask( void *pvParameters ) { + /* Prevent compiler warning about unused parameter in the case that + configASSERT() is not defined. */ + ( void ) pvParameters; + /* This task should block on a task notification, and never return. */ ulTaskNotifyTake( pdTRUE, portMAX_DELAY ); diff --git a/FreeRTOS/Demo/WIN32-MingW/.project b/FreeRTOS/Demo/WIN32-MingW/.project index 2df612dba..51cdf8eda 100644 --- a/FreeRTOS/Demo/WIN32-MingW/.project +++ b/FreeRTOS/Demo/WIN32-MingW/.project @@ -56,7 +56,7 @@ - 1418321193247 + 1458581605399 Standard_Demo_Tasks 5 @@ -65,7 +65,7 @@ - 1418321193247 + 1458581605404 Standard_Demo_Tasks 5 @@ -74,7 +74,7 @@ - 1418321193257 + 1458581605410 Standard_Demo_Tasks 5 @@ -83,7 +83,7 @@ - 1418321193257 + 1458581605415 Standard_Demo_Tasks 5 @@ -92,7 +92,7 @@ - 1418321193267 + 1458581605421 Standard_Demo_Tasks 5 @@ -101,7 +101,7 @@ - 1418321193277 + 1458581605427 Standard_Demo_Tasks 5 @@ -110,7 +110,7 @@ - 1418321193277 + 1458581605434 Standard_Demo_Tasks 5 @@ -119,7 +119,7 @@ - 1418321193287 + 1458581605441 Standard_Demo_Tasks 5 @@ -128,7 +128,7 @@ - 1418321193297 + 1458581605450 Standard_Demo_Tasks 5 @@ -137,7 +137,7 @@ - 1418321193297 + 1458581605458 Standard_Demo_Tasks 5 @@ -146,7 +146,7 @@ - 1418321193308 + 1458581605463 Standard_Demo_Tasks 5 @@ -155,7 +155,7 @@ - 1418321193313 + 1458581605473 Standard_Demo_Tasks 5 @@ -164,7 +164,7 @@ - 1418321193319 + 1458581605490 Standard_Demo_Tasks 5 @@ -173,7 +173,7 @@ - 1418321193325 + 1458581605514 Standard_Demo_Tasks 5 @@ -182,7 +182,7 @@ - 1418321193349 + 1458581605524 Standard_Demo_Tasks 5 @@ -191,7 +191,7 @@ - 1418321193369 + 1458581605530 Standard_Demo_Tasks 5 @@ -200,7 +200,7 @@ - 1418321193379 + 1458581605535 Standard_Demo_Tasks 5 @@ -208,6 +208,24 @@ 1.0-name-matches-false-false-TaskNotify.c + + 1458581605540 + Standard_Demo_Tasks + 5 + + org.eclipse.ui.ide.multiFilter + 1.0-name-matches-false-false-QueueSetPolling.c + + + + 1458581605547 + Standard_Demo_Tasks + 5 + + org.eclipse.ui.ide.multiFilter + 1.0-name-matches-false-false-AbortDelay.c + + 0 FreeRTOS_Source/portable diff --git a/FreeRTOS/Demo/WIN32-MingW/.settings/org.eclipse.cdt.codan.core.prefs b/FreeRTOS/Demo/WIN32-MingW/.settings/org.eclipse.cdt.codan.core.prefs index 82c09e194..3d999f356 100644 --- a/FreeRTOS/Demo/WIN32-MingW/.settings/org.eclipse.cdt.codan.core.prefs +++ b/FreeRTOS/Demo/WIN32-MingW/.settings/org.eclipse.cdt.codan.core.prefs @@ -4,6 +4,10 @@ org.eclipse.cdt.codan.checkers.errnoreturn=-Warning org.eclipse.cdt.codan.checkers.errnoreturn.params={launchModes\=>{RUN_ON_FULL_BUILD\=>true,RUN_ON_INC_BUILD\=>true,RUN_ON_FILE_OPEN\=>false,RUN_ON_FILE_SAVE\=>false,RUN_AS_YOU_TYPE\=>true,RUN_ON_DEMAND\=>true},implicit\=>false} org.eclipse.cdt.codan.checkers.errreturnvalue=-Error org.eclipse.cdt.codan.checkers.errreturnvalue.params={launchModes\=>{RUN_ON_FULL_BUILD\=>true,RUN_ON_INC_BUILD\=>true,RUN_ON_FILE_OPEN\=>false,RUN_ON_FILE_SAVE\=>false,RUN_AS_YOU_TYPE\=>true,RUN_ON_DEMAND\=>true}} +org.eclipse.cdt.codan.checkers.nocommentinside=-Error +org.eclipse.cdt.codan.checkers.nocommentinside.params={launchModes\=>{RUN_ON_FULL_BUILD\=>true,RUN_ON_INC_BUILD\=>true,RUN_ON_FILE_OPEN\=>false,RUN_ON_FILE_SAVE\=>false,RUN_AS_YOU_TYPE\=>true,RUN_ON_DEMAND\=>true}} +org.eclipse.cdt.codan.checkers.nolinecomment=-Error +org.eclipse.cdt.codan.checkers.nolinecomment.params={launchModes\=>{RUN_ON_FULL_BUILD\=>true,RUN_ON_INC_BUILD\=>true,RUN_ON_FILE_OPEN\=>false,RUN_ON_FILE_SAVE\=>false,RUN_AS_YOU_TYPE\=>true,RUN_ON_DEMAND\=>true}} org.eclipse.cdt.codan.checkers.noreturn=-Error org.eclipse.cdt.codan.checkers.noreturn.params={launchModes\=>{RUN_ON_FULL_BUILD\=>true,RUN_ON_INC_BUILD\=>true,RUN_ON_FILE_OPEN\=>false,RUN_ON_FILE_SAVE\=>false,RUN_AS_YOU_TYPE\=>true,RUN_ON_DEMAND\=>true},implicit\=>false} org.eclipse.cdt.codan.internal.checkers.AbstractClassCreation=-Error diff --git a/FreeRTOS/Demo/WIN32-MingW/FreeRTOSConfig.h b/FreeRTOS/Demo/WIN32-MingW/FreeRTOSConfig.h index 91a5781e8..42d77701f 100644 --- a/FreeRTOS/Demo/WIN32-MingW/FreeRTOSConfig.h +++ b/FreeRTOS/Demo/WIN32-MingW/FreeRTOSConfig.h @@ -78,7 +78,8 @@ * application requirements. * * THESE PARAMETERS ARE DESCRIBED WITHIN THE 'CONFIGURATION' SECTION OF THE - * FreeRTOS API DOCUMENTATION AVAILABLE ON THE FreeRTOS.org WEB SITE. + * FreeRTOS API DOCUMENTATION AVAILABLE ON THE FreeRTOS.org WEB SITE. See + * http://www.freertos.org/a00110.html *----------------------------------------------------------*/ #define configUSE_PREEMPTION 1 @@ -87,7 +88,7 @@ #define configUSE_TICK_HOOK 1 #define configTICK_RATE_HZ ( 1000 ) /* In this non-real time simulated environment the tick frequency has to be at least a multiple of the Win32 tick frequency, and therefore very slow. */ #define configMINIMAL_STACK_SIZE ( ( unsigned short ) 50 ) /* In this simulated case, the stack only has to hold one small structure as the real stack is part of the win32 thread. */ -#define configTOTAL_HEAP_SIZE ( ( size_t ) ( 23 * 1024 ) ) +#define configTOTAL_HEAP_SIZE ( ( size_t ) ( 35 * 1024 ) ) #define configMAX_TASK_NAME_LEN ( 12 ) #define configUSE_TRACE_FACILITY 1 #define configUSE_16_BIT_TICKS 0 @@ -146,6 +147,8 @@ functions anyway. */ #define INCLUDE_eTaskGetState 1 #define INCLUDE_xSemaphoreGetMutexHolder 1 #define INCLUDE_xTimerPendFunctionCall 1 +#define INCLUDE_xTaskAbortDelay 1 +#define INCLUDE_xTaskGetTaskHandle 1 /* It is a good idea to define configASSERT() while developing. configASSERT() uses the same semantics as the standard C assert() macro. */ diff --git a/FreeRTOS/Demo/WIN32-MingW/main.c b/FreeRTOS/Demo/WIN32-MingW/main.c index 85572f0aa..7de3f1206 100644 --- a/FreeRTOS/Demo/WIN32-MingW/main.c +++ b/FreeRTOS/Demo/WIN32-MingW/main.c @@ -116,9 +116,9 @@ that make up the total heap. This is only done to provide an example of heap_5 being used as this demo could easily create one large heap region instead of multiple smaller heap regions - in which case heap_4.c would be the more appropriate choice. */ -#define mainREGION_1_SIZE 3001 +#define mainREGION_1_SIZE 7001 #define mainREGION_2_SIZE 18105 -#define mainREGION_3_SIZE 1107 +#define mainREGION_3_SIZE 2807 /* * main_blinky() is used when mainCREATE_SIMPLE_BLINKY_DEMO_ONLY is set to 1. diff --git a/FreeRTOS/Demo/WIN32-MingW/main_full.c b/FreeRTOS/Demo/WIN32-MingW/main_full.c index 7bd398fd9..e37b92b9f 100644 --- a/FreeRTOS/Demo/WIN32-MingW/main_full.c +++ b/FreeRTOS/Demo/WIN32-MingW/main_full.c @@ -139,6 +139,9 @@ #include "EventGroupsDemo.h" #include "IntSemTest.h" #include "TaskNotify.h" +#include "QueueSetPolling.h" +#include "blocktim.h" +#include "AbortDelay.h" /* Priorities at which the tasks are created. */ #define mainCHECK_TASK_PRIORITY ( configMAX_PRIORITIES - 2 ) @@ -217,6 +220,9 @@ int main_full( void ) xTaskCreate( prvDemoQueueSpaceFunctions, "QSpace", configMINIMAL_STACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); vStartEventGroupTasks(); vStartInterruptSemaphoreTasks(); + vStartQueueSetPollingTask(); + vCreateBlockTimeTasks(); + vCreateAbortDelayTasks(); #if( configUSE_PREEMPTION != 0 ) { @@ -238,16 +244,16 @@ int main_full( void ) /* Start the scheduler itself. */ vTaskStartScheduler(); - /* Should never get here unless there was not enough heap space to create + /* Should never get here unless there was not enough heap space to create the idle and other system tasks. */ - return 0; + return 0; } /*-----------------------------------------------------------*/ static void prvCheckTask( void *pvParameters ) { TickType_t xNextWakeTime; -const TickType_t xCycleFrequency = 2500 / portTICK_PERIOD_MS; +const TickType_t xCycleFrequency = pdMS_TO_TICKS( 2500UL ); /* Just to remove compiler warning. */ ( void ) pvParameters; @@ -336,6 +342,18 @@ const TickType_t xCycleFrequency = 2500 / portTICK_PERIOD_MS; { pcStatusMessage = "Error: Queue overwrite"; } + else if( xAreQueueSetPollTasksStillRunning() != pdPASS ) + { + pcStatusMessage = "Error: Queue set polling"; + } + else if( xAreBlockTimeTestTasksStillRunning() != pdPASS ) + { + pcStatusMessage = "Error: Block time"; + } + else if( xAreAbortDelayTestTasksStillRunning() != pdPASS ) + { + pcStatusMessage = "Error: Abort delay"; + } /* This is the only task that uses stdout so its ok to call printf() directly. */ @@ -416,6 +434,7 @@ void vFullDemoTickHookFunction( void ) /* Write to a queue that is in use as part of the queue set demo to demonstrate using queue sets from an ISR. */ vQueueSetAccessQueueSetFromISR(); + vQueueSetPollingInterruptAccess(); /* Exercise event groups from interrupts. */ vPeriodicEventGroupsProcessing(); diff --git a/FreeRTOS/Source/event_groups.c b/FreeRTOS/Source/event_groups.c index 942a34a5c..2f4cd7991 100644 --- a/FreeRTOS/Source/event_groups.c +++ b/FreeRTOS/Source/event_groups.c @@ -111,8 +111,8 @@ typedef struct xEventGroupDefinition UBaseType_t uxEventGroupNumber; #endif - #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - uint8_t ucStaticallyAllocated; + #if( ( configSUPPORT_STATIC_ALLOCATION == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) + uint8_t ucStaticallyAllocated; /*< Set to pdTRUE if the event group is statically allocated to ensure no attempt is made to free the memory. */ #endif } EventGroup_t; @@ -130,49 +130,79 @@ static BaseType_t prvTestWaitCondition( const EventBits_t uxCurrentEventBits, co /*-----------------------------------------------------------*/ -EventGroupHandle_t xEventGroupGenericCreate( StaticEventGroup_t *pxStaticEventGroup ) -{ -EventGroup_t *pxEventBits; +#if( configSUPPORT_STATIC_ALLOCATION == 1 ) - if( pxStaticEventGroup == NULL ) - { - /* The user has not provided a statically allocated event group, so - create on dynamically. */ - pxEventBits = ( EventGroup_t * ) pvPortMalloc( sizeof( EventGroup_t ) ); - } - else + EventGroupHandle_t xEventGroupCreateStatic( StaticEventGroup_t *pxStaticEventGroup ) { + EventGroup_t *pxEventBits; + + /* A StaticEventGroup_t object must be provided. */ + configASSERT( pxStaticEventGroup ); + /* The user has provided a statically allocated event group - use it. */ pxEventBits = ( EventGroup_t * ) pxStaticEventGroup; /*lint !e740 EventGroup_t and StaticEventGroup_t are guaranteed to have the same size and alignment requirement - checked by configASSERT(). */ + + if( pxEventBits != NULL ) + { + pxEventBits->uxEventBits = 0; + vListInitialise( &( pxEventBits->xTasksWaitingForBits ) ); + + #if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + { + /* Both static and dynamic allocation can be used, so note that + this event group was created statically in case the event group + is later deleted. */ + pxEventBits->ucStaticallyAllocated = pdTRUE; + } + #endif /* configSUPPORT_DYNAMIC_ALLOCATION */ + + traceEVENT_GROUP_CREATE( pxEventBits ); + } + else + { + traceEVENT_GROUP_CREATE_FAILED(); + } + + return ( EventGroupHandle_t ) pxEventBits; } - if( pxEventBits != NULL ) +#endif /* configSUPPORT_STATIC_ALLOCATION */ +/*-----------------------------------------------------------*/ + +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + + EventGroupHandle_t xEventGroupCreate( void ) { - pxEventBits->uxEventBits = 0; - vListInitialise( &( pxEventBits->xTasksWaitingForBits ) ); + EventGroup_t *pxEventBits; + + /* Allocate the event group. */ + pxEventBits = ( EventGroup_t * ) pvPortMalloc( sizeof( EventGroup_t ) ); - #if( configSUPPORT_STATIC_ALLOCATION == 1 ) + if( pxEventBits != NULL ) { - if( pxStaticEventGroup == NULL ) + pxEventBits->uxEventBits = 0; + vListInitialise( &( pxEventBits->xTasksWaitingForBits ) ); + + #if( configSUPPORT_STATIC_ALLOCATION == 1 ) { + /* Both static and dynamic allocation can be used, so note this + event group was allocated statically in case the event group is + later deleted. */ pxEventBits->ucStaticallyAllocated = pdFALSE; } - else - { - pxEventBits->ucStaticallyAllocated = pdTRUE; - } + #endif /* configSUPPORT_STATIC_ALLOCATION */ + + traceEVENT_GROUP_CREATE( pxEventBits ); + } + else + { + traceEVENT_GROUP_CREATE_FAILED(); } - #endif /* configSUPPORT_STATIC_ALLOCATION */ - traceEVENT_GROUP_CREATE( pxEventBits ); - } - else - { - traceEVENT_GROUP_CREATE_FAILED(); + return ( EventGroupHandle_t ) pxEventBits; } - return ( EventGroupHandle_t ) pxEventBits; -} +#endif /* configSUPPORT_DYNAMIC_ALLOCATION */ /*-----------------------------------------------------------*/ EventBits_t xEventGroupSync( EventGroupHandle_t xEventGroup, const EventBits_t uxBitsToSet, const EventBits_t uxBitsToWaitFor, TickType_t xTicksToWait ) @@ -608,19 +638,26 @@ const List_t *pxTasksWaitingForBits = &( pxEventBits->xTasksWaitingForBits ); ( void ) xTaskRemoveFromUnorderedEventList( pxTasksWaitingForBits->xListEnd.pxNext, eventUNBLOCKED_DUE_TO_BIT_SET ); } - /* Only free the memory if it was allocated dynamically. */ - #if( configSUPPORT_STATIC_ALLOCATION == 1 ) + #if( ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 0 ) ) + { + /* The event group can only have been allocated dynamically - free + it again. */ + vPortFree( pxEventBits ); + } + #elif( ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 1 ) ) { + /* The event group could have been allocated statically or + dynamically, so check before attempting to free the memory. */ if( pxEventBits->ucStaticallyAllocated == ( uint8_t ) pdFALSE ) { vPortFree( pxEventBits ); } + else + { + mtCOVERAGE_TEST_MARKER(); + } } - #else - { - vPortFree( pxEventBits ); - } - #endif /* configSUPPORT_STATIC_ALLOCATION */ + #endif /* configSUPPORT_DYNAMIC_ALLOCATION */ } ( void ) xTaskResumeAll(); } diff --git a/FreeRTOS/Source/include/FreeRTOS.h b/FreeRTOS/Source/include/FreeRTOS.h index 3ea860df1..7e6411d8c 100644 --- a/FreeRTOS/Source/include/FreeRTOS.h +++ b/FreeRTOS/Source/include/FreeRTOS.h @@ -173,10 +173,6 @@ extern "C" { #define INCLUDE_xTaskAbortDelay 0 #endif -#ifndef INCLUDE_xTimerGetTimerDaemonTaskHandle - #define INCLUDE_xTimerGetTimerDaemonTaskHandle 0 -#endif - #ifndef INCLUDE_xQueueGetMutexHolder #define INCLUDE_xQueueGetMutexHolder 0 #endif @@ -691,14 +687,6 @@ extern "C" { #define portYIELD_WITHIN_API portYIELD #endif -#ifndef pvPortMallocAligned - #define pvPortMallocAligned( x, puxPreallocatedBuffer ) ( ( ( puxPreallocatedBuffer ) == NULL ) ? ( pvPortMalloc( ( x ) ) ) : ( puxPreallocatedBuffer ) ) -#endif - -#ifndef vPortFreeAligned - #define vPortFreeAligned( pvBlockToFree ) vPortFree( pvBlockToFree ) -#endif - #ifndef portSUPPRESS_TICKS_AND_SLEEP #define portSUPPRESS_TICKS_AND_SLEEP( xExpectedIdleTime ) #endif @@ -784,9 +772,30 @@ extern "C" { #endif #ifndef configSUPPORT_STATIC_ALLOCATION + /* Defaults to 0 for backward compatibility. */ #define configSUPPORT_STATIC_ALLOCATION 0 #endif +#ifndef configSUPPORT_DYNAMIC_ALLOCATION + /* Defaults to 1 for backward compatibility. */ + #define configSUPPORT_DYNAMIC_ALLOCATION 1 +#endif + +/* Sanity check the configuration. */ +#if( configUSE_TICKLESS_IDLE != 0 ) + #if( INCLUDE_vTaskSuspend != 1 ) + #error INCLUDE_vTaskSuspend must be set to 1 if configUSE_TICKLESS_IDLE is not set to 0 + #endif /* INCLUDE_vTaskSuspend */ +#endif /* configUSE_TICKLESS_IDLE */ + +#if( ( portUSING_MPU_WRAPPERS == 1 ) && ( configSUPPORT_STATIC_ALLOCATION != 1 ) ) + #error configSUPPORT_STATIC_ALLOCATION must be set to 1 in FreeRTOSConfig.h when the MPU is used. +#endif + +#if( ( configSUPPORT_STATIC_ALLOCATION == 0 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 0 ) ) + #error configSUPPORT_STATIC_ALLOCATION and configSUPPORT_DYNAMIC_ALLOCATION cannot both be 0, but can both be 1. +#endif + #if( ( configUSE_RECURSIVE_MUTEXES == 1 ) && ( configUSE_MUTEXES != 1 ) ) #error configUSE_MUTEXES must be set to 1 to use recursive mutexes #endif @@ -966,19 +975,20 @@ typedef struct xSTATIC_QUEUE } u; StaticList_t xDummy3[ 2 ]; - UBaseType_t uxDummy4[ 5 ]; + UBaseType_t uxDummy4[ 3 ]; + uint8_t ucDummy5[ 2 ]; + + #if( configSUPPORT_STATIC_ALLOCATION == 1 ) + uint8_t ucDummy6; + #endif #if ( configUSE_QUEUE_SETS == 1 ) void *pvDummy7; #endif #if ( configUSE_TRACE_FACILITY == 1 ) - UBaseType_t uxDummy5; - uint8_t ucDummy6; - #endif - - #if ( configSUPPORT_STATIC_ALLOCATION == 1 ) - uint8_t ucDummy7; + UBaseType_t uxDummy8; + uint8_t ucDummy9; #endif } StaticQueue_t; diff --git a/FreeRTOS/Source/include/event_groups.h b/FreeRTOS/Source/include/event_groups.h index f348da9fe..c7189a1f8 100644 --- a/FreeRTOS/Source/include/event_groups.h +++ b/FreeRTOS/Source/include/event_groups.h @@ -74,6 +74,7 @@ #error "include FreeRTOS.h" must appear in source files before "include event_groups.h" #endif +/* FreeRTOS includes. */ #include "timers.h" #ifdef __cplusplus @@ -173,10 +174,12 @@ typedef TickType_t EventBits_t; * \defgroup xEventGroupCreate xEventGroupCreate * \ingroup EventGroup */ -#define xEventGroupCreate() xEventGroupGenericCreate( NULL ) +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + EventGroupHandle_t xEventGroupCreate( void ) PRIVILEGED_FUNCTION; +#endif #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - #define xEventGroupCreateStatic( pxStaticEventGroup ) xEventGroupGenericCreate( ( pxStaticEventGroup ) ) + EventGroupHandle_t xEventGroupCreateStatic( StaticEventGroup_t *pxStaticEventGroup ) PRIVILEGED_FUNCTION; #endif /** @@ -721,11 +724,6 @@ void vEventGroupDelete( EventGroupHandle_t xEventGroup ) PRIVILEGED_FUNCTION; void vEventGroupSetBitsCallback( void *pvEventGroup, const uint32_t ulBitsToSet ) PRIVILEGED_FUNCTION; void vEventGroupClearBitsCallback( void *pvEventGroup, const uint32_t ulBitsToClear ) PRIVILEGED_FUNCTION; -/* - * Generic version of the event group creation function, which is in turn called - * by the event group creation macros. - */ -EventGroupHandle_t xEventGroupGenericCreate( StaticEventGroup_t *pxStaticEventGroup ) PRIVILEGED_FUNCTION; #if (configUSE_TRACE_FACILITY == 1) UBaseType_t uxEventGroupGetNumber( void* xEventGroup ) PRIVILEGED_FUNCTION; diff --git a/FreeRTOS/Source/include/mpu_wrappers.h b/FreeRTOS/Source/include/mpu_wrappers.h index ae3e0bece..7ce1c4162 100644 --- a/FreeRTOS/Source/include/mpu_wrappers.h +++ b/FreeRTOS/Source/include/mpu_wrappers.h @@ -123,8 +123,11 @@ only for ports that are using the MPU. */ #define xQueueRemoveFromSet MPU_xQueueRemoveFromSet #define xQueueGetMutexHolder MPU_xQueueGetMutexHolder - #define pvPortMalloc MPU_pvPortMalloc - #define vPortFree MPU_vPortFree + #if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + #define pvPortMalloc MPU_pvPortMalloc + #define vPortFree MPU_vPortFree + #endif /* configSUPPORT_DYNAMIC_ALLOCATION */ + #define xPortGetFreeHeapSize MPU_xPortGetFreeHeapSize #define vPortInitialiseBlocks MPU_vPortInitialiseBlocks #define xPortGetMinimumEverFreeHeapSize MPU_xPortGetMinimumEverFreeHeapSize diff --git a/FreeRTOS/Source/include/queue.h b/FreeRTOS/Source/include/queue.h index 273e408eb..e8f54a435 100644 --- a/FreeRTOS/Source/include/queue.h +++ b/FreeRTOS/Source/include/queue.h @@ -181,7 +181,9 @@ typedef void * QueueSetMemberHandle_t; * \defgroup xQueueCreate xQueueCreate * \ingroup QueueManagement */ -#define xQueueCreate( uxQueueLength, uxItemSize ) xQueueGenericCreate( uxQueueLength, uxItemSize, NULL, NULL, queueQUEUE_TYPE_BASE ) +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + #define xQueueCreate( uxQueueLength, uxItemSize ) xQueueGenericCreate( ( uxQueueLength ), ( uxItemSize ), ( queueQUEUE_TYPE_BASE ) ) +#endif /** * queue. h @@ -275,7 +277,7 @@ typedef void * QueueSetMemberHandle_t; * \ingroup QueueManagement */ #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - #define xQueueCreateStatic( uxQueueLength, uxItemSize, pucQueueStorage, pxQueueBuffer ) xQueueGenericCreate( ( uxQueueLength ), ( uxItemSize ), ( pucQueueStorage ), ( pxQueueBuffer ), ( queueQUEUE_TYPE_BASE ) ) + #define xQueueCreateStatic( uxQueueLength, uxItemSize, pucQueueStorage, pxQueueBuffer ) xQueueGenericCreateStatic( ( uxQueueLength ), ( uxItemSize ), ( pucQueueStorage ), ( pxQueueBuffer ), ( queueQUEUE_TYPE_BASE ) ) #endif /* configSUPPORT_STATIC_ALLOCATION */ /** @@ -1562,8 +1564,10 @@ BaseType_t xQueueCRReceive( QueueHandle_t xQueue, void *pvBuffer, TickType_t xTi * xSemaphoreCreateCounting() or xSemaphoreGetMutexHolder() instead of calling * these functions directly. */ -QueueHandle_t xQueueCreateMutex( const uint8_t ucQueueType, StaticQueue_t *pxStaticQueue ) PRIVILEGED_FUNCTION; -QueueHandle_t xQueueCreateCountingSemaphore( const UBaseType_t uxMaxCount, const UBaseType_t uxInitialCount, StaticQueue_t *pxStaticQueue ) PRIVILEGED_FUNCTION; +QueueHandle_t xQueueCreateMutex( const uint8_t ucQueueType ) PRIVILEGED_FUNCTION; +QueueHandle_t xQueueCreateMutexStatic( const uint8_t ucQueueType, StaticQueue_t *pxStaticQueue ) PRIVILEGED_FUNCTION; +QueueHandle_t xQueueCreateCountingSemaphore( const UBaseType_t uxMaxCount, const UBaseType_t uxInitialCount ) PRIVILEGED_FUNCTION; +QueueHandle_t xQueueCreateCountingSemaphoreStatic( const UBaseType_t uxMaxCount, const UBaseType_t uxInitialCount, StaticQueue_t *pxStaticQueue ) PRIVILEGED_FUNCTION; void* xQueueGetMutexHolder( QueueHandle_t xSemaphore ) PRIVILEGED_FUNCTION; /* @@ -1635,10 +1639,22 @@ BaseType_t xQueueGiveMutexRecursive( QueueHandle_t pxMutex ) PRIVILEGED_FUNCTION #endif /* - * Generic version of the queue creation function, which is in turn called by - * any queue, semaphore or mutex creation function or macro. + * Generic version of the function used to creaet a queue using dynamic memory + * allocation. This is called by other functions and macros that create other + * RTOS objects that use the queue structure as their base. */ -QueueHandle_t xQueueGenericCreate( const UBaseType_t uxQueueLength, const UBaseType_t uxItemSize, uint8_t *pucQueueStorage, StaticQueue_t *pxStaticQueue, const uint8_t ucQueueType ) PRIVILEGED_FUNCTION; +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + QueueHandle_t xQueueGenericCreate( const UBaseType_t uxQueueLength, const UBaseType_t uxItemSize, const uint8_t ucQueueType ) PRIVILEGED_FUNCTION; +#endif + +/* + * Generic version of the function used to creaet a queue using dynamic memory + * allocation. This is called by other functions and macros that create other + * RTOS objects that use the queue structure as their base. + */ +#if( configSUPPORT_STATIC_ALLOCATION == 1 ) + QueueHandle_t xQueueGenericCreateStatic( const UBaseType_t uxQueueLength, const UBaseType_t uxItemSize, uint8_t *pucQueueStorage, StaticQueue_t *pxStaticQueue, const uint8_t ucQueueType ) PRIVILEGED_FUNCTION; +#endif /* * Queue sets provide a mechanism to allow a task to block (pend) on a read diff --git a/FreeRTOS/Source/include/semphr.h b/FreeRTOS/Source/include/semphr.h index 48d384095..4dbd6f578 100644 --- a/FreeRTOS/Source/include/semphr.h +++ b/FreeRTOS/Source/include/semphr.h @@ -132,14 +132,16 @@ typedef QueueHandle_t SemaphoreHandle_t; * \defgroup vSemaphoreCreateBinary vSemaphoreCreateBinary * \ingroup Semaphores */ -#define vSemaphoreCreateBinary( xSemaphore ) \ - { \ - ( xSemaphore ) = xQueueGenericCreate( ( UBaseType_t ) 1, semSEMAPHORE_QUEUE_ITEM_LENGTH, NULL, NULL, queueQUEUE_TYPE_BINARY_SEMAPHORE ); \ - if( ( xSemaphore ) != NULL ) \ - { \ - ( void ) xSemaphoreGive( ( xSemaphore ) ); \ - } \ - } +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + #define vSemaphoreCreateBinary( xSemaphore ) \ + { \ + ( xSemaphore ) = xQueueGenericCreate( ( UBaseType_t ) 1, semSEMAPHORE_QUEUE_ITEM_LENGTH, queueQUEUE_TYPE_BINARY_SEMAPHORE ); \ + if( ( xSemaphore ) != NULL ) \ + { \ + ( void ) xSemaphoreGive( ( xSemaphore ) ); \ + } \ + } +#endif /** * semphr. h @@ -199,7 +201,9 @@ typedef QueueHandle_t SemaphoreHandle_t; * \defgroup xSemaphoreCreateBinary xSemaphoreCreateBinary * \ingroup Semaphores */ -#define xSemaphoreCreateBinary() xQueueGenericCreate( ( UBaseType_t ) 1, semSEMAPHORE_QUEUE_ITEM_LENGTH, NULL, NULL, queueQUEUE_TYPE_BINARY_SEMAPHORE ) +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + #define xSemaphoreCreateBinary() xQueueGenericCreate( ( UBaseType_t ) 1, semSEMAPHORE_QUEUE_ITEM_LENGTH, queueQUEUE_TYPE_BINARY_SEMAPHORE ) +#endif /** * semphr. h @@ -267,7 +271,7 @@ typedef QueueHandle_t SemaphoreHandle_t; * \ingroup Semaphores */ #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - #define xSemaphoreCreateBinaryStatic( pxStaticSemaphore ) xQueueGenericCreate( ( UBaseType_t ) 1, semSEMAPHORE_QUEUE_ITEM_LENGTH, NULL, pxStaticSemaphore, queueQUEUE_TYPE_BINARY_SEMAPHORE ) + #define xSemaphoreCreateBinaryStatic( pxStaticSemaphore ) xQueueGenericCreateStatic( ( UBaseType_t ) 1, semSEMAPHORE_QUEUE_ITEM_LENGTH, NULL, pxStaticSemaphore, queueQUEUE_TYPE_BINARY_SEMAPHORE ) #endif /* configSUPPORT_STATIC_ALLOCATION */ /** @@ -758,7 +762,9 @@ typedef QueueHandle_t SemaphoreHandle_t; * \defgroup xSemaphoreCreateMutex xSemaphoreCreateMutex * \ingroup Semaphores */ -#define xSemaphoreCreateMutex() xQueueCreateMutex( queueQUEUE_TYPE_MUTEX, NULL ) +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + #define xSemaphoreCreateMutex() xQueueCreateMutex( queueQUEUE_TYPE_MUTEX ) +#endif /** * semphr. h @@ -823,7 +829,7 @@ typedef QueueHandle_t SemaphoreHandle_t; * \ingroup Semaphores */ #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - #define xSemaphoreCreateMutexStatic( pxMutexBuffer ) xQueueCreateMutex( queueQUEUE_TYPE_MUTEX, ( pxMutexBuffer ) ) + #define xSemaphoreCreateMutexStatic( pxMutexBuffer ) xQueueCreateMutexStatic( queueQUEUE_TYPE_MUTEX, ( pxMutexBuffer ) ) #endif /* configSUPPORT_STATIC_ALLOCATION */ @@ -890,7 +896,9 @@ typedef QueueHandle_t SemaphoreHandle_t; * \defgroup xSemaphoreCreateRecursiveMutex xSemaphoreCreateRecursiveMutex * \ingroup Semaphores */ -#define xSemaphoreCreateRecursiveMutex() xQueueCreateMutex( queueQUEUE_TYPE_RECURSIVE_MUTEX, NULL ) +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + #define xSemaphoreCreateRecursiveMutex() xQueueCreateMutex( queueQUEUE_TYPE_RECURSIVE_MUTEX ) +#endif /** * semphr. h @@ -967,7 +975,7 @@ typedef QueueHandle_t SemaphoreHandle_t; * \ingroup Semaphores */ #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - #define xSemaphoreCreateRecursiveMutexStatic( pxStaticSemaphore ) xQueueCreateMutex( queueQUEUE_TYPE_RECURSIVE_MUTEX, pxStaticSemaphore ) + #define xSemaphoreCreateRecursiveMutexStatic( pxStaticSemaphore ) xQueueCreateMutexStatic( queueQUEUE_TYPE_RECURSIVE_MUTEX, pxStaticSemaphore ) #endif /* configSUPPORT_STATIC_ALLOCATION */ /** @@ -1042,7 +1050,9 @@ typedef QueueHandle_t SemaphoreHandle_t; * \defgroup xSemaphoreCreateCounting xSemaphoreCreateCounting * \ingroup Semaphores */ -#define xSemaphoreCreateCounting( uxMaxCount, uxInitialCount ) xQueueCreateCountingSemaphore( ( uxMaxCount ), ( uxInitialCount ), ( NULL ) ) +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + #define xSemaphoreCreateCounting( uxMaxCount, uxInitialCount ) xQueueCreateCountingSemaphore( ( uxMaxCount ), ( uxInitialCount ) ) +#endif /** * semphr. h @@ -1128,7 +1138,7 @@ typedef QueueHandle_t SemaphoreHandle_t; * \ingroup Semaphores */ #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - #define xSemaphoreCreateCountingStatic( uxMaxCount, uxInitialCount, pxSemaphoreBuffer ) xQueueCreateCountingSemaphore( ( uxMaxCount ), ( uxInitialCount ), ( pxSemaphoreBuffer ) ) + #define xSemaphoreCreateCountingStatic( uxMaxCount, uxInitialCount, pxSemaphoreBuffer ) xQueueCreateCountingSemaphoreStatic( ( uxMaxCount ), ( uxInitialCount ), ( pxSemaphoreBuffer ) ) #endif /* configSUPPORT_STATIC_ALLOCATION */ /** diff --git a/FreeRTOS/Source/include/task.h b/FreeRTOS/Source/include/task.h index bd23f76c7..359bf71d3 100644 --- a/FreeRTOS/Source/include/task.h +++ b/FreeRTOS/Source/include/task.h @@ -357,7 +357,9 @@ is used in assert() statements. */ * \defgroup xTaskCreate xTaskCreate * \ingroup Tasks */ -#define xTaskCreate( pvTaskCode, pcName, usStackDepth, pvParameters, uxPriority, pxCreatedTask ) xTaskGenericCreate( ( pvTaskCode ), ( pcName ), ( usStackDepth ), ( pvParameters ), ( uxPriority ), ( pxCreatedTask ), ( NULL ), ( NULL ), ( NULL ) ) +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + BaseType_t xTaskCreate( TaskFunction_t pxTaskCode, const char * const pcName, const uint16_t usStackDepth, void * const pvParameters, UBaseType_t uxPriority, TaskHandle_t * const pxCreatedTask ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ +#endif /** * task. h @@ -458,21 +460,21 @@ is used in assert() statements. */ TaskHandle_t xHandle = NULL; // Create the task without using any dynamic memory allocation. - xTaskCreate( vTaskCode, // As per xTaskCreate() parameter. - "NAME", // As per xTaskCreate() parameter. - STACK_SIZE, // As per xTaskCreate() parameter. - &ucParameterToPass, // As per xTaskCreate() parameter. - tskIDLE_PRIORITY, // As per xTaskCreate() parameter. - &xHandle, // As per xTaskCreate() parameter. - xStack, // Pointer to the buffer that the task being created will use as its stack. - &xTaskBuffer ); // Pointer to a StaticTask_t structure for use as the memory require by the task. + xTaskCreateStatic( vTaskCode, // As per xTaskCreate() parameter. + "NAME", // As per xTaskCreate() parameter. + STACK_SIZE, // As per xTaskCreate() parameter. + &ucParameterToPass, // As per xTaskCreate() parameter. + tskIDLE_PRIORITY, // As per xTaskCreate() parameter. + &xHandle, // As per xTaskCreate() parameter. + xStack, // Pointer to the buffer that the task being created will use as its stack. + &xTaskBuffer ); // Pointer to a StaticTask_t structure for use as the memory require by the task. } * \defgroup xTaskCreateStatic xTaskCreateStatic * \ingroup Tasks */ #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - #define xTaskCreateStatic( pvTaskCode, pcName, usStackDepth, pvParameters, uxPriority, pxCreatedTask, puxStackBuffer, pxTaskBuffer ) xTaskGenericCreate( ( pvTaskCode ), ( pcName ), ( usStackDepth ), ( pvParameters ), ( uxPriority ), ( pxCreatedTask ), ( puxStackBuffer ), ( pxTaskBuffer ), ( NULL ) ) + BaseType_t xTaskCreateStatic( TaskFunction_t pxTaskCode, const char * const pcName, const uint16_t usStackDepth, void * const pvParameters, UBaseType_t uxPriority, TaskHandle_t * const pxCreatedTask, StackType_t * const puxStackBuffer, StaticTask_t * const pxTaskBuffer ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ #endif /* configSUPPORT_STATIC_ALLOCATION */ /** @@ -2207,12 +2209,6 @@ void vTaskPriorityInherit( TaskHandle_t const pxMutexHolder ) PRIVILEGED_FUNCTIO */ BaseType_t xTaskPriorityDisinherit( TaskHandle_t const pxMutexHolder ) PRIVILEGED_FUNCTION; -/* - * Generic version of the task creation function which is in turn called by the - * xTaskCreate() and xTaskCreateRestricted() macros. - */ -BaseType_t xTaskGenericCreate( TaskFunction_t pxTaskCode, const char * const pcName, const uint16_t usStackDepth, void * const pvParameters, UBaseType_t uxPriority, TaskHandle_t * const pxCreatedTask, StackType_t * const puxStackBuffer, StaticTask_t * const pxTaskBuffer, const MemoryRegion_t * const xRegions ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ - /* * Get the uxTCBNumber assigned to the task referenced by the xTask parameter. */ diff --git a/FreeRTOS/Source/include/timers.h b/FreeRTOS/Source/include/timers.h index 04f120d88..5a6003d7b 100644 --- a/FreeRTOS/Source/include/timers.h +++ b/FreeRTOS/Source/include/timers.h @@ -266,7 +266,9 @@ typedef void (*PendedFunction_t)( void *, uint32_t ); * } * @endverbatim */ -#define xTimerCreate( pcTimerName, xTimerPeriodInTicks, uxAutoReload, pvTimerID, pxCallbackFunction ) xTimerGenericCreate( ( pcTimerName ), ( xTimerPeriodInTicks ), ( uxAutoReload ), ( pvTimerID ), ( pxCallbackFunction ), NULL ) +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + TimerHandle_t xTimerCreate( const char * const pcTimerName, const TickType_t xTimerPeriodInTicks, const UBaseType_t uxAutoReload, void * const pvTimerID, TimerCallbackFunction_t pxCallbackFunction ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ +#endif /** * TimerHandle_t xTimerCreateStatic(const char * const pcTimerName, @@ -399,7 +401,7 @@ typedef void (*PendedFunction_t)( void *, uint32_t ); * @endverbatim */ #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - #define xTimerCreateStatic( pcTimerName, xTimerPeriodInTicks, uxAutoReload, pvTimerID, pxCallbackFunction, pxTimerBuffer ) xTimerGenericCreate( ( pcTimerName ), ( xTimerPeriodInTicks ), ( uxAutoReload ), ( pvTimerID ), ( pxCallbackFunction ), ( pxTimerBuffer ) ) + TimerHandle_t xTimerCreateStatic( const char * const pcTimerName, const TickType_t xTimerPeriodInTicks, const UBaseType_t uxAutoReload, void * const pvTimerID, TimerCallbackFunction_t pxCallbackFunction, StaticTimer_t *pxTimerBuffer ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ #endif /* configSUPPORT_STATIC_ALLOCATION */ /** @@ -1279,7 +1281,6 @@ const char * pcTimerGetTimerName( TimerHandle_t xTimer ) PRIVILEGED_FUNCTION; /* */ BaseType_t xTimerCreateTimerTask( void ) PRIVILEGED_FUNCTION; BaseType_t xTimerGenericCommand( TimerHandle_t xTimer, const BaseType_t xCommandID, const TickType_t xOptionalValue, BaseType_t * const pxHigherPriorityTaskWoken, const TickType_t xTicksToWait ) PRIVILEGED_FUNCTION; -TimerHandle_t xTimerGenericCreate( const char * const pcTimerName, const TickType_t xTimerPeriodInTicks, const UBaseType_t uxAutoReload, void * const pvTimerID, TimerCallbackFunction_t pxCallbackFunction, StaticTimer_t *pxTimerBuffer ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ #ifdef __cplusplus } diff --git a/FreeRTOS/Source/portable/GCC/ARM_CM3_MPU/port.c b/FreeRTOS/Source/portable/GCC/ARM_CM3_MPU/port.c index 66c4566ff..b2ad3f9c5 100644 --- a/FreeRTOS/Source/portable/GCC/ARM_CM3_MPU/port.c +++ b/FreeRTOS/Source/portable/GCC/ARM_CM3_MPU/port.c @@ -71,6 +71,8 @@ * Implementation of functions defined in portable.h for the ARM CM3 port. *----------------------------------------------------------*/ +#error This port is not currently supported in this V9.0.0 revision number but will be by the final release. For now use V8.2.3 instead. + /* Defining MPU_WRAPPERS_INCLUDED_FROM_API_FILE prevents task.h from redefining all the API functions to use the MPU wrappers. That should only be done when task.h is included from an application file. */ @@ -1156,27 +1158,35 @@ BaseType_t xRunningPrivileged = prvRaisePrivilege(); } /*-----------------------------------------------------------*/ -void *MPU_pvPortMalloc( size_t xSize ) -{ -void *pvReturn; -BaseType_t xRunningPrivileged = prvRaisePrivilege(); +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + + void *MPU_pvPortMalloc( size_t xSize ) + { + void *pvReturn; + BaseType_t xRunningPrivileged = prvRaisePrivilege(); - pvReturn = pvPortMalloc( xSize ); + pvReturn = pvPortMalloc( xSize ); - portRESET_PRIVILEGE( xRunningPrivileged ); + portRESET_PRIVILEGE( xRunningPrivileged ); - return pvReturn; -} + return pvReturn; + } + +#endif /* configSUPPORT_DYNAMIC_ALLOCATION */ /*-----------------------------------------------------------*/ -void MPU_vPortFree( void *pv ) -{ -BaseType_t xRunningPrivileged = prvRaisePrivilege(); +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) - vPortFree( pv ); + void MPU_vPortFree( void *pv ) + { + BaseType_t xRunningPrivileged = prvRaisePrivilege(); - portRESET_PRIVILEGE( xRunningPrivileged ); -} + vPortFree( pv ); + + portRESET_PRIVILEGE( xRunningPrivileged ); + } + +#endif /* configSUPPORT_DYNAMIC_ALLOCATION */ /*-----------------------------------------------------------*/ void MPU_vPortInitialiseBlocks( void ) diff --git a/FreeRTOS/Source/portable/GCC/IA32_flat/port.c b/FreeRTOS/Source/portable/GCC/IA32_flat/port.c index 09b75552f..9d2d017e6 100644 --- a/FreeRTOS/Source/portable/GCC/IA32_flat/port.c +++ b/FreeRTOS/Source/portable/GCC/IA32_flat/port.c @@ -89,6 +89,10 @@ #error configMAX_API_CALL_INTERRUPT_PRIORITY must be between 2 and 15 #endif +#if( ( configSUPPORT_FPU == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 0 ) ) + #error configSUPPORT_DYNAMIC_ALLOCATION must be set to 1 to use this port with an FPU +#endif + /* A critical section is exited when the critical section nesting count reaches this value. */ #define portNO_CRITICAL_NESTING ( ( uint32_t ) 0 ) @@ -640,7 +644,7 @@ BaseType_t xPortInstallInterruptHandler( ISR_Handler_t pxHandler, uint32_t ulVec BaseType_t xReturn; xReturn = prvCheckValidityOfVectorNumber( ulVectorNumber ); - + if( xReturn != pdFAIL ) { taskENTER_CRITICAL(); diff --git a/FreeRTOS/Source/portable/GCC/MicroBlaze/port.c b/FreeRTOS/Source/portable/GCC/MicroBlaze/port.c index 4687c1f88..1cac38e84 100644 --- a/FreeRTOS/Source/portable/GCC/MicroBlaze/port.c +++ b/FreeRTOS/Source/portable/GCC/MicroBlaze/port.c @@ -84,6 +84,10 @@ #include #include +#if( configSUPPORT_DYNAMIC_ALLOCATION == 0 ) + #error configSUPPORT_DYNAMIC_ALLOCATION must be set to 1 to use this port. +#endif + /* Tasks are started with interrupts enabled. */ #define portINITIAL_MSR_STATE ( ( StackType_t ) 0x02 ) @@ -99,7 +103,7 @@ to reach zero, so it is initialised to a high value. */ debugging. */ #define portISR_STACK_FILL_VALUE 0x55555555 -/* Counts the nesting depth of calls to portENTER_CRITICAL(). Each task +/* Counts the nesting depth of calls to portENTER_CRITICAL(). Each task maintains it's own count, so this variable is saved as part of the task context. */ volatile UBaseType_t uxCriticalNesting = portINITIAL_NESTING_VALUE; @@ -117,10 +121,10 @@ uint32_t *pulISRStack; static void prvSetupTimerInterrupt( void ); /*-----------------------------------------------------------*/ -/* - * Initialise the stack of a task to look exactly as if a call to +/* + * Initialise the stack of a task to look exactly as if a call to * portSAVE_CONTEXT had been made. - * + * * See the header file portable.h. */ StackType_t *pxPortInitialiseStack( StackType_t *pxTopOfStack, TaskFunction_t pxCode, void *pvParameters ) @@ -129,16 +133,16 @@ extern void *_SDA2_BASE_, *_SDA_BASE_; const uint32_t ulR2 = ( uint32_t ) &_SDA2_BASE_; const uint32_t ulR13 = ( uint32_t ) &_SDA_BASE_; - /* Place a few bytes of known values on the bottom of the stack. + /* Place a few bytes of known values on the bottom of the stack. This is essential for the Microblaze port and these lines must - not be omitted. The parameter value will overwrite the + not be omitted. The parameter value will overwrite the 0x22222222 value during the function prologue. */ *pxTopOfStack = ( StackType_t ) 0x11111111; pxTopOfStack--; *pxTopOfStack = ( StackType_t ) 0x22222222; pxTopOfStack--; *pxTopOfStack = ( StackType_t ) 0x33333333; - pxTopOfStack--; + pxTopOfStack--; /* First stack an initial value for the critical section nesting. This is initialised to zero as tasks are started with interrupts enabled. */ @@ -261,7 +265,7 @@ void vPortEndScheduler( void ) /*-----------------------------------------------------------*/ /* - * Manual context switch called by portYIELD or taskYIELD. + * Manual context switch called by portYIELD or taskYIELD. */ void vPortYield( void ) { @@ -280,7 +284,7 @@ extern void VPortYieldASM( void ); /*-----------------------------------------------------------*/ /* - * Hardware initialisation to generate the RTOS tick. + * Hardware initialisation to generate the RTOS tick. */ static void prvSetupTimerInterrupt( void ) { @@ -295,12 +299,12 @@ UBaseType_t uxMask; XTmrCtr_mSetLoadReg( XPAR_OPB_TIMER_1_BASEADDR, portCOUNTER_0, ulCounterValue ); XTmrCtr_mSetControlStatusReg( XPAR_OPB_TIMER_1_BASEADDR, portCOUNTER_0, XTC_CSR_LOAD_MASK | XTC_CSR_INT_OCCURED_MASK ); - /* Set the timer interrupt enable bit while maintaining the other bit + /* Set the timer interrupt enable bit while maintaining the other bit states. */ uxMask = XIntc_In32( ( XPAR_OPB_INTC_0_BASEADDR + XIN_IER_OFFSET ) ); uxMask |= XPAR_OPB_TIMER_1_INTERRUPT_MASK; - XIntc_Out32( ( XPAR_OPB_INTC_0_BASEADDR + XIN_IER_OFFSET ), ( uxMask ) ); - + XIntc_Out32( ( XPAR_OPB_INTC_0_BASEADDR + XIN_IER_OFFSET ), ( uxMask ) ); + XTmrCtr_Start( &xTimer, XPAR_OPB_TIMER_1_DEVICE_ID ); XTmrCtr_mSetControlStatusReg(XPAR_OPB_TIMER_1_BASEADDR, portCOUNTER_0, XTC_CSR_ENABLE_TMR_MASK | XTC_CSR_ENABLE_INT_MASK | XTC_CSR_AUTO_RELOAD_MASK | XTC_CSR_DOWN_COUNT_MASK | XTC_CSR_INT_OCCURED_MASK ); XIntc_mAckIntr( XPAR_INTC_SINGLE_BASEADDR, 1 ); @@ -310,12 +314,12 @@ UBaseType_t uxMask; /* * The interrupt handler placed in the interrupt vector when the scheduler is * started. The task context has already been saved when this is called. - * This handler determines the interrupt source and calls the relevant + * This handler determines the interrupt source and calls the relevant * peripheral handler. */ void vTaskISRHandler( void ) { -static uint32_t ulPending; +static uint32_t ulPending; /* Which interrupts are pending? */ ulPending = XIntc_In32( ( XPAR_INTC_SINGLE_BASEADDR + XIN_IVR_OFFSET ) ); @@ -346,7 +350,7 @@ static uint32_t ulPending; } /*-----------------------------------------------------------*/ -/* +/* * Handler for the timer interrupt. */ void vTickISR( void *pvBaseAddress ) @@ -360,7 +364,7 @@ uint32_t ulCSR; } /* Clear the timer interrupt */ - ulCSR = XTmrCtr_mGetControlStatusReg(XPAR_OPB_TIMER_1_BASEADDR, 0); + ulCSR = XTmrCtr_mGetControlStatusReg(XPAR_OPB_TIMER_1_BASEADDR, 0); XTmrCtr_mSetControlStatusReg( XPAR_OPB_TIMER_1_BASEADDR, portCOUNTER_0, ulCSR ); } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Source/portable/MSVC-MingW/portmacro.h b/FreeRTOS/Source/portable/MSVC-MingW/portmacro.h index be10e6253..a3da226cc 100644 --- a/FreeRTOS/Source/portable/MSVC-MingW/portmacro.h +++ b/FreeRTOS/Source/portable/MSVC-MingW/portmacro.h @@ -70,7 +70,6 @@ #ifndef PORTMACRO_H #define PORTMACRO_H -#include /****************************************************************************** Defines diff --git a/FreeRTOS/Source/portable/MemMang/heap_1.c b/FreeRTOS/Source/portable/MemMang/heap_1.c index dd26f0788..79f18059a 100644 --- a/FreeRTOS/Source/portable/MemMang/heap_1.c +++ b/FreeRTOS/Source/portable/MemMang/heap_1.c @@ -87,6 +87,10 @@ task.h is included from an application file. */ #undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE +#if( configSUPPORT_DYNAMIC_ALLOCATION == 0 ) + #error This file must not be used if configSUPPORT_DYNAMIC_ALLOCATION is 0 +#endif + /* A few bytes might be lost to byte aligning the heap start address. */ #define configADJUSTED_HEAP_SIZE ( configTOTAL_HEAP_SIZE - portBYTE_ALIGNMENT ) diff --git a/FreeRTOS/Source/portable/MemMang/heap_2.c b/FreeRTOS/Source/portable/MemMang/heap_2.c index 9fe62b53a..5e6f6e011 100644 --- a/FreeRTOS/Source/portable/MemMang/heap_2.c +++ b/FreeRTOS/Source/portable/MemMang/heap_2.c @@ -88,6 +88,10 @@ task.h is included from an application file. */ #undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE +#if( configSUPPORT_DYNAMIC_ALLOCATION == 0 ) + #error This file must not be used if configSUPPORT_DYNAMIC_ALLOCATION is 0 +#endif + /* A few bytes might be lost to byte aligning the heap start address. */ #define configADJUSTED_HEAP_SIZE ( configTOTAL_HEAP_SIZE - portBYTE_ALIGNMENT ) diff --git a/FreeRTOS/Source/portable/MemMang/heap_3.c b/FreeRTOS/Source/portable/MemMang/heap_3.c index 844268eae..789b21721 100644 --- a/FreeRTOS/Source/portable/MemMang/heap_3.c +++ b/FreeRTOS/Source/portable/MemMang/heap_3.c @@ -91,6 +91,10 @@ task.h is included from an application file. */ #undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE +#if( configSUPPORT_DYNAMIC_ALLOCATION == 0 ) + #error This file must not be used if configSUPPORT_DYNAMIC_ALLOCATION is 0 +#endif + /*-----------------------------------------------------------*/ void *pvPortMalloc( size_t xWantedSize ) diff --git a/FreeRTOS/Source/portable/MemMang/heap_4.c b/FreeRTOS/Source/portable/MemMang/heap_4.c index 236b2cfac..5394be79e 100644 --- a/FreeRTOS/Source/portable/MemMang/heap_4.c +++ b/FreeRTOS/Source/portable/MemMang/heap_4.c @@ -87,6 +87,10 @@ task.h is included from an application file. */ #undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE +#if( configSUPPORT_DYNAMIC_ALLOCATION == 0 ) + #error This file must not be used if configSUPPORT_DYNAMIC_ALLOCATION is 0 +#endif + /* Block sizes must not get too small. */ #define heapMINIMUM_BLOCK_SIZE ( ( size_t ) ( xHeapStructSize << 1 ) ) diff --git a/FreeRTOS/Source/portable/MemMang/heap_5.c b/FreeRTOS/Source/portable/MemMang/heap_5.c index f147baf49..832c726f2 100644 --- a/FreeRTOS/Source/portable/MemMang/heap_5.c +++ b/FreeRTOS/Source/portable/MemMang/heap_5.c @@ -121,6 +121,10 @@ task.h is included from an application file. */ #undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE +#if( configSUPPORT_DYNAMIC_ALLOCATION == 0 ) + #error This file must not be used if configSUPPORT_DYNAMIC_ALLOCATION is 0 +#endif + /* Block sizes must not get too small. */ #define heapMINIMUM_BLOCK_SIZE ( ( size_t ) ( xHeapStructSize << 1 ) ) diff --git a/FreeRTOS/Source/portable/Renesas/SH2A_FPU/port.c b/FreeRTOS/Source/portable/Renesas/SH2A_FPU/port.c index d580b0b89..e0a3cb24a 100644 --- a/FreeRTOS/Source/portable/Renesas/SH2A_FPU/port.c +++ b/FreeRTOS/Source/portable/Renesas/SH2A_FPU/port.c @@ -84,13 +84,17 @@ value is for all interrupts to be enabled. */ #define portINITIAL_SR ( 0UL ) -/* Dimensions the array into which the floating point context is saved. +/* Dimensions the array into which the floating point context is saved. Allocate enough space for FPR0 to FPR15, FPUL and FPSCR, each of which is 4 bytes big. If this number is changed then the 72 in portasm.src also needs changing. */ #define portFLOP_REGISTERS_TO_STORE ( 18 ) #define portFLOP_STORAGE_SIZE ( portFLOP_REGISTERS_TO_STORE * 4 ) +#if( configSUPPORT_DYNAMIC_ALLOCATION == 0 ) + #error configSUPPORT_DYNAMIC_ALLOCATION must be 1 to use this port. +#endif + /*-----------------------------------------------------------*/ /* @@ -110,8 +114,8 @@ extern uint32_t ulPortGetGBR( void ); /*-----------------------------------------------------------*/ -/* - * See header file for description. +/* + * See header file for description. */ StackType_t *pxPortInitialiseStack( StackType_t *pxTopOfStack, TaskFunction_t pxCode, void *pvParameters ) { @@ -124,17 +128,17 @@ StackType_t *pxPortInitialiseStack( StackType_t *pxTopOfStack, TaskFunction_t px pxTopOfStack--; /* SR. */ - *pxTopOfStack = portINITIAL_SR; + *pxTopOfStack = portINITIAL_SR; pxTopOfStack--; - + /* PC. */ *pxTopOfStack = ( uint32_t ) pxCode; pxTopOfStack--; - + /* PR. */ *pxTopOfStack = 15; pxTopOfStack--; - + /* 14. */ *pxTopOfStack = 14; pxTopOfStack--; @@ -190,22 +194,22 @@ StackType_t *pxPortInitialiseStack( StackType_t *pxTopOfStack, TaskFunction_t px /* R1. */ *pxTopOfStack = 1; pxTopOfStack--; - + /* R0 */ *pxTopOfStack = 0; pxTopOfStack--; - + /* MACL. */ *pxTopOfStack = 16; pxTopOfStack--; - + /* MACH. */ *pxTopOfStack = 17; pxTopOfStack--; - + /* GBR. */ *pxTopOfStack = ulPortGetGBR(); - + /* GBR = global base register. VBR = vector base register. TBR = jump table base register. @@ -220,7 +224,7 @@ BaseType_t xPortStartScheduler( void ) extern void vApplicationSetupTimerInterrupt( void ); /* Call an application function to set up the timer that will generate the - tick interrupt. This way the application can decide which peripheral to + tick interrupt. This way the application can decide which peripheral to use. A demo application is provided to show a suitable example. */ vApplicationSetupTimerInterrupt(); @@ -252,11 +256,11 @@ int32_t lInterruptMask; /* taskYIELD() can only be called from a task, not an interrupt, so the current interrupt mask can only be 0 or portKERNEL_INTERRUPT_PRIORITY and - the mask can be set without risk of accidentally lowering the mask value. */ + the mask can be set without risk of accidentally lowering the mask value. */ set_imask( portKERNEL_INTERRUPT_PRIORITY ); - + trapa( portYIELD_TRAP_NO ); - + /* Restore the interrupt mask to whatever it was previously (when the function was entered). */ set_imask( ( int ) lInterruptMask ); @@ -282,26 +286,26 @@ extern void * volatile pxCurrentTCB; /* Allocate a buffer large enough to hold all the flop registers. */ pulFlopBuffer = ( uint32_t * ) pvPortMalloc( portFLOP_STORAGE_SIZE ); - + if( pulFlopBuffer != NULL ) { /* Start with the registers in a benign state. */ memset( ( void * ) pulFlopBuffer, 0x00, portFLOP_STORAGE_SIZE ); - + /* The first thing to get saved in the buffer is the FPSCR value - initialise this to the current FPSCR value. */ *pulFlopBuffer = get_fpscr(); - - /* Use the task tag to point to the flop buffer. Pass pointer to just + + /* Use the task tag to point to the flop buffer. Pass pointer to just above the buffer because the flop save routine uses a pre-decrement. */ - vTaskSetApplicationTaskTag( xTask, ( void * ) ( pulFlopBuffer + portFLOP_REGISTERS_TO_STORE ) ); + vTaskSetApplicationTaskTag( xTask, ( void * ) ( pulFlopBuffer + portFLOP_REGISTERS_TO_STORE ) ); xReturn = pdPASS; } else { xReturn = pdFAIL; } - + return xReturn; } /*-----------------------------------------------------------*/ diff --git a/FreeRTOS/Source/portable/WizC/PIC18/port.c b/FreeRTOS/Source/portable/WizC/PIC18/port.c index 04f57a034..7a8fc202c 100644 --- a/FreeRTOS/Source/portable/WizC/PIC18/port.c +++ b/FreeRTOS/Source/portable/WizC/PIC18/port.c @@ -70,7 +70,7 @@ /* Changes from V3.2.1 + CallReturn Depth increased from 8 to 10 levels to accomodate wizC/fedC V12. - + Changes from V3.2.0 + TBLPTRU is now initialised to zero during the initial stack creation of a new task. This solves an error on devices with more than 64kB ROM. @@ -134,7 +134,7 @@ uint16_t usCalcMinStackSize = 0; /*-----------------------------------------------------------*/ /* - * We initialise ucCriticalNesting to the middle value an + * We initialise ucCriticalNesting to the middle value an * uint8_t can contain. This way portENTER_CRITICAL() * and portEXIT_CRITICAL() can be called without interrupts * being enabled before the scheduler starts. @@ -143,9 +143,9 @@ register uint8_t ucCriticalNesting = 0x7F; /*-----------------------------------------------------------*/ -/* +/* * Initialise the stack of a new task. - * See portSAVE_CONTEXT macro for description. + * See portSAVE_CONTEXT macro for description. */ StackType_t *pxPortInitialiseStack( StackType_t *pxTopOfStack, TaskFunction_t pxCode, void *pvParameters ) { @@ -161,7 +161,7 @@ uint8_t ucScratch; ucScratch = PRODL; /* - * Place a few bytes of known values on the bottom of the stack. + * Place a few bytes of known values on the bottom of the stack. * This is just useful for debugging. */ // *pxTopOfStack-- = 0x11; @@ -210,10 +210,10 @@ uint8_t ucScratch; { *pxTopOfStack-- = ( StackType_t ) 0; } - + /* * The only function return address so far is the address of the task entry. - * The order is TOSU/TOSH/TOSL. For devices > 64kB, TOSU is put on the + * The order is TOSU/TOSH/TOSL. For devices > 64kB, TOSU is put on the * stack, too. TOSU is always written as zero here because wizC does not allow * functionpointers to point above 64kB in ROM. */ @@ -231,12 +231,12 @@ uint8_t ucScratch; /* * The code generated by wizC does not maintain separate - * stack and frame pointers. Therefore the portENTER_CRITICAL macro cannot + * stack and frame pointers. Therefore the portENTER_CRITICAL macro cannot * use the stack as per other ports. Instead a variable is used to keep * track of the critical section nesting. This variable has to be stored * as part of the task context and is initially set to zero. */ - *pxTopOfStack-- = ( StackType_t ) portNO_CRITICAL_SECTION_NESTING; + *pxTopOfStack-- = ( StackType_t ) portNO_CRITICAL_SECTION_NESTING; return pxTopOfStack; } @@ -272,7 +272,7 @@ BaseType_t xPortStartScheduler( void ) /* * Setup a timer for the tick ISR for the preemptive scheduler. */ - portSetupTick(); + portSetupTick(); /* * Restore the context of the first task to run. @@ -321,30 +321,39 @@ void vPortYield( void ) */ portRESTORE_CONTEXT(); } - /*-----------------------------------------------------------*/ -void *pvPortMalloc( uint16_t usWantedSize ) -{ -void *pvReturn; +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) - vTaskSuspendAll(); + void *pvPortMalloc( uint16_t usWantedSize ) { - pvReturn = malloc( ( malloc_t ) usWantedSize ); + void *pvReturn; + + vTaskSuspendAll(); + { + pvReturn = malloc( ( malloc_t ) usWantedSize ); + } + xTaskResumeAll(); + + return pvReturn; } - xTaskResumeAll(); - return pvReturn; -} +#endif /* configSUPPORT_STATIC_ALLOCATION */ -void vPortFree( void *pv ) -{ - if( pv ) +/*-----------------------------------------------------------*/ + +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + + void vPortFree( void *pv ) { - vTaskSuspendAll(); + if( pv ) { - free( pv ); + vTaskSuspendAll(); + { + free( pv ); + } + xTaskResumeAll(); } - xTaskResumeAll(); } -} + +#endif /* configSUPPORT_STATIC_ALLOCATION */ \ No newline at end of file diff --git a/FreeRTOS/Source/queue.c b/FreeRTOS/Source/queue.c index 1a230b786..fe1ed0efa 100644 --- a/FreeRTOS/Source/queue.c +++ b/FreeRTOS/Source/queue.c @@ -90,9 +90,9 @@ privileged Vs unprivileged linkage and placement. */ #undef MPU_WRAPPERS_INCLUDED_FROM_API_FILE /*lint !e961 !e750. */ -/* Constants used with the xRxLock and xTxLock structure members. */ -#define queueUNLOCKED ( ( BaseType_t ) -1 ) -#define queueLOCKED_UNMODIFIED ( ( BaseType_t ) 0 ) +/* Constants used with the cRxLock and cTxLock structure members. */ +#define queueUNLOCKED ( ( int8_t ) -1 ) +#define queueLOCKED_UNMODIFIED ( ( int8_t ) 0 ) /* When the Queue_t structure is used to represent a base queue its pcHead and pcTail members are used as pointers into the queue storage area. When the @@ -114,13 +114,6 @@ zero. */ #define queueSEMAPHORE_QUEUE_ITEM_LENGTH ( ( UBaseType_t ) 0 ) #define queueMUTEX_GIVE_BLOCK_TIME ( ( TickType_t ) 0U ) -/* Bits that can be set in xQUEUE->ucStaticAllocationFlags to indicate that the -queue storage area and queue structure were statically allocated respectively. -When these are statically allocated they won't be freed if the queue gets -deleted. */ -#define queueSTATICALLY_ALLOCATED_STORAGE ( ( uint8_t ) 0x01 ) -#define queueSTATICALLY_ALLOCATED_QUEUE_STRUCT ( ( uint8_t ) 0x02 ) - #if( configUSE_PREEMPTION == 0 ) /* If the cooperative scheduler is being used then a yield should not be performed just because a higher priority task has been woken. */ @@ -153,8 +146,12 @@ typedef struct QueueDefinition UBaseType_t uxLength; /*< The length of the queue defined as the number of items it will hold, not the number of bytes. */ UBaseType_t uxItemSize; /*< The size of each items that the queue will hold. */ - volatile BaseType_t xRxLock; /*< Stores the number of items received from the queue (removed from the queue) while the queue was locked. Set to queueUNLOCKED when the queue is not locked. */ - volatile BaseType_t xTxLock; /*< Stores the number of items transmitted to the queue (added to the queue) while the queue was locked. Set to queueUNLOCKED when the queue is not locked. */ + volatile int8_t cRxLock; /*< Stores the number of items received from the queue (removed from the queue) while the queue was locked. Set to queueUNLOCKED when the queue is not locked. */ + volatile int8_t cTxLock; /*< Stores the number of items transmitted to the queue (added to the queue) while the queue was locked. Set to queueUNLOCKED when the queue is not locked. */ + + #if( ( configSUPPORT_STATIC_ALLOCATION == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) + uint8_t ucStaticallyAllocated; /*< Set to pdTRUE if the memory used by the queue was statically allocated to ensure no attempt is made to free the memory. */ + #endif #if ( configUSE_QUEUE_SETS == 1 ) struct QueueDefinition *pxQueueSetContainer; @@ -165,10 +162,6 @@ typedef struct QueueDefinition uint8_t ucQueueType; #endif - #if ( configSUPPORT_STATIC_ALLOCATION == 1 ) - uint8_t ucStaticAllocationFlags; - #endif - } xQUEUE; /* The old xQUEUE name is maintained above then typedefed to the new Queue_t @@ -239,17 +232,6 @@ static BaseType_t prvCopyDataToQueue( Queue_t * const pxQueue, const void *pvIte */ static void prvCopyDataFromQueue( Queue_t * const pxQueue, void * const pvBuffer ) PRIVILEGED_FUNCTION; -/* - * A queue requires two blocks of memory; a structure to hold the queue state - * and a storage area to hold the items in the queue. The memory is assigned - * by prvAllocateQueueMemory(). If ppucQueueStorage is NULL then the queue - * storage will allocated dynamically, otherwise the buffer passed in - * ppucQueueStorage will be used. If pxStaticQueue is NULL then the queue - * structure will be allocated dynamically, otherwise the buffer pointed to by - * pxStaticQueue will be used. - */ -static Queue_t *prvAllocateQueueMemory( const UBaseType_t uxQueueLength, const UBaseType_t uxItemSize, uint8_t **ppucQueueStorage, StaticQueue_t *pxStaticQueue ) PRIVILEGED_FUNCTION; - #if ( configUSE_QUEUE_SETS == 1 ) /* * Checks to see if a queue is a member of a queue set, and if so, notifies @@ -258,6 +240,19 @@ static Queue_t *prvAllocateQueueMemory( const UBaseType_t uxQueueLength, const U static BaseType_t prvNotifyQueueSetContainer( const Queue_t * const pxQueue, const BaseType_t xCopyPosition ) PRIVILEGED_FUNCTION; #endif +/* + * Called after a Queue_t structure has been allocated either statically or + * dynamically to fill in the structure's members. + */ +static void prvInitialiseNewQueue( const UBaseType_t uxQueueLength, const UBaseType_t uxItemSize, uint8_t *pucQueueStorage, const uint8_t ucQueueType, Queue_t *pxNewQueue ) PRIVILEGED_FUNCTION; + +/* + * Mutexes are a special type of queue. When a mutex is created, first the + * queue is created, then prvInitialiseMutex() is called to configure the queue + * as a mutex. + */ +static void prvInitialiseMutex( Queue_t *pxNewQueue ); + /*-----------------------------------------------------------*/ /* @@ -267,13 +262,13 @@ static Queue_t *prvAllocateQueueMemory( const UBaseType_t uxQueueLength, const U #define prvLockQueue( pxQueue ) \ taskENTER_CRITICAL(); \ { \ - if( ( pxQueue )->xRxLock == queueUNLOCKED ) \ + if( ( pxQueue )->cRxLock == queueUNLOCKED ) \ { \ - ( pxQueue )->xRxLock = queueLOCKED_UNMODIFIED; \ + ( pxQueue )->cRxLock = queueLOCKED_UNMODIFIED; \ } \ - if( ( pxQueue )->xTxLock == queueUNLOCKED ) \ + if( ( pxQueue )->cTxLock == queueUNLOCKED ) \ { \ - ( pxQueue )->xTxLock = queueLOCKED_UNMODIFIED; \ + ( pxQueue )->cTxLock = queueLOCKED_UNMODIFIED; \ } \ } \ taskEXIT_CRITICAL() @@ -291,8 +286,8 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue; pxQueue->uxMessagesWaiting = ( UBaseType_t ) 0U; pxQueue->pcWriteTo = pxQueue->pcHead; pxQueue->u.pcReadFrom = pxQueue->pcHead + ( ( pxQueue->uxLength - ( UBaseType_t ) 1U ) * pxQueue->uxItemSize ); - pxQueue->xRxLock = queueUNLOCKED; - pxQueue->xTxLock = queueUNLOCKED; + pxQueue->cRxLock = queueUNLOCKED; + pxQueue->cTxLock = queueUNLOCKED; if( xNewQueue == pdFALSE ) { @@ -332,207 +327,203 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue; } /*-----------------------------------------------------------*/ -static Queue_t *prvAllocateQueueMemory( const UBaseType_t uxQueueLength, const UBaseType_t uxItemSize, uint8_t **ppucQueueStorage, StaticQueue_t *pxStaticQueue ) -{ -Queue_t *pxNewQueue; -size_t xQueueSizeInBytes; - - configASSERT( uxQueueLength > ( UBaseType_t ) 0 ); +#if( configSUPPORT_STATIC_ALLOCATION == 1 ) - #if( ( configASSERT_DEFINED == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 1 ) ) + QueueHandle_t xQueueGenericCreateStatic( const UBaseType_t uxQueueLength, const UBaseType_t uxItemSize, uint8_t *pucQueueStorage, StaticQueue_t *pxStaticQueue, const uint8_t ucQueueType ) { - /* Sanity check that the size of the structure used to declare a - variable of type StaticQueue_t or StaticSemaphore_t equals the size of - the real queue and semaphore structures. */ - volatile size_t xSize = sizeof( StaticQueue_t ); - configASSERT( xSize == sizeof( Queue_t ) ); - } - #endif /* configASSERT_DEFINED */ + Queue_t *pxNewQueue; - if( uxItemSize == ( UBaseType_t ) 0 ) - { - /* There is not going to be a queue storage area. */ - xQueueSizeInBytes = ( size_t ) 0; - } - else - { - /* Allocate enough space to hold the maximum number of items that can be - in the queue at any time. */ - xQueueSizeInBytes = ( size_t ) ( uxQueueLength * uxItemSize ); /*lint !e961 MISRA exception as the casts are only redundant for some ports. */ - } + configASSERT( uxQueueLength > ( UBaseType_t ) 0 ); - #if( configSUPPORT_STATIC_ALLOCATION == 0 ) - { - /* Allocate the new queue structure and storage area. */ - pxNewQueue = ( Queue_t * ) pvPortMalloc( sizeof( Queue_t ) + xQueueSizeInBytes ); + /* The StaticQueue_t structure and the queue storage area must be + supplied. */ + configASSERT( pxStaticQueue != NULL ); + + /* A queue storage area should be provided if the item size is not 0, and + should not be provided if the item size is 0. */ + configASSERT( !( ( pucQueueStorage != NULL ) && ( uxItemSize == 0 ) ) ); + configASSERT( !( ( pucQueueStorage == NULL ) && ( uxItemSize != 0 ) ) ); + + #if( configASSERT_DEFINED == 1 ) + { + /* Sanity check that the size of the structure used to declare a + variable of type StaticQueue_t or StaticSemaphore_t equals the size of + the real queue and semaphore structures. */ + volatile size_t xSize = sizeof( StaticQueue_t ); + configASSERT( xSize == sizeof( Queue_t ) ); + } + #endif /* configASSERT_DEFINED */ + + /* The address of a statically allocated queue was passed in, use it. + The address of a statically allocated storage area was also passed in + but is already set. */ + pxNewQueue = ( Queue_t * ) pxStaticQueue; /*lint !e740 Unusual cast is ok as the structures are designed to have the same alignment, and the size is checked by an assert. */ if( pxNewQueue != NULL ) { - /* Jump past the queue structure to find the location of the queue - storage area. */ - *ppucQueueStorage = ( ( uint8_t * ) pxNewQueue ) + sizeof( Queue_t ); + #if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + { + /* Queues can be allocated wither statically or dynamically, so + note this queue was allocated statically in case the queue is + later deleted. */ + pxNewQueue->ucStaticallyAllocated = pdTRUE; + } + #endif /* configSUPPORT_DYNAMIC_ALLOCATION */ + + prvInitialiseNewQueue( uxQueueLength, uxItemSize, pucQueueStorage, ucQueueType, pxNewQueue ); } - /* The pxStaticQueue parameter is not used. Remove compiler warnings. */ - ( void ) pxStaticQueue; + return pxNewQueue; } - #else + +#endif /* configSUPPORT_STATIC_ALLOCATION */ +/*-----------------------------------------------------------*/ + +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + + QueueHandle_t xQueueGenericCreate( const UBaseType_t uxQueueLength, const UBaseType_t uxItemSize, const uint8_t ucQueueType ) { - if( pxStaticQueue == NULL ) + Queue_t *pxNewQueue; + size_t xQueueSizeInBytes; + uint8_t *pucQueueStorage; + + configASSERT( uxQueueLength > ( UBaseType_t ) 0 ); + + if( uxItemSize == ( UBaseType_t ) 0 ) { - /* A statically allocated queue was not passed in, so create one - dynamically. */ - pxNewQueue = ( Queue_t * ) pvPortMalloc( sizeof( Queue_t ) ); - pxNewQueue->ucStaticAllocationFlags = 0; + /* There is not going to be a queue storage area. */ + xQueueSizeInBytes = ( size_t ) 0; } else { - /* The address of a statically allocated queue was passed in, use - it and note that the queue was not dynamically allocated so there is - no attempt to free it again should the queue be deleted. */ - pxNewQueue = ( Queue_t * ) pxStaticQueue; /*lint !e740 Unusual cast is ok as the structures are designed to have the same alignment, and the size is checked by an assert. */ - pxNewQueue->ucStaticAllocationFlags = queueSTATICALLY_ALLOCATED_QUEUE_STRUCT; + /* Allocate enough space to hold the maximum number of items that + can be in the queue at any time. */ + xQueueSizeInBytes = ( size_t ) ( uxQueueLength * uxItemSize ); /*lint !e961 MISRA exception as the casts are only redundant for some ports. */ } + pxNewQueue = ( Queue_t * ) pvPortMalloc( sizeof( Queue_t ) + xQueueSizeInBytes ); + if( pxNewQueue != NULL ) { - if( ( *ppucQueueStorage == NULL ) && ( xQueueSizeInBytes > ( size_t ) 0 ) ) - { - /* A statically allocated queue storage area was not passed in, - so allocate the queue storage area dynamically. */ - *ppucQueueStorage = ( uint8_t * ) pvPortMalloc( xQueueSizeInBytes ); - - if( *ppucQueueStorage == NULL ) - { - /* The queue storage area could not be created, so free the - queue structure also. */ - if( ( pxNewQueue->ucStaticAllocationFlags & queueSTATICALLY_ALLOCATED_QUEUE_STRUCT ) == 0 ) - { - vPortFree( ( void * ) pxNewQueue ); - } - else - { - mtCOVERAGE_TEST_MARKER(); - } + /* Jump past the queue structure to find the location of the queue + storage area. */ + pucQueueStorage = ( ( uint8_t * ) pxNewQueue ) + sizeof( Queue_t ); - pxNewQueue = NULL; - } - else - { - mtCOVERAGE_TEST_MARKER(); - } - } - else + #if( configSUPPORT_STATIC_ALLOCATION == 1 ) { - /* Note the fact that either the queue storage area was passed - into this function, or the size requirement for the queue - storage area was zero - either way no attempt should be made to - free the queue storage area if the queue is deleted. */ - pxNewQueue->ucStaticAllocationFlags |= queueSTATICALLY_ALLOCATED_STORAGE; + /* Queues can be created either statically or dynamically, so + note this task was created dynamically in case it is later + deleted. */ + pxNewQueue->ucStaticallyAllocated = pdFALSE; } + #endif /* configSUPPORT_STATIC_ALLOCATION */ + + prvInitialiseNewQueue( uxQueueLength, uxItemSize, pucQueueStorage, ucQueueType, pxNewQueue ); } + + return pxNewQueue; } - #endif - return pxNewQueue; -} +#endif /* configSUPPORT_STATIC_ALLOCATION */ /*-----------------------------------------------------------*/ -QueueHandle_t xQueueGenericCreate( const UBaseType_t uxQueueLength, const UBaseType_t uxItemSize, uint8_t *pucQueueStorage, StaticQueue_t *pxStaticQueue, const uint8_t ucQueueType ) +static void prvInitialiseNewQueue( const UBaseType_t uxQueueLength, const UBaseType_t uxItemSize, uint8_t *pucQueueStorage, const uint8_t ucQueueType, Queue_t *pxNewQueue ) { -Queue_t *pxNewQueue; - /* Remove compiler warnings about unused parameters should configUSE_TRACE_FACILITY not be set to 1. */ ( void ) ucQueueType; - /* A queue requires a queue structure and a queue storage area. These may - be allocated statically or dynamically, depending on the parameter - values. */ - pxNewQueue = prvAllocateQueueMemory( uxQueueLength, uxItemSize, &pucQueueStorage, pxStaticQueue ); + if( uxItemSize == ( UBaseType_t ) 0 ) + { + /* No RAM was allocated for the queue storage area, but PC head cannot + be set to NULL because NULL is used as a key to say the queue is used as + a mutex. Therefore just set pcHead to point to the queue as a benign + value that is known to be within the memory map. */ + pxNewQueue->pcHead = ( int8_t * ) pxNewQueue; + } + else + { + /* Set the head to the start of the queue storage area. */ + pxNewQueue->pcHead = ( int8_t * ) pucQueueStorage; + } - if( pxNewQueue != NULL ) + /* Initialise the queue members as described where the queue type is + defined. */ + pxNewQueue->uxLength = uxQueueLength; + pxNewQueue->uxItemSize = uxItemSize; + ( void ) xQueueGenericReset( pxNewQueue, pdTRUE ); + + #if ( configUSE_TRACE_FACILITY == 1 ) { - if( uxItemSize == ( UBaseType_t ) 0 ) - { - /* No RAM was allocated for the queue storage area, but PC head - cannot be set to NULL because NULL is used as a key to say the queue - is used as a mutex. Therefore just set pcHead to point to the queue - as a benign value that is known to be within the memory map. */ - pxNewQueue->pcHead = ( int8_t * ) pxNewQueue; - } - else - { - /* Set the head to the start of the queue storage area. */ - pxNewQueue->pcHead = ( int8_t * ) pucQueueStorage; - } + pxNewQueue->ucQueueType = ucQueueType; + } + #endif /* configUSE_TRACE_FACILITY */ + + #if( configUSE_QUEUE_SETS == 1 ) + { + pxNewQueue->pxQueueSetContainer = NULL; + } + #endif /* configUSE_QUEUE_SETS */ - /* Initialise the queue members as described where the queue type is - defined. */ - pxNewQueue->uxLength = uxQueueLength; - pxNewQueue->uxItemSize = uxItemSize; - ( void ) xQueueGenericReset( pxNewQueue, pdTRUE ); + traceQUEUE_CREATE( pxNewQueue ); +} +/*-----------------------------------------------------------*/ - #if ( configUSE_TRACE_FACILITY == 1 ) - { - pxNewQueue->ucQueueType = ucQueueType; - } - #endif /* configUSE_TRACE_FACILITY */ +static void prvInitialiseMutex( Queue_t *pxNewQueue ) +{ + if( pxNewQueue != NULL ) + { + /* The queue create function will set all the queue structure members + correctly for a generic queue, but this function is creating a + mutex. Overwrite those members that need to be set differently - + in particular the information required for priority inheritance. */ + pxNewQueue->pxMutexHolder = NULL; + pxNewQueue->uxQueueType = queueQUEUE_IS_MUTEX; - #if( configUSE_QUEUE_SETS == 1 ) - { - pxNewQueue->pxQueueSetContainer = NULL; - } - #endif /* configUSE_QUEUE_SETS */ + /* In case this is a recursive mutex. */ + pxNewQueue->u.uxRecursiveCallCount = 0; - traceQUEUE_CREATE( pxNewQueue ); + traceCREATE_MUTEX( pxNewQueue ); + + /* Start with the semaphore in the expected state. */ + ( void ) xQueueGenericSend( pxNewQueue, NULL, ( TickType_t ) 0U, queueSEND_TO_BACK ); } else { - mtCOVERAGE_TEST_MARKER(); + traceCREATE_MUTEX_FAILED(); } - - configASSERT( pxNewQueue ); - - return ( QueueHandle_t ) pxNewQueue; } /*-----------------------------------------------------------*/ -#if ( configUSE_MUTEXES == 1 ) +#if( ( configUSE_MUTEXES == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) - QueueHandle_t xQueueCreateMutex( const uint8_t ucQueueType, StaticQueue_t *pxStaticQueue ) + QueueHandle_t xQueueCreateMutex( const uint8_t ucQueueType ) { Queue_t *pxNewQueue; const UBaseType_t uxMutexLength = ( UBaseType_t ) 1, uxMutexSize = ( UBaseType_t ) 0; - /* Prevent compiler warnings about unused parameters if - configUSE_TRACE_FACILITY does not equal 1. */ - ( void ) ucQueueType; + pxNewQueue = ( Queue_t * ) xQueueGenericCreate( uxMutexLength, uxMutexSize, ucQueueType ); + prvInitialiseMutex( pxNewQueue ); - pxNewQueue = ( Queue_t * ) xQueueGenericCreate( uxMutexLength, uxMutexSize, NULL, pxStaticQueue, ucQueueType ); + return pxNewQueue; + } - /* Allocate the new queue structure. */ - if( pxNewQueue != NULL ) - { - /* xQueueGenericCreate() will set all the queue structure members - correctly for a generic queue, but this function is creating a - mutex. Overwrite those members that need to be set differently - - in particular the information required for priority inheritance. */ - pxNewQueue->pxMutexHolder = NULL; - pxNewQueue->uxQueueType = queueQUEUE_IS_MUTEX; +#endif /* configUSE_MUTEXES */ +/*-----------------------------------------------------------*/ - /* In case this is a recursive mutex. */ - pxNewQueue->u.uxRecursiveCallCount = 0; +#if( ( configUSE_MUTEXES == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 1 ) ) - traceCREATE_MUTEX( pxNewQueue ); + QueueHandle_t xQueueCreateMutexStatic( const uint8_t ucQueueType, StaticQueue_t *pxStaticQueue ) + { + Queue_t *pxNewQueue; + const UBaseType_t uxMutexLength = ( UBaseType_t ) 1, uxMutexSize = ( UBaseType_t ) 0; - /* Start with the semaphore in the expected state. */ - ( void ) xQueueGenericSend( pxNewQueue, NULL, ( TickType_t ) 0U, queueSEND_TO_BACK ); - } - else - { - traceCREATE_MUTEX_FAILED(); - } + /* Prevent compiler warnings about unused parameters if + configUSE_TRACE_FACILITY does not equal 1. */ + ( void ) ucQueueType; + + pxNewQueue = ( Queue_t * ) xQueueGenericCreateStatic( uxMutexLength, uxMutexSize, NULL, pxStaticQueue, ucQueueType ); + prvInitialiseMutex( pxNewQueue ); return pxNewQueue; } @@ -667,16 +658,16 @@ Queue_t *pxNewQueue; #endif /* configUSE_RECURSIVE_MUTEXES */ /*-----------------------------------------------------------*/ -#if ( configUSE_COUNTING_SEMAPHORES == 1 ) +#if( ( configUSE_COUNTING_SEMAPHORES == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 1 ) ) - QueueHandle_t xQueueCreateCountingSemaphore( const UBaseType_t uxMaxCount, const UBaseType_t uxInitialCount, StaticQueue_t *pxStaticQueue ) + QueueHandle_t xQueueCreateCountingSemaphoreStatic( const UBaseType_t uxMaxCount, const UBaseType_t uxInitialCount, StaticQueue_t *pxStaticQueue ) { QueueHandle_t xHandle; configASSERT( uxMaxCount != 0 ); configASSERT( uxInitialCount <= uxMaxCount ); - xHandle = xQueueGenericCreate( uxMaxCount, queueSEMAPHORE_QUEUE_ITEM_LENGTH, NULL, pxStaticQueue, queueQUEUE_TYPE_COUNTING_SEMAPHORE ); + xHandle = xQueueGenericCreateStatic( uxMaxCount, queueSEMAPHORE_QUEUE_ITEM_LENGTH, NULL, pxStaticQueue, queueQUEUE_TYPE_COUNTING_SEMAPHORE ); if( xHandle != NULL ) { @@ -689,11 +680,38 @@ Queue_t *pxNewQueue; traceCREATE_COUNTING_SEMAPHORE_FAILED(); } - configASSERT( xHandle ); return xHandle; } -#endif /* configUSE_COUNTING_SEMAPHORES */ +#endif /* ( ( configUSE_COUNTING_SEMAPHORES == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) */ +/*-----------------------------------------------------------*/ + +#if( ( configUSE_COUNTING_SEMAPHORES == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) + + QueueHandle_t xQueueCreateCountingSemaphore( const UBaseType_t uxMaxCount, const UBaseType_t uxInitialCount ) + { + QueueHandle_t xHandle; + + configASSERT( uxMaxCount != 0 ); + configASSERT( uxInitialCount <= uxMaxCount ); + + xHandle = xQueueGenericCreate( uxMaxCount, queueSEMAPHORE_QUEUE_ITEM_LENGTH, queueQUEUE_TYPE_COUNTING_SEMAPHORE ); + + if( xHandle != NULL ) + { + ( ( Queue_t * ) xHandle )->uxMessagesWaiting = uxInitialCount; + + traceCREATE_COUNTING_SEMAPHORE(); + } + else + { + traceCREATE_COUNTING_SEMAPHORE_FAILED(); + } + + return xHandle; + } + +#endif /* ( ( configUSE_COUNTING_SEMAPHORES == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) */ /*-----------------------------------------------------------*/ BaseType_t xQueueGenericSend( QueueHandle_t xQueue, const void * const pvItemToQueue, TickType_t xTicksToWait, const BaseType_t xCopyPosition ) @@ -940,7 +958,7 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue; /* The event list is not altered if the queue is locked. This will be done when the queue is unlocked later. */ - if( pxQueue->xTxLock == queueUNLOCKED ) + if( pxQueue->cTxLock == queueUNLOCKED ) { #if ( configUSE_QUEUE_SETS == 1 ) { @@ -1026,7 +1044,7 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue; { /* Increment the lock count so the task that unlocks the queue knows that data was posted while it was locked. */ - ++( pxQueue->xTxLock ); + ++( pxQueue->cTxLock ); } xReturn = pdPASS; @@ -1101,7 +1119,7 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue; /* The event list is not altered if the queue is locked. This will be done when the queue is unlocked later. */ - if( pxQueue->xTxLock == queueUNLOCKED ) + if( pxQueue->cTxLock == queueUNLOCKED ) { #if ( configUSE_QUEUE_SETS == 1 ) { @@ -1187,7 +1205,7 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue; { /* Increment the lock count so the task that unlocks the queue knows that data was posted while it was locked. */ - ++( pxQueue->xTxLock ); + ++( pxQueue->cTxLock ); } xReturn = pdPASS; @@ -1438,7 +1456,7 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue; Instead update the lock count so the task that unlocks the queue will know that an ISR has removed data while the queue was locked. */ - if( pxQueue->xRxLock == queueUNLOCKED ) + if( pxQueue->cRxLock == queueUNLOCKED ) { if( listLIST_IS_EMPTY( &( pxQueue->xTasksWaitingToSend ) ) == pdFALSE ) { @@ -1469,7 +1487,7 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue; { /* Increment the lock count so the task that unlocks the queue knows that data was removed while it was locked. */ - ++( pxQueue->xRxLock ); + ++( pxQueue->cRxLock ); } xReturn = pdPASS; @@ -1591,37 +1609,26 @@ void vQueueDelete( QueueHandle_t xQueue ) Queue_t * const pxQueue = ( Queue_t * ) xQueue; configASSERT( pxQueue ); - traceQUEUE_DELETE( pxQueue ); + #if ( configQUEUE_REGISTRY_SIZE > 0 ) { vQueueUnregisterQueue( pxQueue ); } #endif - #if( configSUPPORT_STATIC_ALLOCATION == 0 ) + #if( ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 0 ) ) { - /* The queue and the queue storage area will have been dynamically - allocated in one go. */ + /* The queue can only have been allocated dynamically - free it + again. */ vPortFree( pxQueue ); } - #else + #elif( ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 1 ) ) { - if( ( pxQueue->ucStaticAllocationFlags & queueSTATICALLY_ALLOCATED_STORAGE ) == 0 ) + /* The queue could have been allocated statically or dynamically, so + check before attempting to free the memory. */ + if( pxQueue->ucStaticallyAllocated == ( uint8_t ) pdFALSE ) { - /* The queue storage area was dynamically allocated, so must be - freed. */ - vPortFree( pxQueue->pcHead ); - } - else - { - mtCOVERAGE_TEST_MARKER(); - } - - if( ( pxQueue->ucStaticAllocationFlags & queueSTATICALLY_ALLOCATED_QUEUE_STRUCT ) == 0 ) - { - /* The queue structure was dynamically allocated, so must be - free. */ vPortFree( pxQueue ); } else @@ -1629,7 +1636,7 @@ Queue_t * const pxQueue = ( Queue_t * ) xQueue; mtCOVERAGE_TEST_MARKER(); } } - #endif + #endif /* configSUPPORT_DYNAMIC_ALLOCATION */ } /*-----------------------------------------------------------*/ @@ -1766,7 +1773,7 @@ static void prvUnlockQueue( Queue_t * const pxQueue ) taskENTER_CRITICAL(); { /* See if data was added to the queue while it was locked. */ - while( pxQueue->xTxLock > queueLOCKED_UNMODIFIED ) + while( pxQueue->cTxLock > queueLOCKED_UNMODIFIED ) { /* Data was posted while the queue was locked. Are any tasks blocked waiting for data to become available? */ @@ -1834,17 +1841,17 @@ static void prvUnlockQueue( Queue_t * const pxQueue ) } #endif /* configUSE_QUEUE_SETS */ - --( pxQueue->xTxLock ); + --( pxQueue->cTxLock ); } - pxQueue->xTxLock = queueUNLOCKED; + pxQueue->cTxLock = queueUNLOCKED; } taskEXIT_CRITICAL(); /* Do the same for the Rx lock. */ taskENTER_CRITICAL(); { - while( pxQueue->xRxLock > queueLOCKED_UNMODIFIED ) + while( pxQueue->cRxLock > queueLOCKED_UNMODIFIED ) { if( listLIST_IS_EMPTY( &( pxQueue->xTasksWaitingToSend ) ) == pdFALSE ) { @@ -1857,7 +1864,7 @@ static void prvUnlockQueue( Queue_t * const pxQueue ) mtCOVERAGE_TEST_MARKER(); } - --( pxQueue->xRxLock ); + --( pxQueue->cRxLock ); } else { @@ -1865,7 +1872,7 @@ static void prvUnlockQueue( Queue_t * const pxQueue ) } } - pxQueue->xRxLock = queueUNLOCKED; + pxQueue->cRxLock = queueUNLOCKED; } taskEXIT_CRITICAL(); } @@ -2349,13 +2356,13 @@ BaseType_t xReturn; #endif /* configUSE_TIMERS */ /*-----------------------------------------------------------*/ -#if ( configUSE_QUEUE_SETS == 1 ) +#if( ( configUSE_QUEUE_SETS == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) QueueSetHandle_t xQueueCreateSet( const UBaseType_t uxEventQueueLength ) { QueueSetHandle_t pxQueue; - pxQueue = xQueueGenericCreate( uxEventQueueLength, sizeof( Queue_t * ), NULL, NULL, queueQUEUE_TYPE_SET ); + pxQueue = xQueueGenericCreate( uxEventQueueLength, sizeof( Queue_t * ), queueQUEUE_TYPE_SET ); return pxQueue; } @@ -2477,7 +2484,7 @@ BaseType_t xReturn; /* The data copied is the handle of the queue that contains data. */ xReturn = prvCopyDataToQueue( pxQueueSetContainer, &pxQueue, xCopyPosition ); - if( pxQueueSetContainer->xTxLock == queueUNLOCKED ) + if( pxQueueSetContainer->cTxLock == queueUNLOCKED ) { if( listLIST_IS_EMPTY( &( pxQueueSetContainer->xTasksWaitingToReceive ) ) == pdFALSE ) { @@ -2498,7 +2505,7 @@ BaseType_t xReturn; } else { - ( pxQueueSetContainer->xTxLock )++; + ( pxQueueSetContainer->cTxLock )++; } } else diff --git a/FreeRTOS/Source/tasks.c b/FreeRTOS/Source/tasks.c index 466151154..fdcc8f349 100644 --- a/FreeRTOS/Source/tasks.c +++ b/FreeRTOS/Source/tasks.c @@ -98,22 +98,6 @@ functions but without including stdio.h here. */ #include #endif /* configUSE_STATS_FORMATTING_FUNCTIONS == 1 ) */ -/* Sanity check the configuration. */ -#if( configUSE_TICKLESS_IDLE != 0 ) - #if( INCLUDE_vTaskSuspend != 1 ) - #error INCLUDE_vTaskSuspend must be set to 1 if configUSE_TICKLESS_IDLE is not set to 0 - #endif /* INCLUDE_vTaskSuspend */ -#endif /* configUSE_TICKLESS_IDLE */ - -#if( ( portUSING_MPU_WRAPPERS == 1 ) && ( configSUPPORT_STATIC_ALLOCATION != 1 ) ) - #error configSUPPORT_STATIC_ALLOCATION must be set to 1 in FreeRTOSConfig.h when the MPU is used. -#endif - -/* - * Defines the size, in words, of the stack allocated to the idle task. - */ -#define tskIDLE_STACK_SIZE configMINIMAL_STACK_SIZE - #if( configUSE_PREEMPTION == 0 ) /* If the cooperative scheduler is being used then a yield should not be performed just because a higher priority task has been woken. */ @@ -122,164 +106,11 @@ functions but without including stdio.h here. */ #define taskYIELD_IF_USING_PREEMPTION() portYIELD_WITHIN_API() #endif -/* Bits that can be set in tskTCB->ucStaticAllocationFlags to indicate that the -stack and TCB were statically allocated respectively. When these are statically -allocated they won't be freed if the task using the stack and TCB gets -deleted. */ -#define taskSTATICALLY_ALLOCATED_STACK ( ( uint8_t ) 0x01 ) -#define taskSTATICALLY_ALLOCATED_TCB ( ( uint8_t ) 0x02 ) - /* Values that can be assigned to the ucNotifyState member of the TCB. */ #define taskNOT_WAITING_NOTIFICATION ( ( uint8_t ) 0 ) #define taskWAITING_NOTIFICATION ( ( uint8_t ) 1 ) #define taskNOTIFICATION_RECEIVED ( ( uint8_t ) 2 ) -/* - * Task control block. A task control block (TCB) is allocated for each task, - * and stores task state information, including a pointer to the task's context - * (the task's run time environment, including register values) - */ -typedef struct tskTaskControlBlock -{ - volatile StackType_t *pxTopOfStack; /*< Points to the location of the last item placed on the tasks stack. THIS MUST BE THE FIRST MEMBER OF THE TCB STRUCT. */ - - #if ( portUSING_MPU_WRAPPERS == 1 ) - xMPU_SETTINGS xMPUSettings; /*< The MPU settings are defined as part of the port layer. THIS MUST BE THE SECOND MEMBER OF THE TCB STRUCT. */ - #endif - - ListItem_t xStateListItem; /*< The list that the state list item of a task is reference from denotes the state of that task (Ready, Blocked, Suspended ). */ - ListItem_t xEventListItem; /*< Used to reference a task from an event list. */ - UBaseType_t uxPriority; /*< The priority of the task. 0 is the lowest priority. */ - StackType_t *pxStack; /*< Points to the start of the stack. */ - char pcTaskName[ configMAX_TASK_NAME_LEN ];/*< Descriptive name given to the task when created. Facilitates debugging only. */ /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ - - #if ( portSTACK_GROWTH > 0 ) - StackType_t *pxEndOfStack; /*< Points to the end of the stack on architectures where the stack grows up from low memory. */ - #endif - - #if ( portCRITICAL_NESTING_IN_TCB == 1 ) - UBaseType_t uxCriticalNesting; /*< Holds the critical section nesting depth for ports that do not maintain their own count in the port layer. */ - #endif - - #if ( configUSE_TRACE_FACILITY == 1 ) - UBaseType_t uxTCBNumber; /*< Stores a number that increments each time a TCB is created. It allows debuggers to determine when a task has been deleted and then recreated. */ - UBaseType_t uxTaskNumber; /*< Stores a number specifically for use by third party trace code. */ - #endif - - #if ( configUSE_MUTEXES == 1 ) - UBaseType_t uxBasePriority; /*< The priority last assigned to the task - used by the priority inheritance mechanism. */ - UBaseType_t uxMutexesHeld; - #endif - - #if ( configUSE_APPLICATION_TASK_TAG == 1 ) - TaskHookFunction_t pxTaskTag; - #endif - - #if( configNUM_THREAD_LOCAL_STORAGE_POINTERS > 0 ) - void *pvThreadLocalStoragePointers[ configNUM_THREAD_LOCAL_STORAGE_POINTERS ]; - #endif - - #if( configGENERATE_RUN_TIME_STATS == 1 ) - uint32_t ulRunTimeCounter; /*< Stores the amount of time the task has spent in the Running state. */ - #endif - - #if ( configUSE_NEWLIB_REENTRANT == 1 ) - /* Allocate a Newlib reent structure that is specific to this task. - Note Newlib support has been included by popular demand, but is not - used by the FreeRTOS maintainers themselves. FreeRTOS is not - responsible for resulting newlib operation. User must be familiar with - newlib and must provide system-wide implementations of the necessary - stubs. Be warned that (at the time of writing) the current newlib design - implements a system-wide malloc() that must be provided with locks. */ - struct _reent xNewLib_reent; - #endif - - #if( configUSE_TASK_NOTIFICATIONS == 1 ) - volatile uint32_t ulNotifiedValue; - volatile uint8_t ucNotifyState; - #endif - - #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - uint8_t ucStaticAllocationFlags; /* Set to pdTRUE if the stack is a statically allocated array, and pdFALSE if the stack is dynamically allocated. */ - #endif - - #if( INCLUDE_xTaskAbortDelay == 1 ) - uint8_t ucDelayAborted; - #endif - -} tskTCB; - -/* The old tskTCB name is maintained above then typedefed to the new TCB_t name -below to enable the use of older kernel aware debuggers. */ -typedef tskTCB TCB_t; - -/* - * Some kernel aware debuggers require the data the debugger needs access to be - * global, rather than file scope. - */ -#ifdef portREMOVE_STATIC_QUALIFIER - #define static -#endif - -/*lint -e956 A manual analysis and inspection has been used to determine which -static variables must be declared volatile. */ - -PRIVILEGED_DATA TCB_t * volatile pxCurrentTCB = NULL; - -/* Lists for ready and blocked tasks. --------------------*/ -PRIVILEGED_DATA static List_t pxReadyTasksLists[ configMAX_PRIORITIES ];/*< Prioritised ready tasks. */ -PRIVILEGED_DATA static List_t xDelayedTaskList1; /*< Delayed tasks. */ -PRIVILEGED_DATA static List_t xDelayedTaskList2; /*< Delayed tasks (two lists are used - one for delays that have overflowed the current tick count. */ -PRIVILEGED_DATA static List_t * volatile pxDelayedTaskList; /*< Points to the delayed task list currently being used. */ -PRIVILEGED_DATA static List_t * volatile pxOverflowDelayedTaskList; /*< Points to the delayed task list currently being used to hold tasks that have overflowed the current tick count. */ -PRIVILEGED_DATA static List_t xPendingReadyList; /*< Tasks that have been readied while the scheduler was suspended. They will be moved to the ready list when the scheduler is resumed. */ - -#if ( INCLUDE_vTaskDelete == 1 ) - - PRIVILEGED_DATA static List_t xTasksWaitingTermination; /*< Tasks that have been deleted - but their memory not yet freed. */ - PRIVILEGED_DATA static volatile UBaseType_t uxDeletedTasksWaitingCleanUp = ( UBaseType_t ) 0U; - -#endif - -#if ( INCLUDE_vTaskSuspend == 1 ) - - PRIVILEGED_DATA static List_t xSuspendedTaskList; /*< Tasks that are currently suspended. */ - -#endif - -/* Other file private variables. --------------------------------*/ -PRIVILEGED_DATA static volatile UBaseType_t uxCurrentNumberOfTasks = ( UBaseType_t ) 0U; -PRIVILEGED_DATA static volatile TickType_t xTickCount = ( TickType_t ) 0U; -PRIVILEGED_DATA static volatile UBaseType_t uxTopReadyPriority = tskIDLE_PRIORITY; -PRIVILEGED_DATA static volatile BaseType_t xSchedulerRunning = pdFALSE; -PRIVILEGED_DATA static volatile UBaseType_t uxPendedTicks = ( UBaseType_t ) 0U; -PRIVILEGED_DATA static volatile BaseType_t xYieldPending = pdFALSE; -PRIVILEGED_DATA static volatile BaseType_t xNumOfOverflows = ( BaseType_t ) 0; -PRIVILEGED_DATA static UBaseType_t uxTaskNumber = ( UBaseType_t ) 0U; -PRIVILEGED_DATA static volatile TickType_t xNextTaskUnblockTime = ( TickType_t ) 0U; /* Initialised to portMAX_DELAY before the scheduler starts. */ -PRIVILEGED_DATA static TaskHandle_t xIdleTaskHandle = NULL; /*< Holds the handle of the idle task. The idle task is created automatically when the scheduler is started. */ - -/* Context switches are held pending while the scheduler is suspended. Also, -interrupts must not manipulate the xStateListItem of a TCB, or any of the -lists the xStateListItem can be referenced from, if the scheduler is suspended. -If an interrupt needs to unblock a task while the scheduler is suspended then it -moves the task's event list item into the xPendingReadyList, ready for the -kernel to move the task from the pending ready list into the real ready list -when the scheduler is unsuspended. The pending ready list itself can only be -accessed from a critical section. */ -PRIVILEGED_DATA static volatile UBaseType_t uxSchedulerSuspended = ( UBaseType_t ) pdFALSE; - -#if ( configGENERATE_RUN_TIME_STATS == 1 ) - - PRIVILEGED_DATA static uint32_t ulTaskSwitchedInTime = 0UL; /*< Holds the value of a timer/counter the last time a task was switched in. */ - PRIVILEGED_DATA static uint32_t ulTotalRunTime = 0UL; /*< Holds the total amount of execution time as defined by the run time counter clock. */ - -#endif - -/*lint +e956 */ - -/* Debugging and trace facilities private variables and macros. ------------*/ - /* * The value used to fill the stack of a task when the task is created. This * is used purely for checking the high water mark for tasks. @@ -294,7 +125,13 @@ PRIVILEGED_DATA static volatile UBaseType_t uxSchedulerSuspended = ( UBaseType_t #define tskDELETED_CHAR ( 'D' ) #define tskSUSPENDED_CHAR ( 'S' ) -/*-----------------------------------------------------------*/ +/* + * Some kernel aware debuggers require the data the debugger needs access to be + * global, rather than file scope. + */ +#ifdef portREMOVE_STATIC_QUALIFIER + #define static +#endif #if ( configUSE_PORT_OPTIMISED_TASK_SELECTION == 0 ) @@ -425,6 +262,144 @@ to its original value when it is released. */ #define taskEVENT_LIST_ITEM_VALUE_IN_USE 0x80000000UL #endif +/* + * Task control block. A task control block (TCB) is allocated for each task, + * and stores task state information, including a pointer to the task's context + * (the task's run time environment, including register values) + */ +typedef struct tskTaskControlBlock +{ + volatile StackType_t *pxTopOfStack; /*< Points to the location of the last item placed on the tasks stack. THIS MUST BE THE FIRST MEMBER OF THE TCB STRUCT. */ + + #if ( portUSING_MPU_WRAPPERS == 1 ) + xMPU_SETTINGS xMPUSettings; /*< The MPU settings are defined as part of the port layer. THIS MUST BE THE SECOND MEMBER OF THE TCB STRUCT. */ + #endif + + ListItem_t xStateListItem; /*< The list that the state list item of a task is reference from denotes the state of that task (Ready, Blocked, Suspended ). */ + ListItem_t xEventListItem; /*< Used to reference a task from an event list. */ + UBaseType_t uxPriority; /*< The priority of the task. 0 is the lowest priority. */ + StackType_t *pxStack; /*< Points to the start of the stack. */ + char pcTaskName[ configMAX_TASK_NAME_LEN ];/*< Descriptive name given to the task when created. Facilitates debugging only. */ /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ + + #if ( portSTACK_GROWTH > 0 ) + StackType_t *pxEndOfStack; /*< Points to the end of the stack on architectures where the stack grows up from low memory. */ + #endif + + #if ( portCRITICAL_NESTING_IN_TCB == 1 ) + UBaseType_t uxCriticalNesting; /*< Holds the critical section nesting depth for ports that do not maintain their own count in the port layer. */ + #endif + + #if ( configUSE_TRACE_FACILITY == 1 ) + UBaseType_t uxTCBNumber; /*< Stores a number that increments each time a TCB is created. It allows debuggers to determine when a task has been deleted and then recreated. */ + UBaseType_t uxTaskNumber; /*< Stores a number specifically for use by third party trace code. */ + #endif + + #if ( configUSE_MUTEXES == 1 ) + UBaseType_t uxBasePriority; /*< The priority last assigned to the task - used by the priority inheritance mechanism. */ + UBaseType_t uxMutexesHeld; + #endif + + #if ( configUSE_APPLICATION_TASK_TAG == 1 ) + TaskHookFunction_t pxTaskTag; + #endif + + #if( configNUM_THREAD_LOCAL_STORAGE_POINTERS > 0 ) + void *pvThreadLocalStoragePointers[ configNUM_THREAD_LOCAL_STORAGE_POINTERS ]; + #endif + + #if( configGENERATE_RUN_TIME_STATS == 1 ) + uint32_t ulRunTimeCounter; /*< Stores the amount of time the task has spent in the Running state. */ + #endif + + #if ( configUSE_NEWLIB_REENTRANT == 1 ) + /* Allocate a Newlib reent structure that is specific to this task. + Note Newlib support has been included by popular demand, but is not + used by the FreeRTOS maintainers themselves. FreeRTOS is not + responsible for resulting newlib operation. User must be familiar with + newlib and must provide system-wide implementations of the necessary + stubs. Be warned that (at the time of writing) the current newlib design + implements a system-wide malloc() that must be provided with locks. */ + struct _reent xNewLib_reent; + #endif + + #if( configUSE_TASK_NOTIFICATIONS == 1 ) + volatile uint32_t ulNotifiedValue; + volatile uint8_t ucNotifyState; + #endif + + #if( ( configSUPPORT_STATIC_ALLOCATION == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) + uint8_t ucStaticallyAllocated; /* Set to pdTRUE if the task is a statically allocated to ensure no attempt is made to free the memory. */ + #endif + + #if( INCLUDE_xTaskAbortDelay == 1 ) + uint8_t ucDelayAborted; + #endif + +} tskTCB; + +/* The old tskTCB name is maintained above then typedefed to the new TCB_t name +below to enable the use of older kernel aware debuggers. */ +typedef tskTCB TCB_t; + +/*lint -e956 A manual analysis and inspection has been used to determine which +static variables must be declared volatile. */ + +PRIVILEGED_DATA TCB_t * volatile pxCurrentTCB = NULL; + +/* Lists for ready and blocked tasks. --------------------*/ +PRIVILEGED_DATA static List_t pxReadyTasksLists[ configMAX_PRIORITIES ];/*< Prioritised ready tasks. */ +PRIVILEGED_DATA static List_t xDelayedTaskList1; /*< Delayed tasks. */ +PRIVILEGED_DATA static List_t xDelayedTaskList2; /*< Delayed tasks (two lists are used - one for delays that have overflowed the current tick count. */ +PRIVILEGED_DATA static List_t * volatile pxDelayedTaskList; /*< Points to the delayed task list currently being used. */ +PRIVILEGED_DATA static List_t * volatile pxOverflowDelayedTaskList; /*< Points to the delayed task list currently being used to hold tasks that have overflowed the current tick count. */ +PRIVILEGED_DATA static List_t xPendingReadyList; /*< Tasks that have been readied while the scheduler was suspended. They will be moved to the ready list when the scheduler is resumed. */ + +#if( ( INCLUDE_vTaskDelete == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) + + PRIVILEGED_DATA static List_t xTasksWaitingTermination; /*< Tasks that have been deleted - but their memory not yet freed. */ + PRIVILEGED_DATA static volatile UBaseType_t uxDeletedTasksWaitingCleanUp = ( UBaseType_t ) 0U; + +#endif + +#if ( INCLUDE_vTaskSuspend == 1 ) + + PRIVILEGED_DATA static List_t xSuspendedTaskList; /*< Tasks that are currently suspended. */ + +#endif + +/* Other file private variables. --------------------------------*/ +PRIVILEGED_DATA static volatile UBaseType_t uxCurrentNumberOfTasks = ( UBaseType_t ) 0U; +PRIVILEGED_DATA static volatile TickType_t xTickCount = ( TickType_t ) 0U; +PRIVILEGED_DATA static volatile UBaseType_t uxTopReadyPriority = tskIDLE_PRIORITY; +PRIVILEGED_DATA static volatile BaseType_t xSchedulerRunning = pdFALSE; +PRIVILEGED_DATA static volatile UBaseType_t uxPendedTicks = ( UBaseType_t ) 0U; +PRIVILEGED_DATA static volatile BaseType_t xYieldPending = pdFALSE; +PRIVILEGED_DATA static volatile BaseType_t xNumOfOverflows = ( BaseType_t ) 0; +PRIVILEGED_DATA static UBaseType_t uxTaskNumber = ( UBaseType_t ) 0U; +PRIVILEGED_DATA static volatile TickType_t xNextTaskUnblockTime = ( TickType_t ) 0U; /* Initialised to portMAX_DELAY before the scheduler starts. */ +PRIVILEGED_DATA static TaskHandle_t xIdleTaskHandle = NULL; /*< Holds the handle of the idle task. The idle task is created automatically when the scheduler is started. */ + +/* Context switches are held pending while the scheduler is suspended. Also, +interrupts must not manipulate the xStateListItem of a TCB, or any of the +lists the xStateListItem can be referenced from, if the scheduler is suspended. +If an interrupt needs to unblock a task while the scheduler is suspended then it +moves the task's event list item into the xPendingReadyList, ready for the +kernel to move the task from the pending ready list into the real ready list +when the scheduler is unsuspended. The pending ready list itself can only be +accessed from a critical section. */ +PRIVILEGED_DATA static volatile UBaseType_t uxSchedulerSuspended = ( UBaseType_t ) pdFALSE; + +#if ( configGENERATE_RUN_TIME_STATS == 1 ) + + PRIVILEGED_DATA static uint32_t ulTaskSwitchedInTime = 0UL; /*< Holds the value of a timer/counter the last time a task was switched in. */ + PRIVILEGED_DATA static uint32_t ulTotalRunTime = 0UL; /*< Holds the total amount of execution time as defined by the run time counter clock. */ + +#endif + +/*lint +e956 */ + +/*-----------------------------------------------------------*/ + /* Callback function prototypes. --------------------------*/ #if( configCHECK_FOR_STACK_OVERFLOW > 0 ) extern void vApplicationStackOverflowHook( TaskHandle_t xTask, char *pcTaskName ); @@ -440,12 +415,6 @@ to its original value when it is released. */ /* File private functions. --------------------------------*/ -/* - * Utility to ready a TCB for a given task. Mainly just copies the parameters - * into the TCB structure. - */ -static void prvInitialiseTCBVariables( TCB_t * const pxTCB, const char * const pcName, UBaseType_t uxPriority, const MemoryRegion_t * const xRegions, const uint16_t usStackDepth ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ - /** * Utility task that simply returns pdTRUE if the task referenced by xTask is * currently in the Suspended state, or pdFALSE if the task referenced by xTask @@ -500,12 +469,6 @@ static void prvCheckTasksWaitingTermination( void ) PRIVILEGED_FUNCTION; */ static void prvAddCurrentTaskToDelayedList( TickType_t xTicksToWait, const BaseType_t xCanBlockIndefinitely ) PRIVILEGED_FUNCTION; -/* - * Allocates memory from the heap for a TCB and associated stack. Checks the - * allocation was successful. - */ -static TCB_t *prvAllocateTCBAndStack( const uint16_t usStackDepth, StackType_t * const puxStackBuffer, TCB_t * const pucTCBBuffer ) PRIVILEGED_FUNCTION; - /* * Fills an TaskStatus_t structure with information on each task that is * referenced from the pxList list (which may be a ready list, a delayed list, @@ -571,109 +534,369 @@ static void prvResetNextTaskUnblockTime( void ); static char *prvWriteNameToBuffer( char *pcBuffer, const char *pcTaskName ) PRIVILEGED_FUNCTION; #endif + +/* + * Called after a Task_t structure has been allocated either statically or + * dynamically to fill in the structure's members. + */ +static void prvInitialiseNewTask( TaskFunction_t pxTaskCode, const char * const pcName, const uint16_t usStackDepth, void * const pvParameters, UBaseType_t uxPriority, TaskHandle_t * const pxCreatedTask, TCB_t *pxNewTCB ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ + +/* + * Called after a new task has been created and initialised to place the task + * under the control of the scheduler. + */ +static void prvAddNewTaskToReadyList( TCB_t *pxNewTCB ) PRIVILEGED_FUNCTION; + +/*-----------------------------------------------------------*/ + +#if( configSUPPORT_STATIC_ALLOCATION == 1 ) + + BaseType_t xTaskCreateStatic( TaskFunction_t pxTaskCode, const char * const pcName, const uint16_t usStackDepth, void * const pvParameters, UBaseType_t uxPriority, TaskHandle_t * const pxCreatedTask, StackType_t * const puxStackBuffer, StaticTask_t * const pxTaskBuffer ) /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ + { + TCB_t *pxNewTCB; + BaseType_t xReturn; + + configASSERT( puxStackBuffer != NULL ); + configASSERT( pxTaskBuffer != NULL ); + + /* The memory used for the task's TCB and stack are passed into this + function - use them. */ + pxNewTCB = ( TCB_t * ) pxTaskBuffer; /*lint !e740 Unusual cast is ok as the structures are designed to have the same alignment, and the size is checked by an assert. */ + + if( pxNewTCB != NULL ) + { + pxNewTCB->pxStack = ( StackType_t * ) puxStackBuffer; + + #if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + { + /* Tasks can be created statically or dynamically, so note this + task was created statically in case the task is later deleted. */ + pxNewTCB->ucStaticallyAllocated = pdTRUE; + } + #endif /* configSUPPORT_DYNAMIC_ALLOCATION */ + + prvInitialiseNewTask( pxTaskCode, pcName, usStackDepth, pvParameters, uxPriority, pxCreatedTask, pxNewTCB ); + prvAddNewTaskToReadyList( pxNewTCB ); + xReturn = pdPASS; + } + else + { + xReturn = errCOULD_NOT_ALLOCATE_REQUIRED_MEMORY; + } + + return xReturn; + } + +#endif /* SUPPORT_STATIC_ALLOCATION */ +/*-----------------------------------------------------------*/ + +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + + BaseType_t xTaskCreate( TaskFunction_t pxTaskCode, const char * const pcName, const uint16_t usStackDepth, void * const pvParameters, UBaseType_t uxPriority, TaskHandle_t * const pxCreatedTask ) /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ + { + TCB_t *pxNewTCB; + BaseType_t xReturn; + + /* If the stack grows down then allocate the stack then the TCB so the stack + does not grow into the TCB. Likewise if the stack grows up then allocate + the TCB then the stack. */ + #if( portSTACK_GROWTH > 0 ) + { + /* Allocate space for the TCB. Where the memory comes from depends on + the implementation of the port malloc function and whether or not static + allocation is being used. */ + pxNewTCB = ( TCB_t * ) pvPortMalloc( sizeof( TCB_t ) ); + + if( pxNewTCB != NULL ) + { + /* Allocate space for the stack used by the task being created. + The base of the stack memory stored in the TCB so the task can + be deleted later if required. */ + pxNewTCB->pxStack = ( StackType_t * ) pvPortMalloc( ( ( ( size_t ) usStackDepth ) * sizeof( StackType_t ) ) ); /*lint !e961 MISRA exception as the casts are only redundant for some ports. */ + + if( pxNewTCB->pxStack == NULL ) + { + /* Could not allocate the stack. Delete the allocated TCB. */ + vPortFree( pxNewTCB ); + pxNewTCB = NULL; + } + } + } + #else /* portSTACK_GROWTH */ + { + StackType_t *pxStack; + + /* Allocate space for the stack used by the task being created. */ + pxStack = ( StackType_t * ) pvPortMalloc( ( ( ( size_t ) usStackDepth ) * sizeof( StackType_t ) ) ); /*lint !e961 MISRA exception as the casts are only redundant for some ports. */ + + if( pxStack != NULL ) + { + /* Allocate space for the TCB. */ + pxNewTCB = ( TCB_t * ) pvPortMalloc( sizeof( TCB_t ) ); /*lint !e961 MISRA exception as the casts are only redundant for some paths. */ + + if( pxNewTCB != NULL ) + { + /* Store the stack location in the TCB. */ + pxNewTCB->pxStack = pxStack; + } + else + { + /* The stack cannot be used as the TCB was not created. Free + it again. */ + vPortFree( pxStack ); + } + } + else + { + pxNewTCB = NULL; + } + } + #endif /* portSTACK_GROWTH */ + + if( pxNewTCB != NULL ) + { + #if( configSUPPORT_STATIC_ALLOCATION == 1 ) + { + /* Tasks can be created statically or dynamically, so note this + task was created dynamically in case it is later deleted. */ + pxNewTCB->ucStaticallyAllocated = pdFALSE; + } + #endif /* configSUPPORT_STATIC_ALLOCATION */ + + prvInitialiseNewTask( pxTaskCode, pcName, usStackDepth, pvParameters, uxPriority, pxCreatedTask, pxNewTCB ); + prvAddNewTaskToReadyList( pxNewTCB ); + xReturn = pdPASS; + } + else + { + xReturn = errCOULD_NOT_ALLOCATE_REQUIRED_MEMORY; + } + + return xReturn; + } + +#endif /* configSUPPORT_DYNAMIC_ALLOCATION */ +/*-----------------------------------------------------------*/ + +static void prvInitialiseNewTask( TaskFunction_t pxTaskCode, const char * const pcName, const uint16_t usStackDepth, void * const pvParameters, UBaseType_t uxPriority, TaskHandle_t * const pxCreatedTask, TCB_t *pxNewTCB ) /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ +{ +StackType_t *pxTopOfStack; +UBaseType_t x; + + #if( portUSING_MPU_WRAPPERS == 1 ) + /* Should the task be created in privileged mode? */ + BaseType_t xRunPrivileged; + if( ( uxPriority & portPRIVILEGE_BIT ) != 0U ) + { + xRunPrivileged = pdTRUE; + } + else + { + xRunPrivileged = pdFALSE; + } + uxPriority &= ~portPRIVILEGE_BIT; + #endif /* portUSING_MPU_WRAPPERS == 1 */ + + /* Avoid dependency on memset() if it is not required. */ + #if( ( configCHECK_FOR_STACK_OVERFLOW > 1 ) || ( configUSE_TRACE_FACILITY == 1 ) || ( INCLUDE_uxTaskGetStackHighWaterMark == 1 ) ) + { + /* Fill the stack with a known value to assist debugging. */ + ( void ) memset( pxNewTCB->pxStack, ( int ) tskSTACK_FILL_BYTE, ( size_t ) usStackDepth * sizeof( StackType_t ) ); + } + #endif /* ( ( configCHECK_FOR_STACK_OVERFLOW > 1 ) || ( ( configUSE_TRACE_FACILITY == 1 ) || ( INCLUDE_uxTaskGetStackHighWaterMark == 1 ) ) ) */ + + /* Calculate the top of stack address. This depends on whether the stack + grows from high memory to low (as per the 80x86) or vice versa. + portSTACK_GROWTH is used to make the result positive or negative as required + by the port. */ + #if( portSTACK_GROWTH < 0 ) + { + pxTopOfStack = pxNewTCB->pxStack + ( usStackDepth - ( uint16_t ) 1 ); + pxTopOfStack = ( StackType_t * ) ( ( ( portPOINTER_SIZE_TYPE ) pxTopOfStack ) & ( ~( ( portPOINTER_SIZE_TYPE ) portBYTE_ALIGNMENT_MASK ) ) ); /*lint !e923 MISRA exception. Avoiding casts between pointers and integers is not practical. Size differences accounted for using portPOINTER_SIZE_TYPE type. */ + + /* Check the alignment of the calculated top of stack is correct. */ + configASSERT( ( ( ( portPOINTER_SIZE_TYPE ) pxTopOfStack & ( portPOINTER_SIZE_TYPE ) portBYTE_ALIGNMENT_MASK ) == 0UL ) ); + } + #else /* portSTACK_GROWTH */ + { + pxTopOfStack = pxNewTCB->pxStack; + + /* Check the alignment of the stack buffer is correct. */ + configASSERT( ( ( ( portPOINTER_SIZE_TYPE ) pxNewTCB->pxStack & ( portPOINTER_SIZE_TYPE ) portBYTE_ALIGNMENT_MASK ) == 0UL ) ); + + /* The other extreme of the stack space is required if stack checking is + performed. */ + pxNewTCB->pxEndOfStack = pxNewTCB->pxStack + ( usStackDepth - ( uint16_t ) 1 ); + } + #endif /* portSTACK_GROWTH */ + + /* Store the task name in the TCB. */ + for( x = ( UBaseType_t ) 0; x < ( UBaseType_t ) configMAX_TASK_NAME_LEN; x++ ) + { + pxNewTCB->pcTaskName[ x ] = pcName[ x ]; + + /* Don't copy all configMAX_TASK_NAME_LEN if the string is shorter than + configMAX_TASK_NAME_LEN characters just in case the memory after the + string is not accessible (extremely unlikely). */ + if( pcName[ x ] == 0x00 ) + { + break; + } + else + { + mtCOVERAGE_TEST_MARKER(); + } + } + + /* Ensure the name string is terminated in the case that the string length + was greater or equal to configMAX_TASK_NAME_LEN. */ + pxNewTCB->pcTaskName[ configMAX_TASK_NAME_LEN - 1 ] = '\0'; + + /* This is used as an array index so must ensure it's not too large. First + remove the privilege bit if one is present. */ + if( uxPriority >= ( UBaseType_t ) configMAX_PRIORITIES ) + { + uxPriority = ( UBaseType_t ) configMAX_PRIORITIES - ( UBaseType_t ) 1U; + } + else + { + mtCOVERAGE_TEST_MARKER(); + } + + pxNewTCB->uxPriority = uxPriority; + #if ( configUSE_MUTEXES == 1 ) + { + pxNewTCB->uxBasePriority = uxPriority; + pxNewTCB->uxMutexesHeld = 0; + } + #endif /* configUSE_MUTEXES */ + + vListInitialiseItem( &( pxNewTCB->xStateListItem ) ); + vListInitialiseItem( &( pxNewTCB->xEventListItem ) ); + + /* Set the pxNewTCB as a link back from the ListItem_t. This is so we can get + back to the containing TCB from a generic item in a list. */ + listSET_LIST_ITEM_OWNER( &( pxNewTCB->xStateListItem ), pxNewTCB ); + + /* Event lists are always in priority order. */ + listSET_LIST_ITEM_VALUE( &( pxNewTCB->xEventListItem ), ( TickType_t ) configMAX_PRIORITIES - ( TickType_t ) uxPriority ); /*lint !e961 MISRA exception as the casts are only redundant for some ports. */ + listSET_LIST_ITEM_OWNER( &( pxNewTCB->xEventListItem ), pxNewTCB ); + + #if ( portCRITICAL_NESTING_IN_TCB == 1 ) + { + pxNewTCB->uxCriticalNesting = ( UBaseType_t ) 0U; + } + #endif /* portCRITICAL_NESTING_IN_TCB */ + + #if ( configUSE_APPLICATION_TASK_TAG == 1 ) + { + pxNewTCB->pxTaskTag = NULL; + } + #endif /* configUSE_APPLICATION_TASK_TAG */ + + #if ( configGENERATE_RUN_TIME_STATS == 1 ) + { + pxNewTCB->ulRunTimeCounter = 0UL; + } + #endif /* configGENERATE_RUN_TIME_STATS */ + + #if ( portUSING_MPU_WRAPPERS == 1 ) + { + vPortStoreTaskMPUSettings( &( pxNewTCB->xMPUSettings ), xRegions, pxNewTCB->pxStack, usStackDepth ); + } + #endif + + #if( configNUM_THREAD_LOCAL_STORAGE_POINTERS != 0 ) + { + for( x = 0; x < ( UBaseType_t ) configNUM_THREAD_LOCAL_STORAGE_POINTERS; x++ ) + { + pxNewTCB->pvThreadLocalStoragePointers[ x ] = NULL; + } + } + #endif + + #if ( configUSE_TASK_NOTIFICATIONS == 1 ) + { + pxNewTCB->ulNotifiedValue = 0; + pxNewTCB->ucNotifyState = taskNOT_WAITING_NOTIFICATION; + } + #endif + + #if ( configUSE_NEWLIB_REENTRANT == 1 ) + { + /* Initialise this task's Newlib reent structure. */ + _REENT_INIT_PTR( ( &( pxNewTCB->xNewLib_reent ) ) ); + } + #endif + + #if( INCLUDE_xTaskAbortDelay == 1 ) + { + pxNewTCB->ucDelayAborted = pdFALSE; + } + #endif + + /* Initialize the TCB stack to look as if the task was already running, + but had been interrupted by the scheduler. The return address is set + to the start of the task function. Once the stack has been initialised + the top of stack variable is updated. */ + #if( portUSING_MPU_WRAPPERS == 1 ) + { + pxNewTCB->pxTopOfStack = pxPortInitialiseStack( pxTopOfStack, pxTaskCode, pvParameters, xRunPrivileged ); + } + #else /* portUSING_MPU_WRAPPERS */ + { + pxNewTCB->pxTopOfStack = pxPortInitialiseStack( pxTopOfStack, pxTaskCode, pvParameters ); + } + #endif /* portUSING_MPU_WRAPPERS */ + + if( ( void * ) pxCreatedTask != NULL ) + { + /* Pass the handle out in an anonymous way. The handle can be used to + change the created task's priority, delete the created task, etc.*/ + *pxCreatedTask = ( TaskHandle_t ) pxNewTCB; + } + else + { + mtCOVERAGE_TEST_MARKER(); + } +} /*-----------------------------------------------------------*/ -BaseType_t xTaskGenericCreate( TaskFunction_t pxTaskCode, const char * const pcName, const uint16_t usStackDepth, void * const pvParameters, UBaseType_t uxPriority, TaskHandle_t * const pxCreatedTask, StackType_t * const puxStackBuffer, StaticTask_t * const pxTaskBuffer, const MemoryRegion_t * const xRegions ) /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ +static void prvAddNewTaskToReadyList( TCB_t *pxNewTCB ) { -BaseType_t xReturn; -TCB_t * pxNewTCB; -StackType_t *pxTopOfStack; - - configASSERT( pxTaskCode ); - configASSERT( ( ( uxPriority & ( UBaseType_t ) ( ~portPRIVILEGE_BIT ) ) < ( UBaseType_t ) configMAX_PRIORITIES ) ); - - /* Allocate the memory required by the TCB and stack for the new task, - checking that the allocation was successful. */ - pxNewTCB = prvAllocateTCBAndStack( usStackDepth, puxStackBuffer, ( TCB_t* ) pxTaskBuffer ); /*lint !e740 Unusual cast is ok as the structures are designed to have the same alignment, and the size is checked by an assert. */ - - if( pxNewTCB != NULL ) + /* Ensure interrupts don't access the task lists while the lists are being + updated. */ + taskENTER_CRITICAL(); { - #if( portUSING_MPU_WRAPPERS == 1 ) - /* Should the task be created in privileged mode? */ - BaseType_t xRunPrivileged; - if( ( uxPriority & portPRIVILEGE_BIT ) != 0U ) + uxCurrentNumberOfTasks++; + if( pxCurrentTCB == NULL ) + { + /* There are no other tasks, or all the other tasks are in + the suspended state - make this the current task. */ + pxCurrentTCB = pxNewTCB; + + if( uxCurrentNumberOfTasks == ( UBaseType_t ) 1 ) { - xRunPrivileged = pdTRUE; + /* This is the first task to be created so do the preliminary + initialisation required. We will not recover if this call + fails, but we will report the failure. */ + prvInitialiseTaskLists(); } else { - xRunPrivileged = pdFALSE; + mtCOVERAGE_TEST_MARKER(); } - uxPriority &= ~portPRIVILEGE_BIT; - #endif /* portUSING_MPU_WRAPPERS == 1 */ - - /* Calculate the top of stack address. This depends on whether the - stack grows from high memory to low (as per the 80x86) or vice versa. - portSTACK_GROWTH is used to make the result positive or negative as - required by the port. */ - #if( portSTACK_GROWTH < 0 ) - { - pxTopOfStack = pxNewTCB->pxStack + ( usStackDepth - ( uint16_t ) 1 ); - pxTopOfStack = ( StackType_t * ) ( ( ( portPOINTER_SIZE_TYPE ) pxTopOfStack ) & ( ~( ( portPOINTER_SIZE_TYPE ) portBYTE_ALIGNMENT_MASK ) ) ); /*lint !e923 MISRA exception. Avoiding casts between pointers and integers is not practical. Size differences accounted for using portPOINTER_SIZE_TYPE type. */ - - /* Check the alignment of the calculated top of stack is correct. */ - configASSERT( ( ( ( portPOINTER_SIZE_TYPE ) pxTopOfStack & ( portPOINTER_SIZE_TYPE ) portBYTE_ALIGNMENT_MASK ) == 0UL ) ); - } - #else /* portSTACK_GROWTH */ - { - pxTopOfStack = pxNewTCB->pxStack; - - /* Check the alignment of the stack buffer is correct. */ - configASSERT( ( ( ( portPOINTER_SIZE_TYPE ) pxNewTCB->pxStack & ( portPOINTER_SIZE_TYPE ) portBYTE_ALIGNMENT_MASK ) == 0UL ) ); - - /* If we want to use stack checking on architectures that use - a positive stack growth direction then we also need to store the - other extreme of the stack space. */ - pxNewTCB->pxEndOfStack = pxNewTCB->pxStack + ( usStackDepth - ( uint16_t ) 1 ); - } - #endif /* portSTACK_GROWTH */ - - /* Setup the newly allocated TCB with the initial state of the task. */ - prvInitialiseTCBVariables( pxNewTCB, pcName, uxPriority, xRegions, usStackDepth ); - - /* Initialize the TCB stack to look as if the task was already running, - but had been interrupted by the scheduler. The return address is set - to the start of the task function. Once the stack has been initialised - the top of stack variable is updated. */ - #if( portUSING_MPU_WRAPPERS == 1 ) - { - pxNewTCB->pxTopOfStack = pxPortInitialiseStack( pxTopOfStack, pxTaskCode, pvParameters, xRunPrivileged ); - } - #else /* portUSING_MPU_WRAPPERS */ - { - pxNewTCB->pxTopOfStack = pxPortInitialiseStack( pxTopOfStack, pxTaskCode, pvParameters ); - } - #endif /* portUSING_MPU_WRAPPERS */ - - if( ( void * ) pxCreatedTask != NULL ) - { - /* Pass the TCB out - in an anonymous way. The calling function/ - task can use this as a handle to delete the task later if - required.*/ - *pxCreatedTask = ( TaskHandle_t ) pxNewTCB; } else { - mtCOVERAGE_TEST_MARKER(); - } - - /* Ensure interrupts don't access the task lists while they are being - updated. */ - taskENTER_CRITICAL(); - { - uxCurrentNumberOfTasks++; - if( pxCurrentTCB == NULL ) + /* If the scheduler is not already running, make this task the + current task if it is the highest priority task to be created + so far. */ + if( xSchedulerRunning == pdFALSE ) { - /* There are no other tasks, or all the other tasks are in - the suspended state - make this the current task. */ - pxCurrentTCB = pxNewTCB; - - if( uxCurrentNumberOfTasks == ( UBaseType_t ) 1 ) + if( pxCurrentTCB->uxPriority <= pxNewTCB->uxPriority ) { - /* This is the first task to be created so do the preliminary - initialisation required. We will not recover if this call - fails, but we will report the failure. */ - prvInitialiseTaskLists(); + pxCurrentTCB = pxNewTCB; } else { @@ -682,71 +905,43 @@ StackType_t *pxTopOfStack; } else { - /* If the scheduler is not already running, make this task the - current task if it is the highest priority task to be created - so far. */ - if( xSchedulerRunning == pdFALSE ) - { - if( pxCurrentTCB->uxPriority <= uxPriority ) - { - pxCurrentTCB = pxNewTCB; - } - else - { - mtCOVERAGE_TEST_MARKER(); - } - } - else - { - mtCOVERAGE_TEST_MARKER(); - } + mtCOVERAGE_TEST_MARKER(); } + } - uxTaskNumber++; + uxTaskNumber++; - #if ( configUSE_TRACE_FACILITY == 1 ) - { - /* Add a counter into the TCB for tracing only. */ - pxNewTCB->uxTCBNumber = uxTaskNumber; - } - #endif /* configUSE_TRACE_FACILITY */ - traceTASK_CREATE( pxNewTCB ); + #if ( configUSE_TRACE_FACILITY == 1 ) + { + /* Add a counter into the TCB for tracing only. */ + pxNewTCB->uxTCBNumber = uxTaskNumber; + } + #endif /* configUSE_TRACE_FACILITY */ + traceTASK_CREATE( pxNewTCB ); - prvAddTaskToReadyList( pxNewTCB ); + prvAddTaskToReadyList( pxNewTCB ); - xReturn = pdPASS; - portSETUP_TCB( pxNewTCB ); - } - taskEXIT_CRITICAL(); - } - else - { - xReturn = errCOULD_NOT_ALLOCATE_REQUIRED_MEMORY; - traceTASK_CREATE_FAILED(); + portSETUP_TCB( pxNewTCB ); } + taskEXIT_CRITICAL(); - if( xReturn == pdPASS ) + if( xSchedulerRunning != pdFALSE ) { - if( xSchedulerRunning != pdFALSE ) + /* If the created task is of a higher priority than the current task + then it should run now. */ + if( pxCurrentTCB->uxPriority < pxNewTCB->uxPriority ) { - /* If the created task is of a higher priority than the current task - then it should run now. */ - if( pxCurrentTCB->uxPriority < uxPriority ) - { - taskYIELD_IF_USING_PREEMPTION(); - } - else - { - mtCOVERAGE_TEST_MARKER(); - } + taskYIELD_IF_USING_PREEMPTION(); } else { mtCOVERAGE_TEST_MARKER(); } } - - return xReturn; + else + { + mtCOVERAGE_TEST_MARKER(); + } } /*-----------------------------------------------------------*/ @@ -1533,19 +1728,26 @@ StackType_t *pxTopOfStack; void vTaskStartScheduler( void ) { BaseType_t xReturn; -StaticTask_t *pxIdleTaskTCBBuffer = NULL; -StackType_t *pxIdleTaskStackBuffer = NULL; -uint16_t usIdleTaskStackSize = tskIDLE_STACK_SIZE; +uint16_t usIdleTaskStackSize = configMINIMAL_STACK_SIZE; + /* Add the idle task at the lowest priority. */ #if( configSUPPORT_STATIC_ALLOCATION == 1 ) { + StaticTask_t *pxIdleTaskTCBBuffer = NULL; + StackType_t *pxIdleTaskStackBuffer = NULL; + + /* The Idle task is created using user provided RAM - obtain the + address of the RAM then create the idle task. */ vApplicationGetIdleTaskMemory( &pxIdleTaskTCBBuffer, &pxIdleTaskStackBuffer, &usIdleTaskStackSize ); + xReturn = xTaskCreateStatic( prvIdleTask, "IDLE", usIdleTaskStackSize, ( void * ) NULL, ( tskIDLE_PRIORITY | portPRIVILEGE_BIT ), &xIdleTaskHandle, pxIdleTaskStackBuffer, pxIdleTaskTCBBuffer ); /*lint !e961 MISRA exception, justified as it is not a redundant explicit cast to all supported compilers. */ + } + #else + { + /* The Idle task is being created using dynamically allocated RAM. */ + xReturn = xTaskCreate( prvIdleTask, "IDLE", usIdleTaskStackSize, ( void * ) NULL, ( tskIDLE_PRIORITY | portPRIVILEGE_BIT ), &xIdleTaskHandle ); /*lint !e961 MISRA exception, justified as it is not a redundant explicit cast to all supported compilers. */ } #endif /* configSUPPORT_STATIC_ALLOCATION */ - /* Add the idle task at the lowest priority. */ - xReturn = xTaskGenericCreate( prvIdleTask, "IDLE", usIdleTaskStackSize, ( void * ) NULL, ( tskIDLE_PRIORITY | portPRIVILEGE_BIT ), &xIdleTaskHandle, pxIdleTaskStackBuffer, pxIdleTaskTCBBuffer, NULL ); /*lint !e961 MISRA exception, justified as it is not a redundant explicit cast to all supported compilers. */ - #if ( configUSE_TIMERS == 1 ) { if( xReturn == pdPASS ) @@ -2220,7 +2422,7 @@ BaseType_t xSwitchRequired = pdFALSE; unlikely that the if( xTickCount >= xNextTaskUnblockTime ) test will pass next time through. */ - xNextTaskUnblockTime = portMAX_DELAY; + xNextTaskUnblockTime = portMAX_DELAY; /*lint !e961 MISRA exception as the casts are only redundant for some ports. */ break; } else @@ -2956,122 +3158,6 @@ static portTASK_FUNCTION( prvIdleTask, pvParameters ) #endif /* configUSE_TICKLESS_IDLE */ /*-----------------------------------------------------------*/ -static void prvInitialiseTCBVariables( TCB_t * const pxTCB, const char * const pcName, UBaseType_t uxPriority, const MemoryRegion_t * const xRegions, const uint16_t usStackDepth ) /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ -{ -UBaseType_t x; - - /* Store the task name in the TCB. */ - for( x = ( UBaseType_t ) 0; x < ( UBaseType_t ) configMAX_TASK_NAME_LEN; x++ ) - { - pxTCB->pcTaskName[ x ] = pcName[ x ]; - - /* Don't copy all configMAX_TASK_NAME_LEN if the string is shorter than - configMAX_TASK_NAME_LEN characters just in case the memory after the - string is not accessible (extremely unlikely). */ - if( pcName[ x ] == 0x00 ) - { - break; - } - else - { - mtCOVERAGE_TEST_MARKER(); - } - } - - /* Ensure the name string is terminated in the case that the string length - was greater or equal to configMAX_TASK_NAME_LEN. */ - pxTCB->pcTaskName[ configMAX_TASK_NAME_LEN - 1 ] = '\0'; - - /* This is used as an array index so must ensure it's not too large. First - remove the privilege bit if one is present. */ - if( uxPriority >= ( UBaseType_t ) configMAX_PRIORITIES ) - { - uxPriority = ( UBaseType_t ) configMAX_PRIORITIES - ( UBaseType_t ) 1U; - } - else - { - mtCOVERAGE_TEST_MARKER(); - } - - pxTCB->uxPriority = uxPriority; - #if ( configUSE_MUTEXES == 1 ) - { - pxTCB->uxBasePriority = uxPriority; - pxTCB->uxMutexesHeld = 0; - } - #endif /* configUSE_MUTEXES */ - - vListInitialiseItem( &( pxTCB->xStateListItem ) ); - vListInitialiseItem( &( pxTCB->xEventListItem ) ); - - /* Set the pxTCB as a link back from the ListItem_t. This is so we can get - back to the containing TCB from a generic item in a list. */ - listSET_LIST_ITEM_OWNER( &( pxTCB->xStateListItem ), pxTCB ); - - /* Event lists are always in priority order. */ - listSET_LIST_ITEM_VALUE( &( pxTCB->xEventListItem ), ( TickType_t ) configMAX_PRIORITIES - ( TickType_t ) uxPriority ); /*lint !e961 MISRA exception as the casts are only redundant for some ports. */ - listSET_LIST_ITEM_OWNER( &( pxTCB->xEventListItem ), pxTCB ); - - #if ( portCRITICAL_NESTING_IN_TCB == 1 ) - { - pxTCB->uxCriticalNesting = ( UBaseType_t ) 0U; - } - #endif /* portCRITICAL_NESTING_IN_TCB */ - - #if ( configUSE_APPLICATION_TASK_TAG == 1 ) - { - pxTCB->pxTaskTag = NULL; - } - #endif /* configUSE_APPLICATION_TASK_TAG */ - - #if ( configGENERATE_RUN_TIME_STATS == 1 ) - { - pxTCB->ulRunTimeCounter = 0UL; - } - #endif /* configGENERATE_RUN_TIME_STATS */ - - #if ( portUSING_MPU_WRAPPERS == 1 ) - { - vPortStoreTaskMPUSettings( &( pxTCB->xMPUSettings ), xRegions, pxTCB->pxStack, usStackDepth ); - } - #else /* portUSING_MPU_WRAPPERS */ - { - ( void ) xRegions; - ( void ) usStackDepth; - } - #endif /* portUSING_MPU_WRAPPERS */ - - #if( configNUM_THREAD_LOCAL_STORAGE_POINTERS != 0 ) - { - for( x = 0; x < ( UBaseType_t ) configNUM_THREAD_LOCAL_STORAGE_POINTERS; x++ ) - { - pxTCB->pvThreadLocalStoragePointers[ x ] = NULL; - } - } - #endif - - #if ( configUSE_TASK_NOTIFICATIONS == 1 ) - { - pxTCB->ulNotifiedValue = 0; - pxTCB->ucNotifyState = taskNOT_WAITING_NOTIFICATION; - } - #endif - - #if ( configUSE_NEWLIB_REENTRANT == 1 ) - { - /* Initialise this task's Newlib reent structure. */ - _REENT_INIT_PTR( ( &( pxTCB->xNewLib_reent ) ) ); - } - #endif - - #if( INCLUDE_xTaskAbortDelay == 1 ) - { - pxTCB->ucDelayAborted = pdFALSE; - } - #endif -} -/*-----------------------------------------------------------*/ - #if ( configNUM_THREAD_LOCAL_STORAGE_POINTERS != 0 ) void vTaskSetThreadLocalStoragePointer( TaskHandle_t xTaskToSet, BaseType_t xIndex, void *pvValue ) @@ -3203,129 +3289,6 @@ static void prvCheckTasksWaitingTermination( void ) } /*-----------------------------------------------------------*/ -static TCB_t *prvAllocateTCBAndStack( const uint16_t usStackDepth, StackType_t * const puxStackBuffer, TCB_t * const pxTaskBuffer ) -{ -TCB_t *pxNewTCB; - - #if( ( configASSERT_DEFINED == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 1 ) ) - { - /* Sanity check that the size of the structure used to declare a - variable of type StaticTask_t matches the size of the actual TCB_t - structure. */ - volatile size_t xSize = sizeof( StaticTask_t ); - configASSERT( xSize == sizeof( TCB_t ) ); - } - #endif /* configASSERT_DEFINED */ - - /* If the stack grows down then allocate the stack then the TCB so the stack - does not grow into the TCB. Likewise if the stack grows up then allocate - the TCB then the stack. */ - #if( portSTACK_GROWTH > 0 ) - { - /* Allocate space for the TCB. Where the memory comes from depends on - the implementation of the port malloc function. */ - pxNewTCB = ( TCB_t * ) pvPortMallocAligned( sizeof( TCB_t ), pxTaskBuffer ); - - if( pxNewTCB != NULL ) - { - /* Allocate space for the stack used by the task being created. - The base of the stack memory stored in the TCB so the task can - be deleted later if required. */ - pxNewTCB->pxStack = ( StackType_t * ) pvPortMallocAligned( ( ( ( size_t ) usStackDepth ) * sizeof( StackType_t ) ), puxStackBuffer ); /*lint !e961 MISRA exception as the casts are only redundant for some ports. */ - - if( pxNewTCB->pxStack == NULL ) - { - /* Could not allocate the stack. Delete the allocated TCB - if - it was allocated dynamically. */ - if( pxTaskBuffer == NULL ) - { - vPortFree( pxNewTCB ); - } - pxNewTCB = NULL; - } - } - } - #else /* portSTACK_GROWTH */ - { - StackType_t *pxStack; - - /* Allocate space for the stack used by the task being created. */ - pxStack = ( StackType_t * ) pvPortMallocAligned( ( ( ( size_t ) usStackDepth ) * sizeof( StackType_t ) ), puxStackBuffer ); /*lint !e961 MISRA exception as the casts are only redundant for some ports. */ - - if( pxStack != NULL ) - { - /* Allocate space for the TCB. */ - pxNewTCB = ( TCB_t * ) pvPortMallocAligned( sizeof( TCB_t ), pxTaskBuffer ); /*lint !e961 MISRA exception as the casts are only redundant for some paths. */ - - if( pxNewTCB != NULL ) - { - /* Store the stack location in the TCB. */ - pxNewTCB->pxStack = pxStack; - } - else - { - /* The stack cannot be used as the TCB was not created. Free it - again. */ - if( puxStackBuffer == NULL ) - { - vPortFree( pxStack ); - } - else - { - mtCOVERAGE_TEST_MARKER(); - } - } - } - else - { - pxNewTCB = NULL; - } - } - #endif /* portSTACK_GROWTH */ - - if( pxNewTCB != NULL ) - { - /* Avoid dependency on memset() if it is not required. */ - #if( ( configCHECK_FOR_STACK_OVERFLOW > 1 ) || ( configUSE_TRACE_FACILITY == 1 ) || ( INCLUDE_uxTaskGetStackHighWaterMark == 1 ) ) - { - /* Just to help debugging. */ - ( void ) memset( pxNewTCB->pxStack, ( int ) tskSTACK_FILL_BYTE, ( size_t ) usStackDepth * sizeof( StackType_t ) ); - } - #endif /* ( ( configCHECK_FOR_STACK_OVERFLOW > 1 ) || ( ( configUSE_TRACE_FACILITY == 1 ) || ( INCLUDE_uxTaskGetStackHighWaterMark == 1 ) ) ) */ - - #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - { - pxNewTCB->ucStaticAllocationFlags = 0; - - if( puxStackBuffer != NULL ) - { - /* The application provided its own stack - note the fact so no - attempt is made to delete the stack if the task is deleted. */ - pxNewTCB->ucStaticAllocationFlags |= taskSTATICALLY_ALLOCATED_STACK; - } - else - { - mtCOVERAGE_TEST_MARKER(); - } - - if( pxTaskBuffer != NULL ) - { - /* The application provided its own TCB. Note the fact so no - attempt is made to delete the TCB if the task is deleted. */ - pxNewTCB->ucStaticAllocationFlags |= taskSTATICALLY_ALLOCATED_TCB; - } - else - { - mtCOVERAGE_TEST_MARKER(); - } - } - #endif /* configSUPPORT_STATIC_ALLOCATION */ - } - - return pxNewTCB; -} -/*-----------------------------------------------------------*/ - #if( configUSE_TRACE_FACILITY == 1 ) void vTaskGetTaskInfo( TaskHandle_t xTask, TaskStatus_t *pxTaskStatus, BaseType_t xGetFreeStackSpace, eTaskState eState ) @@ -3513,34 +3476,28 @@ TCB_t *pxNewTCB; } #endif /* configUSE_NEWLIB_REENTRANT */ - #if( configSUPPORT_STATIC_ALLOCATION == 1 ) + #if( ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 0 ) ) { - /* Only free the stack and TCB if they were allocated dynamically in - the first place. */ - if( ( pxTCB->ucStaticAllocationFlags & taskSTATICALLY_ALLOCATED_STACK ) == ( uint8_t ) 0 ) - { - vPortFreeAligned( pxTCB->pxStack ); - } - else - { - mtCOVERAGE_TEST_MARKER(); - } - - if( ( pxTCB->ucStaticAllocationFlags & taskSTATICALLY_ALLOCATED_TCB ) == ( uint8_t ) 0 ) + /* The task can only have been allocated dynamically - free it + again. */ + vPortFree( pxTCB->pxStack ); + vPortFree( pxTCB ); + } + #elif( ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 1 ) ) + { + /* The task could have been allocated statically or dynamically, so + check before attempting to free the memory. */ + if( pxTCB->ucStaticallyAllocated == ( uint8_t ) pdFALSE ) { - vPortFreeAligned( pxTCB ); + vPortFree( pxTCB->pxStack ); + vPortFree( pxTCB ); } else { mtCOVERAGE_TEST_MARKER(); } } - #else - { - vPortFreeAligned( pxTCB->pxStack ); - vPortFree( pxTCB ); - } - #endif + #endif /* configSUPPORT_DYNAMIC_ALLOCATION */ } #endif /* INCLUDE_vTaskDelete */ @@ -3891,7 +3848,9 @@ TCB_t *pxTCB; function is executing. */ uxArraySize = uxCurrentNumberOfTasks; - /* Allocate an array index for each task. */ + /* Allocate an array index for each task. NOTE! if + configSUPPORT_DYNAMIC_ALLOCATION is set to 0 then pvPortMalloc() will + equate to NULL. */ pxTaskStatusArray = pvPortMalloc( uxCurrentNumberOfTasks * sizeof( TaskStatus_t ) ); if( pxTaskStatusArray != NULL ) @@ -3931,7 +3890,8 @@ TCB_t *pxTCB; pcWriteBuffer += strlen( pcWriteBuffer ); } - /* Free the array again. */ + /* Free the array again. NOTE! If configSUPPORT_DYNAMIC_ALLOCATION + is 0 then vPortFree() will be #defined to nothing. */ vPortFree( pxTaskStatusArray ); } else @@ -3989,7 +3949,9 @@ TCB_t *pxTCB; function is executing. */ uxArraySize = uxCurrentNumberOfTasks; - /* Allocate an array index for each task. */ + /* Allocate an array index for each task. NOTE! If + configSUPPORT_DYNAMIC_ALLOCATION is set to 0 then pvPortMalloc() will + equate to NULL. */ pxTaskStatusArray = pvPortMalloc( uxCurrentNumberOfTasks * sizeof( TaskStatus_t ) ); if( pxTaskStatusArray != NULL ) @@ -4055,7 +4017,8 @@ TCB_t *pxTCB; mtCOVERAGE_TEST_MARKER(); } - /* Free the array again. */ + /* Free the array again. NOTE! If configSUPPORT_DYNAMIC_ALLOCATION + is 0 then vPortFree() will be #defined to nothing. */ vPortFree( pxTaskStatusArray ); } else diff --git a/FreeRTOS/Source/timers.c b/FreeRTOS/Source/timers.c index 4c7dc382e..6e5a341aa 100644 --- a/FreeRTOS/Source/timers.c +++ b/FreeRTOS/Source/timers.c @@ -113,8 +113,8 @@ typedef struct tmrTimerControl UBaseType_t uxTimerNumber; /*<< An ID assigned by trace tools such as FreeRTOS+Trace */ #endif - #if( configSUPPORT_STATIC_ALLOCATION == 1 ) - uint8_t ucStaticallyAllocated; /*<< Set to pdTRUE if the timer was created from a StaticTimer_t structure, and pdFALSE if the timer structure was allocated dynamically. */ + #if( ( configSUPPORT_STATIC_ALLOCATION == 1 ) && ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) ) + uint8_t ucStaticallyAllocated; /*<< Set to pdTRUE if the timer was created statically so no attempt is made to free the memory again if the timer is later deleted. */ #endif } xTIMER; @@ -171,12 +171,7 @@ PRIVILEGED_DATA static List_t *pxOverflowTimerList; /* A queue that is used to send commands to the timer service task. */ PRIVILEGED_DATA static QueueHandle_t xTimerQueue = NULL; - -#if ( INCLUDE_xTimerGetTimerDaemonTaskHandle == 1 ) - - PRIVILEGED_DATA static TaskHandle_t xTimerTaskHandle = NULL; - -#endif +PRIVILEGED_DATA static TaskHandle_t xTimerTaskHandle = NULL; /*lint +e956 */ @@ -249,13 +244,16 @@ static TickType_t prvGetNextExpireTime( BaseType_t * const pxListWasEmpty ) PRIV */ static void prvProcessTimerOrBlockTask( const TickType_t xNextExpireTime, BaseType_t xListWasEmpty ) PRIVILEGED_FUNCTION; +/* + * Called after a Timer_t structure has been allocated either statically or + * dynamically to fill in the structure's members. + */ +static void prvInitialiseNewTimer( const char * const pcTimerName, const TickType_t xTimerPeriodInTicks, const UBaseType_t uxAutoReload, void * const pvTimerID, TimerCallbackFunction_t pxCallbackFunction, Timer_t *pxNewTimer ) PRIVILEGED_FUNCTION; /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ /*-----------------------------------------------------------*/ BaseType_t xTimerCreateTimerTask( void ) { BaseType_t xReturn = pdFAIL; -StaticTask_t *pxTimerTaskTCBBuffer = NULL; -StackType_t *pxTimerTaskStackBuffer = NULL; uint16_t usTimerTaskStackSize = configTIMER_TASK_STACK_DEPTH; @@ -270,22 +268,17 @@ uint16_t usTimerTaskStackSize = configTIMER_TASK_STACK_DEPTH; #if( configSUPPORT_STATIC_ALLOCATION == 1 ) { - vApplicationGetTimerTaskMemory( &pxTimerTaskTCBBuffer, &pxTimerTaskStackBuffer, &usTimerTaskStackSize ); - } - #endif /* configSUPPORT_STATIC_ALLOCATION */ + StaticTask_t *pxTimerTaskTCBBuffer = NULL; + StackType_t *pxTimerTaskStackBuffer = NULL; - #if ( INCLUDE_xTimerGetTimerDaemonTaskHandle == 1 ) - { - /* Create the timer task, storing its handle in xTimerTaskHandle so - it can be returned by the xTimerGetTimerDaemonTaskHandle() function. */ - xReturn = xTaskGenericCreate( prvTimerTask, "Tmr Svc", usTimerTaskStackSize, NULL, ( ( UBaseType_t ) configTIMER_TASK_PRIORITY ) | portPRIVILEGE_BIT, &xTimerTaskHandle, pxTimerTaskStackBuffer, pxTimerTaskTCBBuffer, NULL ); + vApplicationGetTimerTaskMemory( &pxTimerTaskTCBBuffer, &pxTimerTaskStackBuffer, &usTimerTaskStackSize ); + xReturn = xTaskCreateStatic( prvTimerTask, "Tmr Svc", usTimerTaskStackSize, NULL, ( ( UBaseType_t ) configTIMER_TASK_PRIORITY ) | portPRIVILEGE_BIT, &xTimerTaskHandle, pxTimerTaskStackBuffer, pxTimerTaskTCBBuffer ); } #else { - /* Create the timer task without storing its handle. */ - xReturn = xTaskGenericCreate( prvTimerTask, "Tmr Svc", usTimerTaskStackSize, NULL, ( ( UBaseType_t ) configTIMER_TASK_PRIORITY ) | portPRIVILEGE_BIT, NULL, pxTimerTaskStackBuffer, pxTimerTaskTCBBuffer, NULL ); + xReturn = xTaskCreate( prvTimerTask, "Tmr Svc", usTimerTaskStackSize, NULL, ( ( UBaseType_t ) configTIMER_TASK_PRIORITY ) | portPRIVILEGE_BIT, &xTimerTaskHandle ); } - #endif + #endif /* configSUPPORT_STATIC_ALLOCATION */ } else { @@ -297,78 +290,94 @@ uint16_t usTimerTaskStackSize = configTIMER_TASK_STACK_DEPTH; } /*-----------------------------------------------------------*/ -TimerHandle_t xTimerGenericCreate( const char * const pcTimerName, const TickType_t xTimerPeriodInTicks, const UBaseType_t uxAutoReload, void * const pvTimerID, TimerCallbackFunction_t pxCallbackFunction, StaticTimer_t *pxTimerBuffer ) /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ -{ -Timer_t *pxNewTimer; +#if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) - #if( ( configASSERT_DEFINED == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 1 ) ) + TimerHandle_t xTimerCreate( const char * const pcTimerName, const TickType_t xTimerPeriodInTicks, const UBaseType_t uxAutoReload, void * const pvTimerID, TimerCallbackFunction_t pxCallbackFunction ) /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ { - /* Sanity check that the size of the structure used to declare a - variable of type StaticTimer_t equals the size of the real timer - structures. */ - volatile size_t xSize = sizeof( StaticTimer_t ); - configASSERT( xSize == sizeof( Timer_t ) ); - } - #endif /* configASSERT_DEFINED */ + Timer_t *pxNewTimer; - /* Allocate the timer structure. */ - if( xTimerPeriodInTicks == ( TickType_t ) 0U ) - { - pxNewTimer = NULL; - } - else - { - /* If the user passed in a statically allocated timer structure then use - it, otherwise allocate the structure dynamically. */ - if( pxTimerBuffer == NULL ) - { - pxNewTimer = ( Timer_t * ) pvPortMalloc( sizeof( Timer_t ) ); - } - else - { - pxNewTimer = ( Timer_t * ) pxTimerBuffer; /*lint !e740 Unusual cast is ok as the structures are designed to have the same alignment, and the size is checked by an assert. */ - } + pxNewTimer = ( Timer_t * ) pvPortMalloc( sizeof( Timer_t ) ); if( pxNewTimer != NULL ) { - /* Ensure the infrastructure used by the timer service task has been - created/initialised. */ - prvCheckForValidListAndQueue(); - - /* Initialise the timer structure members using the function - parameters. */ - pxNewTimer->pcTimerName = pcTimerName; - pxNewTimer->xTimerPeriodInTicks = xTimerPeriodInTicks; - pxNewTimer->uxAutoReload = uxAutoReload; - pxNewTimer->pvTimerID = pvTimerID; - pxNewTimer->pxCallbackFunction = pxCallbackFunction; - vListInitialiseItem( &( pxNewTimer->xTimerListItem ) ); + prvInitialiseNewTimer( pcTimerName, xTimerPeriodInTicks, uxAutoReload, pvTimerID, pxCallbackFunction, pxNewTimer ); #if( configSUPPORT_STATIC_ALLOCATION == 1 ) { - if( pxTimerBuffer == NULL ) - { - pxNewTimer->ucStaticallyAllocated = pdFALSE; - } - else - { - pxNewTimer->ucStaticallyAllocated = pdTRUE; - } + /* Timers can be created statically or dynamically, so note this + timer was created dynamically in case the timer is later + deleted. */ + pxNewTimer->ucStaticallyAllocated = pdFALSE; } #endif /* configSUPPORT_STATIC_ALLOCATION */ + } - traceTIMER_CREATE( pxNewTimer ); + return pxNewTimer; + } + +#endif /* configSUPPORT_STATIC_ALLOCATION */ +/*-----------------------------------------------------------*/ + +#if( configSUPPORT_STATIC_ALLOCATION == 1 ) + + TimerHandle_t xTimerCreateStatic( const char * const pcTimerName, const TickType_t xTimerPeriodInTicks, const UBaseType_t uxAutoReload, void * const pvTimerID, TimerCallbackFunction_t pxCallbackFunction, StaticTimer_t *pxTimerBuffer ) /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ + { + Timer_t *pxNewTimer; + + #if( configASSERT_DEFINED == 1 ) + { + /* Sanity check that the size of the structure used to declare a + variable of type StaticTimer_t equals the size of the real timer + structures. */ + volatile size_t xSize = sizeof( StaticTimer_t ); + configASSERT( xSize == sizeof( Timer_t ) ); } - else + #endif /* configASSERT_DEFINED */ + + /* A pointer to a StaticTimer_t structure MUST be provided, use it. */ + configASSERT( pxTimerBuffer ); + pxNewTimer = ( Timer_t * ) pxTimerBuffer; /*lint !e740 Unusual cast is ok as the structures are designed to have the same alignment, and the size is checked by an assert. */ + + if( pxNewTimer != NULL ) { - traceTIMER_CREATE_FAILED(); + prvInitialiseNewTimer( pcTimerName, xTimerPeriodInTicks, uxAutoReload, pvTimerID, pxCallbackFunction, pxNewTimer ); + + #if( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) + { + /* Timers can be created statically or dynamically so note this + timer was created statically in case it is later deleted. */ + pxNewTimer->ucStaticallyAllocated = pdTRUE; + } + #endif /* configSUPPORT_DYNAMIC_ALLOCATION */ } + + return pxNewTimer; } +#endif /* configSUPPORT_STATIC_ALLOCATION */ +/*-----------------------------------------------------------*/ + +static void prvInitialiseNewTimer( const char * const pcTimerName, const TickType_t xTimerPeriodInTicks, const UBaseType_t uxAutoReload, void * const pvTimerID, TimerCallbackFunction_t pxCallbackFunction, Timer_t *pxNewTimer ) /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ +{ /* 0 is not a valid value for xTimerPeriodInTicks. */ configASSERT( ( xTimerPeriodInTicks > 0 ) ); - return ( TimerHandle_t ) pxNewTimer; + if( pxNewTimer != NULL ) + { + /* Ensure the infrastructure used by the timer service task has been + created/initialised. */ + prvCheckForValidListAndQueue(); + + /* Initialise the timer structure members using the function + parameters. */ + pxNewTimer->pcTimerName = pcTimerName; + pxNewTimer->xTimerPeriodInTicks = xTimerPeriodInTicks; + pxNewTimer->uxAutoReload = uxAutoReload; + pxNewTimer->pvTimerID = pvTimerID; + pxNewTimer->pxCallbackFunction = pxCallbackFunction; + vListInitialiseItem( &( pxNewTimer->xTimerListItem ) ); + traceTIMER_CREATE( pxNewTimer ); + } } /*-----------------------------------------------------------*/ @@ -415,17 +424,13 @@ DaemonTaskMessage_t xMessage; } /*-----------------------------------------------------------*/ -#if ( INCLUDE_xTimerGetTimerDaemonTaskHandle == 1 ) - - TaskHandle_t xTimerGetTimerDaemonTaskHandle( void ) - { - /* If xTimerGetTimerDaemonTaskHandle() is called before the scheduler has been - started, then xTimerTaskHandle will be NULL. */ - configASSERT( ( xTimerTaskHandle != NULL ) ); - return xTimerTaskHandle; - } - -#endif +TaskHandle_t xTimerGetTimerDaemonTaskHandle( void ) +{ + /* If xTimerGetTimerDaemonTaskHandle() is called before the scheduler has been + started, then xTimerTaskHandle will be NULL. */ + configASSERT( ( xTimerTaskHandle != NULL ) ); + return xTimerTaskHandle; +} /*-----------------------------------------------------------*/ const char * pcTimerGetTimerName( TimerHandle_t xTimer ) /*lint !e971 Unqualified char types are allowed for strings and single characters only. */ @@ -633,7 +638,7 @@ BaseType_t xProcessTimerNow = pdFALSE; { /* Has the expiry time elapsed between the command to start/reset a timer was issued, and the time the command was processed? */ - if( ( ( TickType_t ) ( xTimeNow - xCommandTime ) ) >= pxTimer->xTimerPeriodInTicks ) + if( ( ( TickType_t ) ( xTimeNow - xCommandTime ) ) >= pxTimer->xTimerPeriodInTicks ) /*lint !e961 MISRA exception as the casts are only redundant for some ports. */ { /* The time between a command being issued and the command being processed actually exceeds the timers period. */ @@ -778,8 +783,17 @@ TickType_t xTimeNow; /* The timer has already been removed from the active list, just free up the memory if the memory was dynamically allocated. */ - #if( configSUPPORT_STATIC_ALLOCATION == 1 ) + #if( ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 0 ) ) { + /* The timer can only have been allocated dynamically - + free it again. */ + vPortFree( pxTimer ); + } + #elif( ( configSUPPORT_DYNAMIC_ALLOCATION == 1 ) && ( configSUPPORT_STATIC_ALLOCATION == 1 ) ) + { + /* The timer could have been allocated statically or + dynamically, so check before attempting to free the + memory. */ if( pxTimer->ucStaticallyAllocated == ( uint8_t ) pdFALSE ) { vPortFree( pxTimer ); @@ -789,11 +803,7 @@ TickType_t xTimeNow; mtCOVERAGE_TEST_MARKER(); } } - #else - { - vPortFree( pxTimer ); - } - #endif /* configSUPPORT_STATIC_ALLOCATION */ + #endif /* configSUPPORT_DYNAMIC_ALLOCATION */ break; default : @@ -877,8 +887,21 @@ static void prvCheckForValidListAndQueue( void ) vListInitialise( &xActiveTimerList2 ); pxCurrentTimerList = &xActiveTimerList1; pxOverflowTimerList = &xActiveTimerList2; - xTimerQueue = xQueueCreate( ( UBaseType_t ) configTIMER_QUEUE_LENGTH, sizeof( DaemonTaskMessage_t ) ); - configASSERT( xTimerQueue ); + + #if( configSUPPORT_STATIC_ALLOCATION == 1 ) + { + /* The timer queue is allocated statically in case + configSUPPORT_DYNAMIC_ALLOCATION is 0. */ + static StaticQueue_t xStaticTimerQueue; + static uint8_t ucStaticTimerQueueStorage[ configTIMER_QUEUE_LENGTH * sizeof( DaemonTaskMessage_t ) ]; + + xTimerQueue = xQueueCreateStatic( ( UBaseType_t ) configTIMER_QUEUE_LENGTH, sizeof( DaemonTaskMessage_t ), &( ucStaticTimerQueueStorage[ 0 ] ), &xStaticTimerQueue ); + } + #else + { + xTimerQueue = xQueueCreate( ( UBaseType_t ) configTIMER_QUEUE_LENGTH, sizeof( DaemonTaskMessage_t ) ); + } + #endif #if ( configQUEUE_REGISTRY_SIZE > 0 ) {