diff options
Diffstat (limited to 'openpicc/os/core')
30 files changed, 13886 insertions, 0 deletions
| diff --git a/openpicc/os/core/ARM7_AT91SAM7S/AT91SAM7.h b/openpicc/os/core/ARM7_AT91SAM7S/AT91SAM7.h new file mode 100644 index 0000000..a788325 --- /dev/null +++ b/openpicc/os/core/ARM7_AT91SAM7S/AT91SAM7.h @@ -0,0 +1,1969 @@ +//  ---------------------------------------------------------------------------- +//          ATMEL Microcontroller Software Support  -  ROUSSET  - +//  ---------------------------------------------------------------------------- +//  DISCLAIMER:  THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR +//  IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +//  MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE +//  DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR ANY DIRECT, INDIRECT, +//  INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +//  LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, +//  OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF +//  LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING +//  NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, +//  EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +//  ---------------------------------------------------------------------------- +// File Name           : AT91SAM7S64.h +// Object              : AT91SAM7S64 definitions +// Generated           : AT91 SW Application Group  08/30/2005 (15:52:59) +//  +// CVS Reference       : /AT91SAM7S64.pl/1.21/Tue Aug 30 11:55:03 2005// +// CVS Reference       : /SYS_SAM7S.pl/1.2/Tue Feb  1 17:01:52 2005// +// CVS Reference       : /MC_SAM7S.pl/1.3/Fri May 20 14:12:30 2005// +// CVS Reference       : /PMC_SAM7S_USB.pl/1.4/Tue Feb  8 13:58:22 2005// +// CVS Reference       : /RSTC_SAM7S.pl/1.2/Wed Jul 13 14:57:40 2005// +// CVS Reference       : /UDP_SAM7S.pl/1.1/Tue May 10 11:34:52 2005// +// CVS Reference       : /PWM_SAM7S.pl/1.1/Tue May 10 11:53:07 2005// +// CVS Reference       : /RTTC_6081A.pl/1.2/Tue Nov  9 14:43:58 2004// +// CVS Reference       : /PITC_6079A.pl/1.2/Tue Nov  9 14:43:56 2004// +// CVS Reference       : /WDTC_6080A.pl/1.3/Tue Nov  9 14:44:00 2004// +// CVS Reference       : /VREG_6085B.pl/1.1/Tue Feb  1 16:05:48 2005// +// CVS Reference       : /AIC_6075B.pl/1.3/Fri May 20 14:01:30 2005// +// CVS Reference       : /PIO_6057A.pl/1.2/Thu Feb  3 10:18:28 2005// +// CVS Reference       : /DBGU_6059D.pl/1.1/Mon Jan 31 13:15:32 2005// +// CVS Reference       : /US_6089C.pl/1.1/Mon Jul 12 18:23:26 2004// +// CVS Reference       : /SPI_6088D.pl/1.3/Fri May 20 14:08:59 2005// +// CVS Reference       : /SSC_6078A.pl/1.1/Tue Jul 13 07:45:40 2004// +// CVS Reference       : /TC_6082A.pl/1.7/Fri Mar 11 12:52:17 2005// +// CVS Reference       : /TWI_6061A.pl/1.1/Tue Jul 13 07:38:06 2004// +// CVS Reference       : /PDC_6074C.pl/1.2/Thu Feb  3 08:48:54 2005// +// CVS Reference       : /ADC_6051C.pl/1.1/Fri Oct 17 09:12:38 2003// +//  ---------------------------------------------------------------------------- + +#ifndef __AT91SAM7_H__ +#define __AT91SAM7_H__ + +typedef volatile unsigned int AT91_REG;	// Hardware register definition + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR System Peripherals +// ***************************************************************************** +typedef struct _AT91S_SYS +{ +  AT91_REG AIC_SMR[32];		// Source Mode Register +  AT91_REG AIC_SVR[32];		// Source Vector Register +  AT91_REG AIC_IVR;		// IRQ Vector Register +  AT91_REG AIC_FVR;		// FIQ Vector Register +  AT91_REG AIC_ISR;		// Interrupt Status Register +  AT91_REG AIC_IPR;		// Interrupt Pending Register +  AT91_REG AIC_IMR;		// Interrupt Mask Register +  AT91_REG AIC_CISR;		// Core Interrupt Status Register +  AT91_REG Reserved0[2];	//  +  AT91_REG AIC_IECR;		// Interrupt Enable Command Register +  AT91_REG AIC_IDCR;		// Interrupt Disable Command Register +  AT91_REG AIC_ICCR;		// Interrupt Clear Command Register +  AT91_REG AIC_ISCR;		// Interrupt Set Command Register +  AT91_REG AIC_EOICR;		// End of Interrupt Command Register +  AT91_REG AIC_SPU;		// Spurious Vector Register +  AT91_REG AIC_DCR;		// Debug Control Register (Protect) +  AT91_REG Reserved1[1];	//  +  AT91_REG AIC_FFER;		// Fast Forcing Enable Register +  AT91_REG AIC_FFDR;		// Fast Forcing Disable Register +  AT91_REG AIC_FFSR;		// Fast Forcing Status Register +  AT91_REG Reserved2[45];	//  +  AT91_REG DBGU_CR;		// Control Register +  AT91_REG DBGU_MR;		// Mode Register +  AT91_REG DBGU_IER;		// Interrupt Enable Register +  AT91_REG DBGU_IDR;		// Interrupt Disable Register +  AT91_REG DBGU_IMR;		// Interrupt Mask Register +  AT91_REG DBGU_CSR;		// Channel Status Register +  AT91_REG DBGU_RHR;		// Receiver Holding Register +  AT91_REG DBGU_THR;		// Transmitter Holding Register +  AT91_REG DBGU_BRGR;		// Baud Rate Generator Register +  AT91_REG Reserved3[7];	//  +  AT91_REG DBGU_CIDR;		// Chip ID Register +  AT91_REG DBGU_EXID;		// Chip ID Extension Register +  AT91_REG DBGU_FNTR;		// Force NTRST Register +  AT91_REG Reserved4[45];	//  +  AT91_REG DBGU_RPR;		// Receive Pointer Register +  AT91_REG DBGU_RCR;		// Receive Counter Register +  AT91_REG DBGU_TPR;		// Transmit Pointer Register +  AT91_REG DBGU_TCR;		// Transmit Counter Register +  AT91_REG DBGU_RNPR;		// Receive Next Pointer Register +  AT91_REG DBGU_RNCR;		// Receive Next Counter Register +  AT91_REG DBGU_TNPR;		// Transmit Next Pointer Register +  AT91_REG DBGU_TNCR;		// Transmit Next Counter Register +  AT91_REG DBGU_PTCR;		// PDC Transfer Control Register +  AT91_REG DBGU_PTSR;		// PDC Transfer Status Register +  AT91_REG Reserved5[54];	//  +  AT91_REG PIOA_PER;		// PIO Enable Register +  AT91_REG PIOA_PDR;		// PIO Disable Register +  AT91_REG PIOA_PSR;		// PIO Status Register +  AT91_REG Reserved6[1];	//  +  AT91_REG PIOA_OER;		// Output Enable Register +  AT91_REG PIOA_ODR;		// Output Disable Registerr +  AT91_REG PIOA_OSR;		// Output Status Register +  AT91_REG Reserved7[1];	//  +  AT91_REG PIOA_IFER;		// Input Filter Enable Register +  AT91_REG PIOA_IFDR;		// Input Filter Disable Register +  AT91_REG PIOA_IFSR;		// Input Filter Status Register +  AT91_REG Reserved8[1];	//  +  AT91_REG PIOA_SODR;		// Set Output Data Register +  AT91_REG PIOA_CODR;		// Clear Output Data Register +  AT91_REG PIOA_ODSR;		// Output Data Status Register +  AT91_REG PIOA_PDSR;		// Pin Data Status Register +  AT91_REG PIOA_IER;		// Interrupt Enable Register +  AT91_REG PIOA_IDR;		// Interrupt Disable Register +  AT91_REG PIOA_IMR;		// Interrupt Mask Register +  AT91_REG PIOA_ISR;		// Interrupt Status Register +  AT91_REG PIOA_MDER;		// Multi-driver Enable Register +  AT91_REG PIOA_MDDR;		// Multi-driver Disable Register +  AT91_REG PIOA_MDSR;		// Multi-driver Status Register +  AT91_REG Reserved9[1];	//  +  AT91_REG PIOA_PPUDR;		// Pull-up Disable Register +  AT91_REG PIOA_PPUER;		// Pull-up Enable Register +  AT91_REG PIOA_PPUSR;		// Pull-up Status Register +  AT91_REG Reserved10[1];	//  +  AT91_REG PIOA_ASR;		// Select A Register +  AT91_REG PIOA_BSR;		// Select B Register +  AT91_REG PIOA_ABSR;		// AB Select Status Register +  AT91_REG Reserved11[9];	//  +  AT91_REG PIOA_OWER;		// Output Write Enable Register +  AT91_REG PIOA_OWDR;		// Output Write Disable Register +  AT91_REG PIOA_OWSR;		// Output Write Status Register +  AT91_REG Reserved12[469];	//  +  AT91_REG PMC_SCER;		// System Clock Enable Register +  AT91_REG PMC_SCDR;		// System Clock Disable Register +  AT91_REG PMC_SCSR;		// System Clock Status Register +  AT91_REG Reserved13[1];	//  +  AT91_REG PMC_PCER;		// Peripheral Clock Enable Register +  AT91_REG PMC_PCDR;		// Peripheral Clock Disable Register +  AT91_REG PMC_PCSR;		// Peripheral Clock Status Register +  AT91_REG Reserved14[1];	//  +  AT91_REG PMC_MOR;		// Main Oscillator Register +  AT91_REG PMC_MCFR;		// Main Clock  Frequency Register +  AT91_REG Reserved15[1];	//  +  AT91_REG PMC_PLLR;		// PLL Register +  AT91_REG PMC_MCKR;		// Master Clock Register +  AT91_REG Reserved16[3];	//  +  AT91_REG PMC_PCKR[3];		// Programmable Clock Register +  AT91_REG Reserved17[5];	//  +  AT91_REG PMC_IER;		// Interrupt Enable Register +  AT91_REG PMC_IDR;		// Interrupt Disable Register +  AT91_REG PMC_SR;		// Status Register +  AT91_REG PMC_IMR;		// Interrupt Mask Register +  AT91_REG Reserved18[36];	//  +  AT91_REG RSTC_RCR;		// Reset Control Register +  AT91_REG RSTC_RSR;		// Reset Status Register +  AT91_REG RSTC_RMR;		// Reset Mode Register +  AT91_REG Reserved19[5];	//  +  AT91_REG RTTC_RTMR;		// Real-time Mode Register +  AT91_REG RTTC_RTAR;		// Real-time Alarm Register +  AT91_REG RTTC_RTVR;		// Real-time Value Register +  AT91_REG RTTC_RTSR;		// Real-time Status Register +  AT91_REG PITC_PIMR;		// Period Interval Mode Register +  AT91_REG PITC_PISR;		// Period Interval Status Register +  AT91_REG PITC_PIVR;		// Period Interval Value Register +  AT91_REG PITC_PIIR;		// Period Interval Image Register +  AT91_REG WDTC_WDCR;		// Watchdog Control Register +  AT91_REG WDTC_WDMR;		// Watchdog Mode Register +  AT91_REG WDTC_WDSR;		// Watchdog Status Register +  AT91_REG Reserved20[5];	//  +  AT91_REG VREG_MR;		// Voltage Regulator Mode Register +} AT91S_SYS, *AT91PS_SYS; + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Advanced Interrupt Controller +// ***************************************************************************** +typedef struct _AT91S_AIC +{ +  AT91_REG AIC_SMR[32];		// Source Mode Register +  AT91_REG AIC_SVR[32];		// Source Vector Register +  AT91_REG AIC_IVR;		// IRQ Vector Register +  AT91_REG AIC_FVR;		// FIQ Vector Register +  AT91_REG AIC_ISR;		// Interrupt Status Register +  AT91_REG AIC_IPR;		// Interrupt Pending Register +  AT91_REG AIC_IMR;		// Interrupt Mask Register +  AT91_REG AIC_CISR;		// Core Interrupt Status Register +  AT91_REG Reserved0[2];	//  +  AT91_REG AIC_IECR;		// Interrupt Enable Command Register +  AT91_REG AIC_IDCR;		// Interrupt Disable Command Register +  AT91_REG AIC_ICCR;		// Interrupt Clear Command Register +  AT91_REG AIC_ISCR;		// Interrupt Set Command Register +  AT91_REG AIC_EOICR;		// End of Interrupt Command Register +  AT91_REG AIC_SPU;		// Spurious Vector Register +  AT91_REG AIC_DCR;		// Debug Control Register (Protect) +  AT91_REG Reserved1[1];	//  +  AT91_REG AIC_FFER;		// Fast Forcing Enable Register +  AT91_REG AIC_FFDR;		// Fast Forcing Disable Register +  AT91_REG AIC_FFSR;		// Fast Forcing Status Register +} AT91S_AIC, *AT91PS_AIC; + +// -------- AIC_SMR : (AIC Offset: 0x0) Control Register --------  +#define AT91C_AIC_PRIOR       ((unsigned int) 0x7 <<  0)	// (AIC) Priority Level +#define 	AT91C_AIC_PRIOR_LOWEST               ((unsigned int) 0x0)	// (AIC) Lowest priority level +#define 	AT91C_AIC_PRIOR_HIGHEST              ((unsigned int) 0x7)	// (AIC) Highest priority level +#define AT91C_AIC_SRCTYPE     ((unsigned int) 0x3 <<  5)	// (AIC) Interrupt Source Type +#define 	AT91C_AIC_SRCTYPE_INT_HIGH_LEVEL       ((unsigned int) 0x0 <<  5)	// (AIC) Internal Sources Code Label High-level Sensitive +#define 	AT91C_AIC_SRCTYPE_EXT_LOW_LEVEL        ((unsigned int) 0x0 <<  5)	// (AIC) External Sources Code Label Low-level Sensitive +#define 	AT91C_AIC_SRCTYPE_INT_POSITIVE_EDGE    ((unsigned int) 0x1 <<  5)	// (AIC) Internal Sources Code Label Positive Edge triggered +#define 	AT91C_AIC_SRCTYPE_EXT_NEGATIVE_EDGE    ((unsigned int) 0x1 <<  5)	// (AIC) External Sources Code Label Negative Edge triggered +#define 	AT91C_AIC_SRCTYPE_HIGH_LEVEL           ((unsigned int) 0x2 <<  5)	// (AIC) Internal Or External Sources Code Label High-level Sensitive +#define 	AT91C_AIC_SRCTYPE_POSITIVE_EDGE        ((unsigned int) 0x3 <<  5)	// (AIC) Internal Or External Sources Code Label Positive Edge triggered +// -------- AIC_CISR : (AIC Offset: 0x114) AIC Core Interrupt Status Register --------  +#define AT91C_AIC_NFIQ        ((unsigned int) 0x1 <<  0)	// (AIC) NFIQ Status +#define AT91C_AIC_NIRQ        ((unsigned int) 0x1 <<  1)	// (AIC) NIRQ Status +// -------- AIC_DCR : (AIC Offset: 0x138) AIC Debug Control Register (Protect) --------  +#define AT91C_AIC_DCR_PROT    ((unsigned int) 0x1 <<  0)	// (AIC) Protection Mode +#define AT91C_AIC_DCR_GMSK    ((unsigned int) 0x1 <<  1)	// (AIC) General Mask + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Peripheral DMA Controller +// ***************************************************************************** +typedef struct _AT91S_PDC +{ +  AT91_REG PDC_RPR;		// Receive Pointer Register +  AT91_REG PDC_RCR;		// Receive Counter Register +  AT91_REG PDC_TPR;		// Transmit Pointer Register +  AT91_REG PDC_TCR;		// Transmit Counter Register +  AT91_REG PDC_RNPR;		// Receive Next Pointer Register +  AT91_REG PDC_RNCR;		// Receive Next Counter Register +  AT91_REG PDC_TNPR;		// Transmit Next Pointer Register +  AT91_REG PDC_TNCR;		// Transmit Next Counter Register +  AT91_REG PDC_PTCR;		// PDC Transfer Control Register +  AT91_REG PDC_PTSR;		// PDC Transfer Status Register +} AT91S_PDC, *AT91PS_PDC; + +// -------- PDC_PTCR : (PDC Offset: 0x20) PDC Transfer Control Register --------  +#define AT91C_PDC_RXTEN       ((unsigned int) 0x1 <<  0)	// (PDC) Receiver Transfer Enable +#define AT91C_PDC_RXTDIS      ((unsigned int) 0x1 <<  1)	// (PDC) Receiver Transfer Disable +#define AT91C_PDC_TXTEN       ((unsigned int) 0x1 <<  8)	// (PDC) Transmitter Transfer Enable +#define AT91C_PDC_TXTDIS      ((unsigned int) 0x1 <<  9)	// (PDC) Transmitter Transfer Disable +// -------- PDC_PTSR : (PDC Offset: 0x24) PDC Transfer Status Register --------  + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Debug Unit +// ***************************************************************************** +typedef struct _AT91S_DBGU +{ +  AT91_REG DBGU_CR;		// Control Register +  AT91_REG DBGU_MR;		// Mode Register +  AT91_REG DBGU_IER;		// Interrupt Enable Register +  AT91_REG DBGU_IDR;		// Interrupt Disable Register +  AT91_REG DBGU_IMR;		// Interrupt Mask Register +  AT91_REG DBGU_CSR;		// Channel Status Register +  AT91_REG DBGU_RHR;		// Receiver Holding Register +  AT91_REG DBGU_THR;		// Transmitter Holding Register +  AT91_REG DBGU_BRGR;		// Baud Rate Generator Register +  AT91_REG Reserved0[7];	//  +  AT91_REG DBGU_CIDR;		// Chip ID Register +  AT91_REG DBGU_EXID;		// Chip ID Extension Register +  AT91_REG DBGU_FNTR;		// Force NTRST Register +  AT91_REG Reserved1[45];	//  +  AT91_REG DBGU_RPR;		// Receive Pointer Register +  AT91_REG DBGU_RCR;		// Receive Counter Register +  AT91_REG DBGU_TPR;		// Transmit Pointer Register +  AT91_REG DBGU_TCR;		// Transmit Counter Register +  AT91_REG DBGU_RNPR;		// Receive Next Pointer Register +  AT91_REG DBGU_RNCR;		// Receive Next Counter Register +  AT91_REG DBGU_TNPR;		// Transmit Next Pointer Register +  AT91_REG DBGU_TNCR;		// Transmit Next Counter Register +  AT91_REG DBGU_PTCR;		// PDC Transfer Control Register +  AT91_REG DBGU_PTSR;		// PDC Transfer Status Register +} AT91S_DBGU, *AT91PS_DBGU; + +// -------- DBGU_CR : (DBGU Offset: 0x0) Debug Unit Control Register --------  +#define AT91C_US_RSTRX        ((unsigned int) 0x1 <<  2)	// (DBGU) Reset Receiver +#define AT91C_US_RSTTX        ((unsigned int) 0x1 <<  3)	// (DBGU) Reset Transmitter +#define AT91C_US_RXEN         ((unsigned int) 0x1 <<  4)	// (DBGU) Receiver Enable +#define AT91C_US_RXDIS        ((unsigned int) 0x1 <<  5)	// (DBGU) Receiver Disable +#define AT91C_US_TXEN         ((unsigned int) 0x1 <<  6)	// (DBGU) Transmitter Enable +#define AT91C_US_TXDIS        ((unsigned int) 0x1 <<  7)	// (DBGU) Transmitter Disable +#define AT91C_US_RSTSTA       ((unsigned int) 0x1 <<  8)	// (DBGU) Reset Status Bits +// -------- DBGU_MR : (DBGU Offset: 0x4) Debug Unit Mode Register --------  +#define AT91C_US_PAR          ((unsigned int) 0x7 <<  9)	// (DBGU) Parity type +#define 	AT91C_US_PAR_EVEN                 ((unsigned int) 0x0 <<  9)	// (DBGU) Even Parity +#define 	AT91C_US_PAR_ODD                  ((unsigned int) 0x1 <<  9)	// (DBGU) Odd Parity +#define 	AT91C_US_PAR_SPACE                ((unsigned int) 0x2 <<  9)	// (DBGU) Parity forced to 0 (Space) +#define 	AT91C_US_PAR_MARK                 ((unsigned int) 0x3 <<  9)	// (DBGU) Parity forced to 1 (Mark) +#define 	AT91C_US_PAR_NONE                 ((unsigned int) 0x4 <<  9)	// (DBGU) No Parity +#define 	AT91C_US_PAR_MULTI_DROP           ((unsigned int) 0x6 <<  9)	// (DBGU) Multi-drop mode +#define AT91C_US_CHMODE       ((unsigned int) 0x3 << 14)	// (DBGU) Channel Mode +#define 	AT91C_US_CHMODE_NORMAL               ((unsigned int) 0x0 << 14)	// (DBGU) Normal Mode: The USART channel operates as an RX/TX USART. +#define 	AT91C_US_CHMODE_AUTO                 ((unsigned int) 0x1 << 14)	// (DBGU) Automatic Echo: Receiver Data Input is connected to the TXD pin. +#define 	AT91C_US_CHMODE_LOCAL                ((unsigned int) 0x2 << 14)	// (DBGU) Local Loopback: Transmitter Output Signal is connected to Receiver Input Signal. +#define 	AT91C_US_CHMODE_REMOTE               ((unsigned int) 0x3 << 14)	// (DBGU) Remote Loopback: RXD pin is internally connected to TXD pin. +// -------- DBGU_IER : (DBGU Offset: 0x8) Debug Unit Interrupt Enable Register --------  +#define AT91C_US_RXRDY        ((unsigned int) 0x1 <<  0)	// (DBGU) RXRDY Interrupt +#define AT91C_US_TXRDY        ((unsigned int) 0x1 <<  1)	// (DBGU) TXRDY Interrupt +#define AT91C_US_ENDRX        ((unsigned int) 0x1 <<  3)	// (DBGU) End of Receive Transfer Interrupt +#define AT91C_US_ENDTX        ((unsigned int) 0x1 <<  4)	// (DBGU) End of Transmit Interrupt +#define AT91C_US_OVRE         ((unsigned int) 0x1 <<  5)	// (DBGU) Overrun Interrupt +#define AT91C_US_FRAME        ((unsigned int) 0x1 <<  6)	// (DBGU) Framing Error Interrupt +#define AT91C_US_PARE         ((unsigned int) 0x1 <<  7)	// (DBGU) Parity Error Interrupt +#define AT91C_US_TXEMPTY      ((unsigned int) 0x1 <<  9)	// (DBGU) TXEMPTY Interrupt +#define AT91C_US_TXBUFE       ((unsigned int) 0x1 << 11)	// (DBGU) TXBUFE Interrupt +#define AT91C_US_RXBUFF       ((unsigned int) 0x1 << 12)	// (DBGU) RXBUFF Interrupt +#define AT91C_US_COMM_TX      ((unsigned int) 0x1 << 30)	// (DBGU) COMM_TX Interrupt +#define AT91C_US_COMM_RX      ((unsigned int) 0x1 << 31)	// (DBGU) COMM_RX Interrupt +// -------- DBGU_IDR : (DBGU Offset: 0xc) Debug Unit Interrupt Disable Register --------  +// -------- DBGU_IMR : (DBGU Offset: 0x10) Debug Unit Interrupt Mask Register --------  +// -------- DBGU_CSR : (DBGU Offset: 0x14) Debug Unit Channel Status Register --------  +// -------- DBGU_FNTR : (DBGU Offset: 0x48) Debug Unit FORCE_NTRST Register --------  +#define AT91C_US_FORCE_NTRST  ((unsigned int) 0x1 <<  0)	// (DBGU) Force NTRST in JTAG + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Parallel Input Output Controler +// ***************************************************************************** +typedef struct _AT91S_PIO +{ +  AT91_REG PIO_PER;		// PIO Enable Register +  AT91_REG PIO_PDR;		// PIO Disable Register +  AT91_REG PIO_PSR;		// PIO Status Register +  AT91_REG Reserved0[1];	//  +  AT91_REG PIO_OER;		// Output Enable Register +  AT91_REG PIO_ODR;		// Output Disable Registerr +  AT91_REG PIO_OSR;		// Output Status Register +  AT91_REG Reserved1[1];	//  +  AT91_REG PIO_IFER;		// Input Filter Enable Register +  AT91_REG PIO_IFDR;		// Input Filter Disable Register +  AT91_REG PIO_IFSR;		// Input Filter Status Register +  AT91_REG Reserved2[1];	//  +  AT91_REG PIO_SODR;		// Set Output Data Register +  AT91_REG PIO_CODR;		// Clear Output Data Register +  AT91_REG PIO_ODSR;		// Output Data Status Register +  AT91_REG PIO_PDSR;		// Pin Data Status Register +  AT91_REG PIO_IER;		// Interrupt Enable Register +  AT91_REG PIO_IDR;		// Interrupt Disable Register +  AT91_REG PIO_IMR;		// Interrupt Mask Register +  AT91_REG PIO_ISR;		// Interrupt Status Register +  AT91_REG PIO_MDER;		// Multi-driver Enable Register +  AT91_REG PIO_MDDR;		// Multi-driver Disable Register +  AT91_REG PIO_MDSR;		// Multi-driver Status Register +  AT91_REG Reserved3[1];	//  +  AT91_REG PIO_PPUDR;		// Pull-up Disable Register +  AT91_REG PIO_PPUER;		// Pull-up Enable Register +  AT91_REG PIO_PPUSR;		// Pull-up Status Register +  AT91_REG Reserved4[1];	//  +  AT91_REG PIO_ASR;		// Select A Register +  AT91_REG PIO_BSR;		// Select B Register +  AT91_REG PIO_ABSR;		// AB Select Status Register +  AT91_REG Reserved5[9];	//  +  AT91_REG PIO_OWER;		// Output Write Enable Register +  AT91_REG PIO_OWDR;		// Output Write Disable Register +  AT91_REG PIO_OWSR;		// Output Write Status Register +} AT91S_PIO, *AT91PS_PIO; + + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Clock Generator Controler +// ***************************************************************************** +typedef struct _AT91S_CKGR +{ +  AT91_REG CKGR_MOR;		// Main Oscillator Register +  AT91_REG CKGR_MCFR;		// Main Clock  Frequency Register +  AT91_REG Reserved0[1];	//  +  AT91_REG CKGR_PLLR;		// PLL Register +} AT91S_CKGR, *AT91PS_CKGR; + +// -------- CKGR_MOR : (CKGR Offset: 0x0) Main Oscillator Register --------  +#define AT91C_CKGR_MOSCEN     ((unsigned int) 0x1 <<  0)	// (CKGR) Main Oscillator Enable +#define AT91C_CKGR_OSCBYPASS  ((unsigned int) 0x1 <<  1)	// (CKGR) Main Oscillator Bypass +#define AT91C_CKGR_OSCOUNT    ((unsigned int) 0xFF <<  8)	// (CKGR) Main Oscillator Start-up Time +// -------- CKGR_MCFR : (CKGR Offset: 0x4) Main Clock Frequency Register --------  +#define AT91C_CKGR_MAINF      ((unsigned int) 0xFFFF <<  0)	// (CKGR) Main Clock Frequency +#define AT91C_CKGR_MAINRDY    ((unsigned int) 0x1 << 16)	// (CKGR) Main Clock Ready +// -------- CKGR_PLLR : (CKGR Offset: 0xc) PLL B Register --------  +#define AT91C_CKGR_DIV        ((unsigned int) 0xFF <<  0)	// (CKGR) Divider Selected +#define 	AT91C_CKGR_DIV_0                    ((unsigned int) 0x0)	// (CKGR) Divider output is 0 +#define 	AT91C_CKGR_DIV_BYPASS               ((unsigned int) 0x1)	// (CKGR) Divider is bypassed +#define AT91C_CKGR_PLLCOUNT   ((unsigned int) 0x3F <<  8)	// (CKGR) PLL Counter +#define AT91C_CKGR_OUT        ((unsigned int) 0x3 << 14)	// (CKGR) PLL Output Frequency Range +#define 	AT91C_CKGR_OUT_0                    ((unsigned int) 0x0 << 14)	// (CKGR) Please refer to the PLL datasheet +#define 	AT91C_CKGR_OUT_1                    ((unsigned int) 0x1 << 14)	// (CKGR) Please refer to the PLL datasheet +#define 	AT91C_CKGR_OUT_2                    ((unsigned int) 0x2 << 14)	// (CKGR) Please refer to the PLL datasheet +#define 	AT91C_CKGR_OUT_3                    ((unsigned int) 0x3 << 14)	// (CKGR) Please refer to the PLL datasheet +#define AT91C_CKGR_MUL        ((unsigned int) 0x7FF << 16)	// (CKGR) PLL Multiplier +#define AT91C_CKGR_USBDIV     ((unsigned int) 0x3 << 28)	// (CKGR) Divider for USB Clocks +#define 	AT91C_CKGR_USBDIV_0                    ((unsigned int) 0x0 << 28)	// (CKGR) Divider output is PLL clock output +#define 	AT91C_CKGR_USBDIV_1                    ((unsigned int) 0x1 << 28)	// (CKGR) Divider output is PLL clock output divided by 2 +#define 	AT91C_CKGR_USBDIV_2                    ((unsigned int) 0x2 << 28)	// (CKGR) Divider output is PLL clock output divided by 4 + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Power Management Controler +// ***************************************************************************** +typedef struct _AT91S_PMC +{ +  AT91_REG PMC_SCER;		// System Clock Enable Register +  AT91_REG PMC_SCDR;		// System Clock Disable Register +  AT91_REG PMC_SCSR;		// System Clock Status Register +  AT91_REG Reserved0[1];	//  +  AT91_REG PMC_PCER;		// Peripheral Clock Enable Register +  AT91_REG PMC_PCDR;		// Peripheral Clock Disable Register +  AT91_REG PMC_PCSR;		// Peripheral Clock Status Register +  AT91_REG Reserved1[1];	//  +  AT91_REG PMC_MOR;		// Main Oscillator Register +  AT91_REG PMC_MCFR;		// Main Clock  Frequency Register +  AT91_REG Reserved2[1];	//  +  AT91_REG PMC_PLLR;		// PLL Register +  AT91_REG PMC_MCKR;		// Master Clock Register +  AT91_REG Reserved3[3];	//  +  AT91_REG PMC_PCKR[3];		// Programmable Clock Register +  AT91_REG Reserved4[5];	//  +  AT91_REG PMC_IER;		// Interrupt Enable Register +  AT91_REG PMC_IDR;		// Interrupt Disable Register +  AT91_REG PMC_SR;		// Status Register +  AT91_REG PMC_IMR;		// Interrupt Mask Register +} AT91S_PMC, *AT91PS_PMC; + +// -------- PMC_SCER : (PMC Offset: 0x0) System Clock Enable Register --------  +#define AT91C_PMC_PCK         ((unsigned int) 0x1 <<  0)	// (PMC) Processor Clock +#define AT91C_PMC_UDP         ((unsigned int) 0x1 <<  7)	// (PMC) USB Device Port Clock +#define AT91C_PMC_PCK0        ((unsigned int) 0x1 <<  8)	// (PMC) Programmable Clock Output +#define AT91C_PMC_PCK1        ((unsigned int) 0x1 <<  9)	// (PMC) Programmable Clock Output +#define AT91C_PMC_PCK2        ((unsigned int) 0x1 << 10)	// (PMC) Programmable Clock Output +// -------- PMC_SCDR : (PMC Offset: 0x4) System Clock Disable Register --------  +// -------- PMC_SCSR : (PMC Offset: 0x8) System Clock Status Register --------  +// -------- CKGR_MOR : (PMC Offset: 0x20) Main Oscillator Register --------  +// -------- CKGR_MCFR : (PMC Offset: 0x24) Main Clock Frequency Register --------  +// -------- CKGR_PLLR : (PMC Offset: 0x2c) PLL B Register --------  +// -------- PMC_MCKR : (PMC Offset: 0x30) Master Clock Register --------  +#define AT91C_PMC_CSS         ((unsigned int) 0x3 <<  0)	// (PMC) Programmable Clock Selection +#define 	AT91C_PMC_CSS_SLOW_CLK             ((unsigned int) 0x0)	// (PMC) Slow Clock is selected +#define 	AT91C_PMC_CSS_MAIN_CLK             ((unsigned int) 0x1)	// (PMC) Main Clock is selected +#define 	AT91C_PMC_CSS_PLL_CLK              ((unsigned int) 0x3)	// (PMC) Clock from PLL is selected +#define AT91C_PMC_PRES        ((unsigned int) 0x7 <<  2)	// (PMC) Programmable Clock Prescaler +#define 	AT91C_PMC_PRES_CLK                  ((unsigned int) 0x0 <<  2)	// (PMC) Selected clock +#define 	AT91C_PMC_PRES_CLK_2                ((unsigned int) 0x1 <<  2)	// (PMC) Selected clock divided by 2 +#define 	AT91C_PMC_PRES_CLK_4                ((unsigned int) 0x2 <<  2)	// (PMC) Selected clock divided by 4 +#define 	AT91C_PMC_PRES_CLK_8                ((unsigned int) 0x3 <<  2)	// (PMC) Selected clock divided by 8 +#define 	AT91C_PMC_PRES_CLK_16               ((unsigned int) 0x4 <<  2)	// (PMC) Selected clock divided by 16 +#define 	AT91C_PMC_PRES_CLK_32               ((unsigned int) 0x5 <<  2)	// (PMC) Selected clock divided by 32 +#define 	AT91C_PMC_PRES_CLK_64               ((unsigned int) 0x6 <<  2)	// (PMC) Selected clock divided by 64 +// -------- PMC_PCKR : (PMC Offset: 0x40) Programmable Clock Register --------  +// -------- PMC_IER : (PMC Offset: 0x60) PMC Interrupt Enable Register --------  +#define AT91C_PMC_MOSCS       ((unsigned int) 0x1 <<  0)	// (PMC) MOSC Status/Enable/Disable/Mask +#define AT91C_PMC_LOCK        ((unsigned int) 0x1 <<  2)	// (PMC) PLL Status/Enable/Disable/Mask +#define AT91C_PMC_MCKRDY      ((unsigned int) 0x1 <<  3)	// (PMC) MCK_RDY Status/Enable/Disable/Mask +#define AT91C_PMC_PCK0RDY     ((unsigned int) 0x1 <<  8)	// (PMC) PCK0_RDY Status/Enable/Disable/Mask +#define AT91C_PMC_PCK1RDY     ((unsigned int) 0x1 <<  9)	// (PMC) PCK1_RDY Status/Enable/Disable/Mask +#define AT91C_PMC_PCK2RDY     ((unsigned int) 0x1 << 10)	// (PMC) PCK2_RDY Status/Enable/Disable/Mask +// -------- PMC_IDR : (PMC Offset: 0x64) PMC Interrupt Disable Register --------  +// -------- PMC_SR : (PMC Offset: 0x68) PMC Status Register --------  +// -------- PMC_IMR : (PMC Offset: 0x6c) PMC Interrupt Mask Register --------  + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Reset Controller Interface +// ***************************************************************************** +typedef struct _AT91S_RSTC +{ +  AT91_REG RSTC_RCR;		// Reset Control Register +  AT91_REG RSTC_RSR;		// Reset Status Register +  AT91_REG RSTC_RMR;		// Reset Mode Register +} AT91S_RSTC, *AT91PS_RSTC; + +// -------- RSTC_RCR : (RSTC Offset: 0x0) Reset Control Register --------  +#define AT91C_RSTC_PROCRST    ((unsigned int) 0x1 <<  0)	// (RSTC) Processor Reset +#define AT91C_RSTC_PERRST     ((unsigned int) 0x1 <<  2)	// (RSTC) Peripheral Reset +#define AT91C_RSTC_EXTRST     ((unsigned int) 0x1 <<  3)	// (RSTC) External Reset +#define AT91C_RSTC_KEY        ((unsigned int) 0xFF << 24)	// (RSTC) Password +// -------- RSTC_RSR : (RSTC Offset: 0x4) Reset Status Register --------  +#define AT91C_RSTC_URSTS      ((unsigned int) 0x1 <<  0)	// (RSTC) User Reset Status +#define AT91C_RSTC_BODSTS     ((unsigned int) 0x1 <<  1)	// (RSTC) Brownout Detection Status +#define AT91C_RSTC_RSTTYP     ((unsigned int) 0x7 <<  8)	// (RSTC) Reset Type +#define 	AT91C_RSTC_RSTTYP_POWERUP              ((unsigned int) 0x0 <<  8)	// (RSTC) Power-up Reset. VDDCORE rising. +#define 	AT91C_RSTC_RSTTYP_WAKEUP               ((unsigned int) 0x1 <<  8)	// (RSTC) WakeUp Reset. VDDCORE rising. +#define 	AT91C_RSTC_RSTTYP_WATCHDOG             ((unsigned int) 0x2 <<  8)	// (RSTC) Watchdog Reset. Watchdog overflow occured. +#define 	AT91C_RSTC_RSTTYP_SOFTWARE             ((unsigned int) 0x3 <<  8)	// (RSTC) Software Reset. Processor reset required by the software. +#define 	AT91C_RSTC_RSTTYP_USER                 ((unsigned int) 0x4 <<  8)	// (RSTC) User Reset. NRST pin detected low. +#define 	AT91C_RSTC_RSTTYP_BROWNOUT             ((unsigned int) 0x5 <<  8)	// (RSTC) Brownout Reset occured. +#define AT91C_RSTC_NRSTL      ((unsigned int) 0x1 << 16)	// (RSTC) NRST pin level +#define AT91C_RSTC_SRCMP      ((unsigned int) 0x1 << 17)	// (RSTC) Software Reset Command in Progress. +// -------- RSTC_RMR : (RSTC Offset: 0x8) Reset Mode Register --------  +#define AT91C_RSTC_URSTEN     ((unsigned int) 0x1 <<  0)	// (RSTC) User Reset Enable +#define AT91C_RSTC_URSTIEN    ((unsigned int) 0x1 <<  4)	// (RSTC) User Reset Interrupt Enable +#define AT91C_RSTC_ERSTL      ((unsigned int) 0xF <<  8)	// (RSTC) User Reset Length +#define AT91C_RSTC_BODIEN     ((unsigned int) 0x1 << 16)	// (RSTC) Brownout Detection Interrupt Enable + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Real Time Timer Controller Interface +// ***************************************************************************** +typedef struct _AT91S_RTTC +{ +  AT91_REG RTTC_RTMR;		// Real-time Mode Register +  AT91_REG RTTC_RTAR;		// Real-time Alarm Register +  AT91_REG RTTC_RTVR;		// Real-time Value Register +  AT91_REG RTTC_RTSR;		// Real-time Status Register +} AT91S_RTTC, *AT91PS_RTTC; + +// -------- RTTC_RTMR : (RTTC Offset: 0x0) Real-time Mode Register --------  +#define AT91C_RTTC_RTPRES     ((unsigned int) 0xFFFF <<  0)	// (RTTC) Real-time Timer Prescaler Value +#define AT91C_RTTC_ALMIEN     ((unsigned int) 0x1 << 16)	// (RTTC) Alarm Interrupt Enable +#define AT91C_RTTC_RTTINCIEN  ((unsigned int) 0x1 << 17)	// (RTTC) Real Time Timer Increment Interrupt Enable +#define AT91C_RTTC_RTTRST     ((unsigned int) 0x1 << 18)	// (RTTC) Real Time Timer Restart +// -------- RTTC_RTAR : (RTTC Offset: 0x4) Real-time Alarm Register --------  +#define AT91C_RTTC_ALMV       ((unsigned int) 0x0 <<  0)	// (RTTC) Alarm Value +// -------- RTTC_RTVR : (RTTC Offset: 0x8) Current Real-time Value Register --------  +#define AT91C_RTTC_CRTV       ((unsigned int) 0x0 <<  0)	// (RTTC) Current Real-time Value +// -------- RTTC_RTSR : (RTTC Offset: 0xc) Real-time Status Register --------  +#define AT91C_RTTC_ALMS       ((unsigned int) 0x1 <<  0)	// (RTTC) Real-time Alarm Status +#define AT91C_RTTC_RTTINC     ((unsigned int) 0x1 <<  1)	// (RTTC) Real-time Timer Increment + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Periodic Interval Timer Controller Interface +// ***************************************************************************** +typedef struct _AT91S_PITC +{ +  AT91_REG PITC_PIMR;		// Period Interval Mode Register +  AT91_REG PITC_PISR;		// Period Interval Status Register +  AT91_REG PITC_PIVR;		// Period Interval Value Register +  AT91_REG PITC_PIIR;		// Period Interval Image Register +} AT91S_PITC, *AT91PS_PITC; + +// -------- PITC_PIMR : (PITC Offset: 0x0) Periodic Interval Mode Register --------  +#define AT91C_PITC_PIV        ((unsigned int) 0xFFFFF <<  0)	// (PITC) Periodic Interval Value +#define AT91C_PITC_PITEN      ((unsigned int) 0x1 << 24)	// (PITC) Periodic Interval Timer Enabled +#define AT91C_PITC_PITIEN     ((unsigned int) 0x1 << 25)	// (PITC) Periodic Interval Timer Interrupt Enable +// -------- PITC_PISR : (PITC Offset: 0x4) Periodic Interval Status Register --------  +#define AT91C_PITC_PITS       ((unsigned int) 0x1 <<  0)	// (PITC) Periodic Interval Timer Status +// -------- PITC_PIVR : (PITC Offset: 0x8) Periodic Interval Value Register --------  +#define AT91C_PITC_CPIV       ((unsigned int) 0xFFFFF <<  0)	// (PITC) Current Periodic Interval Value +#define AT91C_PITC_PICNT      ((unsigned int) 0xFFF << 20)	// (PITC) Periodic Interval Counter +// -------- PITC_PIIR : (PITC Offset: 0xc) Periodic Interval Image Register --------  + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Watchdog Timer Controller Interface +// ***************************************************************************** +typedef struct _AT91S_WDTC +{ +  AT91_REG WDTC_WDCR;		// Watchdog Control Register +  AT91_REG WDTC_WDMR;		// Watchdog Mode Register +  AT91_REG WDTC_WDSR;		// Watchdog Status Register +} AT91S_WDTC, *AT91PS_WDTC; + +// -------- WDTC_WDCR : (WDTC Offset: 0x0) Periodic Interval Image Register --------  +#define AT91C_WDTC_WDRSTT     ((unsigned int) 0x1 <<  0)	// (WDTC) Watchdog Restart +#define AT91C_WDTC_KEY        ((unsigned int) 0xFF << 24)	// (WDTC) Watchdog KEY Password +// -------- WDTC_WDMR : (WDTC Offset: 0x4) Watchdog Mode Register --------  +#define AT91C_WDTC_WDV        ((unsigned int) 0xFFF <<  0)	// (WDTC) Watchdog Timer Restart +#define AT91C_WDTC_WDFIEN     ((unsigned int) 0x1 << 12)	// (WDTC) Watchdog Fault Interrupt Enable +#define AT91C_WDTC_WDRSTEN    ((unsigned int) 0x1 << 13)	// (WDTC) Watchdog Reset Enable +#define AT91C_WDTC_WDRPROC    ((unsigned int) 0x1 << 14)	// (WDTC) Watchdog Timer Restart +#define AT91C_WDTC_WDDIS      ((unsigned int) 0x1 << 15)	// (WDTC) Watchdog Disable +#define AT91C_WDTC_WDD        ((unsigned int) 0xFFF << 16)	// (WDTC) Watchdog Delta Value +#define AT91C_WDTC_WDDBGHLT   ((unsigned int) 0x1 << 28)	// (WDTC) Watchdog Debug Halt +#define AT91C_WDTC_WDIDLEHLT  ((unsigned int) 0x1 << 29)	// (WDTC) Watchdog Idle Halt +// -------- WDTC_WDSR : (WDTC Offset: 0x8) Watchdog Status Register --------  +#define AT91C_WDTC_WDUNF      ((unsigned int) 0x1 <<  0)	// (WDTC) Watchdog Underflow +#define AT91C_WDTC_WDERR      ((unsigned int) 0x1 <<  1)	// (WDTC) Watchdog Error + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Voltage Regulator Mode Controller Interface +// ***************************************************************************** +typedef struct _AT91S_VREG +{ +  AT91_REG VREG_MR;		// Voltage Regulator Mode Register +} AT91S_VREG, *AT91PS_VREG; + +// -------- VREG_MR : (VREG Offset: 0x0) Voltage Regulator Mode Register --------  +#define AT91C_VREG_PSTDBY     ((unsigned int) 0x1 <<  0)	// (VREG) Voltage Regulator Power Standby Mode + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Memory Controller Interface +// ***************************************************************************** +typedef struct _AT91S_MC +{ +  AT91_REG MC_RCR;		// MC Remap Control Register +  AT91_REG MC_ASR;		// MC Abort Status Register +  AT91_REG MC_AASR;		// MC Abort Address Status Register +  AT91_REG Reserved0[21];	//  +  AT91_REG MC_FMR;		// MC Flash Mode Register +  AT91_REG MC_FCR;		// MC Flash Command Register +  AT91_REG MC_FSR;		// MC Flash Status Register +} AT91S_MC, *AT91PS_MC; + +// -------- MC_RCR : (MC Offset: 0x0) MC Remap Control Register --------  +#define AT91C_MC_RCB          ((unsigned int) 0x1 <<  0)	// (MC) Remap Command Bit +// -------- MC_ASR : (MC Offset: 0x4) MC Abort Status Register --------  +#define AT91C_MC_UNDADD       ((unsigned int) 0x1 <<  0)	// (MC) Undefined Addess Abort Status +#define AT91C_MC_MISADD       ((unsigned int) 0x1 <<  1)	// (MC) Misaligned Addess Abort Status +#define AT91C_MC_ABTSZ        ((unsigned int) 0x3 <<  8)	// (MC) Abort Size Status +#define 	AT91C_MC_ABTSZ_BYTE                 ((unsigned int) 0x0 <<  8)	// (MC) Byte +#define 	AT91C_MC_ABTSZ_HWORD                ((unsigned int) 0x1 <<  8)	// (MC) Half-word +#define 	AT91C_MC_ABTSZ_WORD                 ((unsigned int) 0x2 <<  8)	// (MC) Word +#define AT91C_MC_ABTTYP       ((unsigned int) 0x3 << 10)	// (MC) Abort Type Status +#define 	AT91C_MC_ABTTYP_DATAR                ((unsigned int) 0x0 << 10)	// (MC) Data Read +#define 	AT91C_MC_ABTTYP_DATAW                ((unsigned int) 0x1 << 10)	// (MC) Data Write +#define 	AT91C_MC_ABTTYP_FETCH                ((unsigned int) 0x2 << 10)	// (MC) Code Fetch +#define AT91C_MC_MST0         ((unsigned int) 0x1 << 16)	// (MC) Master 0 Abort Source +#define AT91C_MC_MST1         ((unsigned int) 0x1 << 17)	// (MC) Master 1 Abort Source +#define AT91C_MC_SVMST0       ((unsigned int) 0x1 << 24)	// (MC) Saved Master 0 Abort Source +#define AT91C_MC_SVMST1       ((unsigned int) 0x1 << 25)	// (MC) Saved Master 1 Abort Source +// -------- MC_FMR : (MC Offset: 0x60) MC Flash Mode Register --------  +#define AT91C_MC_FRDY         ((unsigned int) 0x1 <<  0)	// (MC) Flash Ready +#define AT91C_MC_LOCKE        ((unsigned int) 0x1 <<  2)	// (MC) Lock Error +#define AT91C_MC_PROGE        ((unsigned int) 0x1 <<  3)	// (MC) Programming Error +#define AT91C_MC_NEBP         ((unsigned int) 0x1 <<  7)	// (MC) No Erase Before Programming +#define AT91C_MC_FWS          ((unsigned int) 0x3 <<  8)	// (MC) Flash Wait State +#define 	AT91C_MC_FWS_0FWS                 ((unsigned int) 0x0 <<  8)	// (MC) 1 cycle for Read, 2 for Write operations +#define 	AT91C_MC_FWS_1FWS                 ((unsigned int) 0x1 <<  8)	// (MC) 2 cycles for Read, 3 for Write operations +#define 	AT91C_MC_FWS_2FWS                 ((unsigned int) 0x2 <<  8)	// (MC) 3 cycles for Read, 4 for Write operations +#define 	AT91C_MC_FWS_3FWS                 ((unsigned int) 0x3 <<  8)	// (MC) 4 cycles for Read, 4 for Write operations +#define AT91C_MC_FMCN         ((unsigned int) 0xFF << 16)	// (MC) Flash Microsecond Cycle Number +// -------- MC_FCR : (MC Offset: 0x64) MC Flash Command Register --------  +#define AT91C_MC_FCMD         ((unsigned int) 0xF <<  0)	// (MC) Flash Command +#define 	AT91C_MC_FCMD_START_PROG           ((unsigned int) 0x1)	// (MC) Starts the programming of th epage specified by PAGEN. +#define 	AT91C_MC_FCMD_LOCK                 ((unsigned int) 0x2)	// (MC) Starts a lock sequence of the sector defined by the bits 4 to 7 of the field PAGEN. +#define 	AT91C_MC_FCMD_PROG_AND_LOCK        ((unsigned int) 0x3)	// (MC) The lock sequence automatically happens after the programming sequence is completed. +#define 	AT91C_MC_FCMD_UNLOCK               ((unsigned int) 0x4)	// (MC) Starts an unlock sequence of the sector defined by the bits 4 to 7 of the field PAGEN. +#define 	AT91C_MC_FCMD_ERASE_ALL            ((unsigned int) 0x8)	// (MC) Starts the erase of the entire flash.If at least a page is locked, the command is cancelled. +#define 	AT91C_MC_FCMD_SET_GP_NVM           ((unsigned int) 0xB)	// (MC) Set General Purpose NVM bits. +#define 	AT91C_MC_FCMD_CLR_GP_NVM           ((unsigned int) 0xD)	// (MC) Clear General Purpose NVM bits. +#define 	AT91C_MC_FCMD_SET_SECURITY         ((unsigned int) 0xF)	// (MC) Set Security Bit. +#define AT91C_MC_PAGEN        ((unsigned int) 0x3FF <<  8)	// (MC) Page Number +#define AT91C_MC_KEY          ((unsigned int) 0xFF << 24)	// (MC) Writing Protect Key +// -------- MC_FSR : (MC Offset: 0x68) MC Flash Command Register --------  +#define AT91C_MC_SECURITY     ((unsigned int) 0x1 <<  4)	// (MC) Security Bit Status +#define AT91C_MC_GPNVM0       ((unsigned int) 0x1 <<  8)	// (MC) Sector 0 Lock Status +#define AT91C_MC_GPNVM1       ((unsigned int) 0x1 <<  9)	// (MC) Sector 1 Lock Status +#define AT91C_MC_GPNVM2       ((unsigned int) 0x1 << 10)	// (MC) Sector 2 Lock Status +#define AT91C_MC_GPNVM3       ((unsigned int) 0x1 << 11)	// (MC) Sector 3 Lock Status +#define AT91C_MC_GPNVM4       ((unsigned int) 0x1 << 12)	// (MC) Sector 4 Lock Status +#define AT91C_MC_GPNVM5       ((unsigned int) 0x1 << 13)	// (MC) Sector 5 Lock Status +#define AT91C_MC_GPNVM6       ((unsigned int) 0x1 << 14)	// (MC) Sector 6 Lock Status +#define AT91C_MC_GPNVM7       ((unsigned int) 0x1 << 15)	// (MC) Sector 7 Lock Status +#define AT91C_MC_LOCKS0       ((unsigned int) 0x1 << 16)	// (MC) Sector 0 Lock Status +#define AT91C_MC_LOCKS1       ((unsigned int) 0x1 << 17)	// (MC) Sector 1 Lock Status +#define AT91C_MC_LOCKS2       ((unsigned int) 0x1 << 18)	// (MC) Sector 2 Lock Status +#define AT91C_MC_LOCKS3       ((unsigned int) 0x1 << 19)	// (MC) Sector 3 Lock Status +#define AT91C_MC_LOCKS4       ((unsigned int) 0x1 << 20)	// (MC) Sector 4 Lock Status +#define AT91C_MC_LOCKS5       ((unsigned int) 0x1 << 21)	// (MC) Sector 5 Lock Status +#define AT91C_MC_LOCKS6       ((unsigned int) 0x1 << 22)	// (MC) Sector 6 Lock Status +#define AT91C_MC_LOCKS7       ((unsigned int) 0x1 << 23)	// (MC) Sector 7 Lock Status +#define AT91C_MC_LOCKS8       ((unsigned int) 0x1 << 24)	// (MC) Sector 8 Lock Status +#define AT91C_MC_LOCKS9       ((unsigned int) 0x1 << 25)	// (MC) Sector 9 Lock Status +#define AT91C_MC_LOCKS10      ((unsigned int) 0x1 << 26)	// (MC) Sector 10 Lock Status +#define AT91C_MC_LOCKS11      ((unsigned int) 0x1 << 27)	// (MC) Sector 11 Lock Status +#define AT91C_MC_LOCKS12      ((unsigned int) 0x1 << 28)	// (MC) Sector 12 Lock Status +#define AT91C_MC_LOCKS13      ((unsigned int) 0x1 << 29)	// (MC) Sector 13 Lock Status +#define AT91C_MC_LOCKS14      ((unsigned int) 0x1 << 30)	// (MC) Sector 14 Lock Status +#define AT91C_MC_LOCKS15      ((unsigned int) 0x1 << 31)	// (MC) Sector 15 Lock Status + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Serial Parallel Interface +// ***************************************************************************** +typedef struct _AT91S_SPI +{ +  AT91_REG SPI_CR;		// Control Register +  AT91_REG SPI_MR;		// Mode Register +  AT91_REG SPI_RDR;		// Receive Data Register +  AT91_REG SPI_TDR;		// Transmit Data Register +  AT91_REG SPI_SR;		// Status Register +  AT91_REG SPI_IER;		// Interrupt Enable Register +  AT91_REG SPI_IDR;		// Interrupt Disable Register +  AT91_REG SPI_IMR;		// Interrupt Mask Register +  AT91_REG Reserved0[4];	//  +  AT91_REG SPI_CSR[4];		// Chip Select Register +  AT91_REG Reserved1[48];	//  +  AT91_REG SPI_RPR;		// Receive Pointer Register +  AT91_REG SPI_RCR;		// Receive Counter Register +  AT91_REG SPI_TPR;		// Transmit Pointer Register +  AT91_REG SPI_TCR;		// Transmit Counter Register +  AT91_REG SPI_RNPR;		// Receive Next Pointer Register +  AT91_REG SPI_RNCR;		// Receive Next Counter Register +  AT91_REG SPI_TNPR;		// Transmit Next Pointer Register +  AT91_REG SPI_TNCR;		// Transmit Next Counter Register +  AT91_REG SPI_PTCR;		// PDC Transfer Control Register +  AT91_REG SPI_PTSR;		// PDC Transfer Status Register +} AT91S_SPI, *AT91PS_SPI; + +// -------- SPI_CR : (SPI Offset: 0x0) SPI Control Register --------  +#define AT91C_SPI_SPIEN       ((unsigned int) 0x1 <<  0)	// (SPI) SPI Enable +#define AT91C_SPI_SPIDIS      ((unsigned int) 0x1 <<  1)	// (SPI) SPI Disable +#define AT91C_SPI_SWRST       ((unsigned int) 0x1 <<  7)	// (SPI) SPI Software reset +#define AT91C_SPI_LASTXFER    ((unsigned int) 0x1 << 24)	// (SPI) SPI Last Transfer +// -------- SPI_MR : (SPI Offset: 0x4) SPI Mode Register --------  +#define AT91C_SPI_MSTR        ((unsigned int) 0x1 <<  0)	// (SPI) Master/Slave Mode +#define AT91C_SPI_PS          ((unsigned int) 0x1 <<  1)	// (SPI) Peripheral Select +#define 	AT91C_SPI_PS_FIXED                ((unsigned int) 0x0 <<  1)	// (SPI) Fixed Peripheral Select +#define 	AT91C_SPI_PS_VARIABLE             ((unsigned int) 0x1 <<  1)	// (SPI) Variable Peripheral Select +#define AT91C_SPI_PCSDEC      ((unsigned int) 0x1 <<  2)	// (SPI) Chip Select Decode +#define AT91C_SPI_FDIV        ((unsigned int) 0x1 <<  3)	// (SPI) Clock Selection +#define AT91C_SPI_MODFDIS     ((unsigned int) 0x1 <<  4)	// (SPI) Mode Fault Detection +#define AT91C_SPI_LLB         ((unsigned int) 0x1 <<  7)	// (SPI) Clock Selection +#define AT91C_SPI_PCS         ((unsigned int) 0xF << 16)	// (SPI) Peripheral Chip Select +#define AT91C_SPI_DLYBCS      ((unsigned int) 0xFF << 24)	// (SPI) Delay Between Chip Selects +// -------- SPI_RDR : (SPI Offset: 0x8) Receive Data Register --------  +#define AT91C_SPI_RD          ((unsigned int) 0xFFFF <<  0)	// (SPI) Receive Data +#define AT91C_SPI_RPCS        ((unsigned int) 0xF << 16)	// (SPI) Peripheral Chip Select Status +// -------- SPI_TDR : (SPI Offset: 0xc) Transmit Data Register --------  +#define AT91C_SPI_TD          ((unsigned int) 0xFFFF <<  0)	// (SPI) Transmit Data +#define AT91C_SPI_TPCS        ((unsigned int) 0xF << 16)	// (SPI) Peripheral Chip Select Status +// -------- SPI_SR : (SPI Offset: 0x10) Status Register --------  +#define AT91C_SPI_RDRF        ((unsigned int) 0x1 <<  0)	// (SPI) Receive Data Register Full +#define AT91C_SPI_TDRE        ((unsigned int) 0x1 <<  1)	// (SPI) Transmit Data Register Empty +#define AT91C_SPI_MODF        ((unsigned int) 0x1 <<  2)	// (SPI) Mode Fault Error +#define AT91C_SPI_OVRES       ((unsigned int) 0x1 <<  3)	// (SPI) Overrun Error Status +#define AT91C_SPI_ENDRX       ((unsigned int) 0x1 <<  4)	// (SPI) End of Receiver Transfer +#define AT91C_SPI_ENDTX       ((unsigned int) 0x1 <<  5)	// (SPI) End of Receiver Transfer +#define AT91C_SPI_RXBUFF      ((unsigned int) 0x1 <<  6)	// (SPI) RXBUFF Interrupt +#define AT91C_SPI_TXBUFE      ((unsigned int) 0x1 <<  7)	// (SPI) TXBUFE Interrupt +#define AT91C_SPI_NSSR        ((unsigned int) 0x1 <<  8)	// (SPI) NSSR Interrupt +#define AT91C_SPI_TXEMPTY     ((unsigned int) 0x1 <<  9)	// (SPI) TXEMPTY Interrupt +#define AT91C_SPI_SPIENS      ((unsigned int) 0x1 << 16)	// (SPI) Enable Status +// -------- SPI_IER : (SPI Offset: 0x14) Interrupt Enable Register --------  +// -------- SPI_IDR : (SPI Offset: 0x18) Interrupt Disable Register --------  +// -------- SPI_IMR : (SPI Offset: 0x1c) Interrupt Mask Register --------  +// -------- SPI_CSR : (SPI Offset: 0x30) Chip Select Register --------  +#define AT91C_SPI_CPOL        ((unsigned int) 0x1 <<  0)	// (SPI) Clock Polarity +#define AT91C_SPI_NCPHA       ((unsigned int) 0x1 <<  1)	// (SPI) Clock Phase +#define AT91C_SPI_CSAAT       ((unsigned int) 0x1 <<  3)	// (SPI) Chip Select Active After Transfer +#define AT91C_SPI_BITS        ((unsigned int) 0xF <<  4)	// (SPI) Bits Per Transfer +#define 	AT91C_SPI_BITS_8                    ((unsigned int) 0x0 <<  4)	// (SPI) 8 Bits Per transfer +#define 	AT91C_SPI_BITS_9                    ((unsigned int) 0x1 <<  4)	// (SPI) 9 Bits Per transfer +#define 	AT91C_SPI_BITS_10                   ((unsigned int) 0x2 <<  4)	// (SPI) 10 Bits Per transfer +#define 	AT91C_SPI_BITS_11                   ((unsigned int) 0x3 <<  4)	// (SPI) 11 Bits Per transfer +#define 	AT91C_SPI_BITS_12                   ((unsigned int) 0x4 <<  4)	// (SPI) 12 Bits Per transfer +#define 	AT91C_SPI_BITS_13                   ((unsigned int) 0x5 <<  4)	// (SPI) 13 Bits Per transfer +#define 	AT91C_SPI_BITS_14                   ((unsigned int) 0x6 <<  4)	// (SPI) 14 Bits Per transfer +#define 	AT91C_SPI_BITS_15                   ((unsigned int) 0x7 <<  4)	// (SPI) 15 Bits Per transfer +#define 	AT91C_SPI_BITS_16                   ((unsigned int) 0x8 <<  4)	// (SPI) 16 Bits Per transfer +#define AT91C_SPI_SCBR        ((unsigned int) 0xFF <<  8)	// (SPI) Serial Clock Baud Rate +#define AT91C_SPI_DLYBS       ((unsigned int) 0xFF << 16)	// (SPI) Delay Before SPCK +#define AT91C_SPI_DLYBCT      ((unsigned int) 0xFF << 24)	// (SPI) Delay Between Consecutive Transfers + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Analog to Digital Convertor +// ***************************************************************************** +typedef struct _AT91S_ADC +{ +  AT91_REG ADC_CR;		// ADC Control Register +  AT91_REG ADC_MR;		// ADC Mode Register +  AT91_REG Reserved0[2];	//  +  AT91_REG ADC_CHER;		// ADC Channel Enable Register +  AT91_REG ADC_CHDR;		// ADC Channel Disable Register +  AT91_REG ADC_CHSR;		// ADC Channel Status Register +  AT91_REG ADC_SR;		// ADC Status Register +  AT91_REG ADC_LCDR;		// ADC Last Converted Data Register +  AT91_REG ADC_IER;		// ADC Interrupt Enable Register +  AT91_REG ADC_IDR;		// ADC Interrupt Disable Register +  AT91_REG ADC_IMR;		// ADC Interrupt Mask Register +  AT91_REG ADC_CDR0;		// ADC Channel Data Register 0 +  AT91_REG ADC_CDR1;		// ADC Channel Data Register 1 +  AT91_REG ADC_CDR2;		// ADC Channel Data Register 2 +  AT91_REG ADC_CDR3;		// ADC Channel Data Register 3 +  AT91_REG ADC_CDR4;		// ADC Channel Data Register 4 +  AT91_REG ADC_CDR5;		// ADC Channel Data Register 5 +  AT91_REG ADC_CDR6;		// ADC Channel Data Register 6 +  AT91_REG ADC_CDR7;		// ADC Channel Data Register 7 +  AT91_REG Reserved1[44];	//  +  AT91_REG ADC_RPR;		// Receive Pointer Register +  AT91_REG ADC_RCR;		// Receive Counter Register +  AT91_REG ADC_TPR;		// Transmit Pointer Register +  AT91_REG ADC_TCR;		// Transmit Counter Register +  AT91_REG ADC_RNPR;		// Receive Next Pointer Register +  AT91_REG ADC_RNCR;		// Receive Next Counter Register +  AT91_REG ADC_TNPR;		// Transmit Next Pointer Register +  AT91_REG ADC_TNCR;		// Transmit Next Counter Register +  AT91_REG ADC_PTCR;		// PDC Transfer Control Register +  AT91_REG ADC_PTSR;		// PDC Transfer Status Register +} AT91S_ADC, *AT91PS_ADC; + +// -------- ADC_CR : (ADC Offset: 0x0) ADC Control Register --------  +#define AT91C_ADC_SWRST       ((unsigned int) 0x1 <<  0)	// (ADC) Software Reset +#define AT91C_ADC_START       ((unsigned int) 0x1 <<  1)	// (ADC) Start Conversion +// -------- ADC_MR : (ADC Offset: 0x4) ADC Mode Register --------  +#define AT91C_ADC_TRGEN       ((unsigned int) 0x1 <<  0)	// (ADC) Trigger Enable +#define 	AT91C_ADC_TRGEN_DIS                  ((unsigned int) 0x0)	// (ADC) Hradware triggers are disabled. Starting a conversion is only possible by software +#define 	AT91C_ADC_TRGEN_EN                   ((unsigned int) 0x1)	// (ADC) Hardware trigger selected by TRGSEL field is enabled. +#define AT91C_ADC_TRGSEL      ((unsigned int) 0x7 <<  1)	// (ADC) Trigger Selection +#define 	AT91C_ADC_TRGSEL_TIOA0                ((unsigned int) 0x0 <<  1)	// (ADC) Selected TRGSEL = TIAO0 +#define 	AT91C_ADC_TRGSEL_TIOA1                ((unsigned int) 0x1 <<  1)	// (ADC) Selected TRGSEL = TIAO1 +#define 	AT91C_ADC_TRGSEL_TIOA2                ((unsigned int) 0x2 <<  1)	// (ADC) Selected TRGSEL = TIAO2 +#define 	AT91C_ADC_TRGSEL_TIOA3                ((unsigned int) 0x3 <<  1)	// (ADC) Selected TRGSEL = TIAO3 +#define 	AT91C_ADC_TRGSEL_TIOA4                ((unsigned int) 0x4 <<  1)	// (ADC) Selected TRGSEL = TIAO4 +#define 	AT91C_ADC_TRGSEL_TIOA5                ((unsigned int) 0x5 <<  1)	// (ADC) Selected TRGSEL = TIAO5 +#define 	AT91C_ADC_TRGSEL_EXT                  ((unsigned int) 0x6 <<  1)	// (ADC) Selected TRGSEL = External Trigger +#define AT91C_ADC_LOWRES      ((unsigned int) 0x1 <<  4)	// (ADC) Resolution. +#define 	AT91C_ADC_LOWRES_10_BIT               ((unsigned int) 0x0 <<  4)	// (ADC) 10-bit resolution +#define 	AT91C_ADC_LOWRES_8_BIT                ((unsigned int) 0x1 <<  4)	// (ADC) 8-bit resolution +#define AT91C_ADC_SLEEP       ((unsigned int) 0x1 <<  5)	// (ADC) Sleep Mode +#define 	AT91C_ADC_SLEEP_NORMAL_MODE          ((unsigned int) 0x0 <<  5)	// (ADC) Normal Mode +#define 	AT91C_ADC_SLEEP_MODE                 ((unsigned int) 0x1 <<  5)	// (ADC) Sleep Mode +#define AT91C_ADC_PRESCAL     ((unsigned int) 0x3F <<  8)	// (ADC) Prescaler rate selection +#define AT91C_ADC_STARTUP     ((unsigned int) 0x1F << 16)	// (ADC) Startup Time +#define AT91C_ADC_SHTIM       ((unsigned int) 0xF << 24)	// (ADC) Sample & Hold Time +// --------     ADC_CHER : (ADC Offset: 0x10) ADC Channel Enable Register --------  +#define AT91C_ADC_CH0         ((unsigned int) 0x1 <<  0)	// (ADC) Channel 0 +#define AT91C_ADC_CH1         ((unsigned int) 0x1 <<  1)	// (ADC) Channel 1 +#define AT91C_ADC_CH2         ((unsigned int) 0x1 <<  2)	// (ADC) Channel 2 +#define AT91C_ADC_CH3         ((unsigned int) 0x1 <<  3)	// (ADC) Channel 3 +#define AT91C_ADC_CH4         ((unsigned int) 0x1 <<  4)	// (ADC) Channel 4 +#define AT91C_ADC_CH5         ((unsigned int) 0x1 <<  5)	// (ADC) Channel 5 +#define AT91C_ADC_CH6         ((unsigned int) 0x1 <<  6)	// (ADC) Channel 6 +#define AT91C_ADC_CH7         ((unsigned int) 0x1 <<  7)	// (ADC) Channel 7 +// --------     ADC_CHDR : (ADC Offset: 0x14) ADC Channel Disable Register --------  +// --------     ADC_CHSR : (ADC Offset: 0x18) ADC Channel Status Register --------  +// -------- ADC_SR : (ADC Offset: 0x1c) ADC Status Register --------  +#define AT91C_ADC_EOC0        ((unsigned int) 0x1 <<  0)	// (ADC) End of Conversion +#define AT91C_ADC_EOC1        ((unsigned int) 0x1 <<  1)	// (ADC) End of Conversion +#define AT91C_ADC_EOC2        ((unsigned int) 0x1 <<  2)	// (ADC) End of Conversion +#define AT91C_ADC_EOC3        ((unsigned int) 0x1 <<  3)	// (ADC) End of Conversion +#define AT91C_ADC_EOC4        ((unsigned int) 0x1 <<  4)	// (ADC) End of Conversion +#define AT91C_ADC_EOC5        ((unsigned int) 0x1 <<  5)	// (ADC) End of Conversion +#define AT91C_ADC_EOC6        ((unsigned int) 0x1 <<  6)	// (ADC) End of Conversion +#define AT91C_ADC_EOC7        ((unsigned int) 0x1 <<  7)	// (ADC) End of Conversion +#define AT91C_ADC_OVRE0       ((unsigned int) 0x1 <<  8)	// (ADC) Overrun Error +#define AT91C_ADC_OVRE1       ((unsigned int) 0x1 <<  9)	// (ADC) Overrun Error +#define AT91C_ADC_OVRE2       ((unsigned int) 0x1 << 10)	// (ADC) Overrun Error +#define AT91C_ADC_OVRE3       ((unsigned int) 0x1 << 11)	// (ADC) Overrun Error +#define AT91C_ADC_OVRE4       ((unsigned int) 0x1 << 12)	// (ADC) Overrun Error +#define AT91C_ADC_OVRE5       ((unsigned int) 0x1 << 13)	// (ADC) Overrun Error +#define AT91C_ADC_OVRE6       ((unsigned int) 0x1 << 14)	// (ADC) Overrun Error +#define AT91C_ADC_OVRE7       ((unsigned int) 0x1 << 15)	// (ADC) Overrun Error +#define AT91C_ADC_DRDY        ((unsigned int) 0x1 << 16)	// (ADC) Data Ready +#define AT91C_ADC_GOVRE       ((unsigned int) 0x1 << 17)	// (ADC) General Overrun +#define AT91C_ADC_ENDRX       ((unsigned int) 0x1 << 18)	// (ADC) End of Receiver Transfer +#define AT91C_ADC_RXBUFF      ((unsigned int) 0x1 << 19)	// (ADC) RXBUFF Interrupt +// -------- ADC_LCDR : (ADC Offset: 0x20) ADC Last Converted Data Register --------  +#define AT91C_ADC_LDATA       ((unsigned int) 0x3FF <<  0)	// (ADC) Last Data Converted +// -------- ADC_IER : (ADC Offset: 0x24) ADC Interrupt Enable Register --------  +// -------- ADC_IDR : (ADC Offset: 0x28) ADC Interrupt Disable Register --------  +// -------- ADC_IMR : (ADC Offset: 0x2c) ADC Interrupt Mask Register --------  +// -------- ADC_CDR0 : (ADC Offset: 0x30) ADC Channel Data Register 0 --------  +#define AT91C_ADC_DATA        ((unsigned int) 0x3FF <<  0)	// (ADC) Converted Data +// -------- ADC_CDR1 : (ADC Offset: 0x34) ADC Channel Data Register 1 --------  +// -------- ADC_CDR2 : (ADC Offset: 0x38) ADC Channel Data Register 2 --------  +// -------- ADC_CDR3 : (ADC Offset: 0x3c) ADC Channel Data Register 3 --------  +// -------- ADC_CDR4 : (ADC Offset: 0x40) ADC Channel Data Register 4 --------  +// -------- ADC_CDR5 : (ADC Offset: 0x44) ADC Channel Data Register 5 --------  +// -------- ADC_CDR6 : (ADC Offset: 0x48) ADC Channel Data Register 6 --------  +// -------- ADC_CDR7 : (ADC Offset: 0x4c) ADC Channel Data Register 7 --------  + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Synchronous Serial Controller Interface +// ***************************************************************************** +typedef struct _AT91S_SSC +{ +  AT91_REG SSC_CR;		// Control Register +  AT91_REG SSC_CMR;		// Clock Mode Register +  AT91_REG Reserved0[2];	//  +  AT91_REG SSC_RCMR;		// Receive Clock ModeRegister +  AT91_REG SSC_RFMR;		// Receive Frame Mode Register +  AT91_REG SSC_TCMR;		// Transmit Clock Mode Register +  AT91_REG SSC_TFMR;		// Transmit Frame Mode Register +  AT91_REG SSC_RHR;		// Receive Holding Register +  AT91_REG SSC_THR;		// Transmit Holding Register +  AT91_REG Reserved1[2];	//  +  AT91_REG SSC_RSHR;		// Receive Sync Holding Register +  AT91_REG SSC_TSHR;		// Transmit Sync Holding Register +  AT91_REG SSC_RC0R;		// Receive Compare 0 Register +  AT91_REG SSC_RC1R;		// Receive Compare 1 Register +  AT91_REG SSC_SR;		// Status Register +  AT91_REG SSC_IER;		// Interrupt Enable Register +  AT91_REG SSC_IDR;		// Interrupt Disable Register +  AT91_REG SSC_IMR;		// Interrupt Mask Register +  AT91_REG Reserved3[44];	//  +  AT91_REG SSC_RPR;		// Receive Pointer Register +  AT91_REG SSC_RCR;		// Receive Counter Register +  AT91_REG SSC_TPR;		// Transmit Pointer Register +  AT91_REG SSC_TCR;		// Transmit Counter Register +  AT91_REG SSC_RNPR;		// Receive Next Pointer Register +  AT91_REG SSC_RNCR;		// Receive Next Counter Register +  AT91_REG SSC_TNPR;		// Transmit Next Pointer Register +  AT91_REG SSC_TNCR;		// Transmit Next Counter Register +  AT91_REG SSC_PTCR;		// PDC Transfer Control Register +  AT91_REG SSC_PTSR;		// PDC Transfer Status Register +} AT91S_SSC, *AT91PS_SSC; + +// -------- SSC_CR : (SSC Offset: 0x0) SSC Control Register --------  +#define AT91C_SSC_RXEN        ((unsigned int) 0x1 <<  0)	// (SSC) Receive Enable +#define AT91C_SSC_RXDIS       ((unsigned int) 0x1 <<  1)	// (SSC) Receive Disable +#define AT91C_SSC_TXEN        ((unsigned int) 0x1 <<  8)	// (SSC) Transmit Enable +#define AT91C_SSC_TXDIS       ((unsigned int) 0x1 <<  9)	// (SSC) Transmit Disable +#define AT91C_SSC_SWRST       ((unsigned int) 0x1 << 15)	// (SSC) Software Reset +// -------- SSC_RCMR : (SSC Offset: 0x10) SSC Receive Clock Mode Register --------  +#define AT91C_SSC_CKS         ((unsigned int) 0x3 <<  0)	// (SSC) Receive/Transmit Clock Selection +#define 	AT91C_SSC_CKS_DIV                  ((unsigned int) 0x0)	// (SSC) Divided Clock +#define 	AT91C_SSC_CKS_TK                   ((unsigned int) 0x1)	// (SSC) TK Clock signal +#define 	AT91C_SSC_CKS_RK                   ((unsigned int) 0x2)	// (SSC) RK pin +#define AT91C_SSC_CKO         ((unsigned int) 0x7 <<  2)	// (SSC) Receive/Transmit Clock Output Mode Selection +#define 	AT91C_SSC_CKO_NONE                 ((unsigned int) 0x0 <<  2)	// (SSC) Receive/Transmit Clock Output Mode: None RK pin: Input-only +#define 	AT91C_SSC_CKO_CONTINOUS            ((unsigned int) 0x1 <<  2)	// (SSC) Continuous Receive/Transmit Clock RK pin: Output +#define 	AT91C_SSC_CKO_DATA_TX              ((unsigned int) 0x2 <<  2)	// (SSC) Receive/Transmit Clock only during data transfers RK pin: Output +#define AT91C_SSC_CKI         ((unsigned int) 0x1 <<  5)	// (SSC) Receive/Transmit Clock Inversion +#define AT91C_SSC_START       ((unsigned int) 0xF <<  8)	// (SSC) Receive/Transmit Start Selection +#define 	AT91C_SSC_START_CONTINOUS            ((unsigned int) 0x0 <<  8)	// (SSC) Continuous, as soon as the receiver is enabled, and immediately after the end of transfer of the previous data. +#define 	AT91C_SSC_START_TX                   ((unsigned int) 0x1 <<  8)	// (SSC) Transmit/Receive start +#define 	AT91C_SSC_START_LOW_RF               ((unsigned int) 0x2 <<  8)	// (SSC) Detection of a low level on RF input +#define 	AT91C_SSC_START_HIGH_RF              ((unsigned int) 0x3 <<  8)	// (SSC) Detection of a high level on RF input +#define 	AT91C_SSC_START_FALL_RF              ((unsigned int) 0x4 <<  8)	// (SSC) Detection of a falling edge on RF input +#define 	AT91C_SSC_START_RISE_RF              ((unsigned int) 0x5 <<  8)	// (SSC) Detection of a rising edge on RF input +#define 	AT91C_SSC_START_LEVEL_RF             ((unsigned int) 0x6 <<  8)	// (SSC) Detection of any level change on RF input +#define 	AT91C_SSC_START_EDGE_RF              ((unsigned int) 0x7 <<  8)	// (SSC) Detection of any edge on RF input +#define 	AT91C_SSC_START_0                    ((unsigned int) 0x8 <<  8)	// (SSC) Compare 0 +#define AT91C_SSC_STTDLY      ((unsigned int) 0xFF << 16)	// (SSC) Receive/Transmit Start Delay +#define AT91C_SSC_PERIOD      ((unsigned int) 0xFF << 24)	// (SSC) Receive/Transmit Period Divider Selection +// -------- SSC_RFMR : (SSC Offset: 0x14) SSC Receive Frame Mode Register --------  +#define AT91C_SSC_DATLEN      ((unsigned int) 0x1F <<  0)	// (SSC) Data Length +#define AT91C_SSC_LOOP        ((unsigned int) 0x1 <<  5)	// (SSC) Loop Mode +#define AT91C_SSC_MSBF        ((unsigned int) 0x1 <<  7)	// (SSC) Most Significant Bit First +#define AT91C_SSC_DATNB       ((unsigned int) 0xF <<  8)	// (SSC) Data Number per Frame +#define AT91C_SSC_FSLEN       ((unsigned int) 0xF << 16)	// (SSC) Receive/Transmit Frame Sync length +#define AT91C_SSC_FSOS        ((unsigned int) 0x7 << 20)	// (SSC) Receive/Transmit Frame Sync Output Selection +#define 	AT91C_SSC_FSOS_NONE                 ((unsigned int) 0x0 << 20)	// (SSC) Selected Receive/Transmit Frame Sync Signal: None RK pin Input-only +#define 	AT91C_SSC_FSOS_NEGATIVE             ((unsigned int) 0x1 << 20)	// (SSC) Selected Receive/Transmit Frame Sync Signal: Negative Pulse +#define 	AT91C_SSC_FSOS_POSITIVE             ((unsigned int) 0x2 << 20)	// (SSC) Selected Receive/Transmit Frame Sync Signal: Positive Pulse +#define 	AT91C_SSC_FSOS_LOW                  ((unsigned int) 0x3 << 20)	// (SSC) Selected Receive/Transmit Frame Sync Signal: Driver Low during data transfer +#define 	AT91C_SSC_FSOS_HIGH                 ((unsigned int) 0x4 << 20)	// (SSC) Selected Receive/Transmit Frame Sync Signal: Driver High during data transfer +#define 	AT91C_SSC_FSOS_TOGGLE               ((unsigned int) 0x5 << 20)	// (SSC) Selected Receive/Transmit Frame Sync Signal: Toggling at each start of data transfer +#define AT91C_SSC_FSEDGE      ((unsigned int) 0x1 << 24)	// (SSC) Frame Sync Edge Detection +// -------- SSC_TCMR : (SSC Offset: 0x18) SSC Transmit Clock Mode Register --------  +// -------- SSC_TFMR : (SSC Offset: 0x1c) SSC Transmit Frame Mode Register --------  +#define AT91C_SSC_DATDEF      ((unsigned int) 0x1 <<  5)	// (SSC) Data Default Value +#define AT91C_SSC_MSBF	      ((unsigned int) 0x1 <<  7)	// (SSC) MSB First +#define AT91C_SSC_FSDEN       ((unsigned int) 0x1 << 23)	// (SSC) Frame Sync Data Enable +// -------- SSC_SR : (SSC Offset: 0x40) SSC Status Register --------  +#define AT91C_SSC_TXRDY       ((unsigned int) 0x1 <<  0)	// (SSC) Transmit Ready +#define AT91C_SSC_TXEMPTY     ((unsigned int) 0x1 <<  1)	// (SSC) Transmit Empty +#define AT91C_SSC_ENDTX       ((unsigned int) 0x1 <<  2)	// (SSC) End Of Transmission +#define AT91C_SSC_TXBUFE      ((unsigned int) 0x1 <<  3)	// (SSC) Transmit Buffer Empty +#define AT91C_SSC_RXRDY       ((unsigned int) 0x1 <<  4)	// (SSC) Receive Ready +#define AT91C_SSC_OVRUN       ((unsigned int) 0x1 <<  5)	// (SSC) Receive Overrun +#define AT91C_SSC_ENDRX       ((unsigned int) 0x1 <<  6)	// (SSC) End of Reception +#define AT91C_SSC_RXBUFF      ((unsigned int) 0x1 <<  7)	// (SSC) Receive Buffer Full +#define AT91C_SSC_CP0         ((unsigned int) 0x1 <<  8)	// (SSC) Compare 0 +#define AT91C_SSC_CP1         ((unsigned int) 0x1 <<  9)	// (SSC) Compare 1 +#define AT91C_SSC_TXSYN       ((unsigned int) 0x1 << 10)	// (SSC) Transmit Sync +#define AT91C_SSC_RXSYN       ((unsigned int) 0x1 << 11)	// (SSC) Receive Sync +#define AT91C_SSC_TXENA       ((unsigned int) 0x1 << 16)	// (SSC) Transmit Enable +#define AT91C_SSC_RXENA       ((unsigned int) 0x1 << 17)	// (SSC) Receive Enable +// -------- SSC_IER : (SSC Offset: 0x44) SSC Interrupt Enable Register --------  +// -------- SSC_IDR : (SSC Offset: 0x48) SSC Interrupt Disable Register --------  +// -------- SSC_IMR : (SSC Offset: 0x4c) SSC Interrupt Mask Register --------  + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Usart +// ***************************************************************************** +typedef struct _AT91S_USART +{ +  AT91_REG US_CR;		// Control Register +  AT91_REG US_MR;		// Mode Register +  AT91_REG US_IER;		// Interrupt Enable Register +  AT91_REG US_IDR;		// Interrupt Disable Register +  AT91_REG US_IMR;		// Interrupt Mask Register +  AT91_REG US_CSR;		// Channel Status Register +  AT91_REG US_RHR;		// Receiver Holding Register +  AT91_REG US_THR;		// Transmitter Holding Register +  AT91_REG US_BRGR;		// Baud Rate Generator Register +  AT91_REG US_RTOR;		// Receiver Time-out Register +  AT91_REG US_TTGR;		// Transmitter Time-guard Register +  AT91_REG Reserved0[5];	//  +  AT91_REG US_FIDI;		// FI_DI_Ratio Register +  AT91_REG US_NER;		// Nb Errors Register +  AT91_REG Reserved1[1];	//  +  AT91_REG US_IF;		// IRDA_FILTER Register +  AT91_REG Reserved2[44];	//  +  AT91_REG US_RPR;		// Receive Pointer Register +  AT91_REG US_RCR;		// Receive Counter Register +  AT91_REG US_TPR;		// Transmit Pointer Register +  AT91_REG US_TCR;		// Transmit Counter Register +  AT91_REG US_RNPR;		// Receive Next Pointer Register +  AT91_REG US_RNCR;		// Receive Next Counter Register +  AT91_REG US_TNPR;		// Transmit Next Pointer Register +  AT91_REG US_TNCR;		// Transmit Next Counter Register +  AT91_REG US_PTCR;		// PDC Transfer Control Register +  AT91_REG US_PTSR;		// PDC Transfer Status Register +} AT91S_USART, *AT91PS_USART; + +// -------- US_CR : (USART Offset: 0x0) Debug Unit Control Register --------  +#define AT91C_US_STTBRK       ((unsigned int) 0x1 <<  9)	// (USART) Start Break +#define AT91C_US_STPBRK       ((unsigned int) 0x1 << 10)	// (USART) Stop Break +#define AT91C_US_STTTO        ((unsigned int) 0x1 << 11)	// (USART) Start Time-out +#define AT91C_US_SENDA        ((unsigned int) 0x1 << 12)	// (USART) Send Address +#define AT91C_US_RSTIT        ((unsigned int) 0x1 << 13)	// (USART) Reset Iterations +#define AT91C_US_RSTNACK      ((unsigned int) 0x1 << 14)	// (USART) Reset Non Acknowledge +#define AT91C_US_RETTO        ((unsigned int) 0x1 << 15)	// (USART) Rearm Time-out +#define AT91C_US_DTREN        ((unsigned int) 0x1 << 16)	// (USART) Data Terminal ready Enable +#define AT91C_US_DTRDIS       ((unsigned int) 0x1 << 17)	// (USART) Data Terminal ready Disable +#define AT91C_US_RTSEN        ((unsigned int) 0x1 << 18)	// (USART) Request to Send enable +#define AT91C_US_RTSDIS       ((unsigned int) 0x1 << 19)	// (USART) Request to Send Disable +// -------- US_MR : (USART Offset: 0x4) Debug Unit Mode Register --------  +#define AT91C_US_USMODE       ((unsigned int) 0xF <<  0)	// (USART) Usart mode +#define 	AT91C_US_USMODE_NORMAL               ((unsigned int) 0x0)	// (USART) Normal +#define 	AT91C_US_USMODE_RS485                ((unsigned int) 0x1)	// (USART) RS485 +#define 	AT91C_US_USMODE_HWHSH                ((unsigned int) 0x2)	// (USART) Hardware Handshaking +#define 	AT91C_US_USMODE_MODEM                ((unsigned int) 0x3)	// (USART) Modem +#define 	AT91C_US_USMODE_ISO7816_0            ((unsigned int) 0x4)	// (USART) ISO7816 protocol: T = 0 +#define 	AT91C_US_USMODE_ISO7816_1            ((unsigned int) 0x6)	// (USART) ISO7816 protocol: T = 1 +#define 	AT91C_US_USMODE_IRDA                 ((unsigned int) 0x8)	// (USART) IrDA +#define 	AT91C_US_USMODE_SWHSH                ((unsigned int) 0xC)	// (USART) Software Handshaking +#define AT91C_US_CLKS         ((unsigned int) 0x3 <<  4)	// (USART) Clock Selection (Baud Rate generator Input Clock +#define 	AT91C_US_CLKS_CLOCK                ((unsigned int) 0x0 <<  4)	// (USART) Clock +#define 	AT91C_US_CLKS_FDIV1                ((unsigned int) 0x1 <<  4)	// (USART) fdiv1 +#define 	AT91C_US_CLKS_SLOW                 ((unsigned int) 0x2 <<  4)	// (USART) slow_clock (ARM) +#define 	AT91C_US_CLKS_EXT                  ((unsigned int) 0x3 <<  4)	// (USART) External (SCK) +#define AT91C_US_CHRL         ((unsigned int) 0x3 <<  6)	// (USART) Clock Selection (Baud Rate generator Input Clock +#define 	AT91C_US_CHRL_5_BITS               ((unsigned int) 0x0 <<  6)	// (USART) Character Length: 5 bits +#define 	AT91C_US_CHRL_6_BITS               ((unsigned int) 0x1 <<  6)	// (USART) Character Length: 6 bits +#define 	AT91C_US_CHRL_7_BITS               ((unsigned int) 0x2 <<  6)	// (USART) Character Length: 7 bits +#define 	AT91C_US_CHRL_8_BITS               ((unsigned int) 0x3 <<  6)	// (USART) Character Length: 8 bits +#define AT91C_US_SYNC         ((unsigned int) 0x1 <<  8)	// (USART) Synchronous Mode Select +#define AT91C_US_NBSTOP       ((unsigned int) 0x3 << 12)	// (USART) Number of Stop bits +#define 	AT91C_US_NBSTOP_1_BIT                ((unsigned int) 0x0 << 12)	// (USART) 1 stop bit +#define 	AT91C_US_NBSTOP_15_BIT               ((unsigned int) 0x1 << 12)	// (USART) Asynchronous (SYNC=0) 2 stop bits Synchronous (SYNC=1) 2 stop bits +#define 	AT91C_US_NBSTOP_2_BIT                ((unsigned int) 0x2 << 12)	// (USART) 2 stop bits +#define AT91C_US_MSBF         ((unsigned int) 0x1 << 16)	// (USART) Bit Order +#define AT91C_US_MODE9        ((unsigned int) 0x1 << 17)	// (USART) 9-bit Character length +#define AT91C_US_CKLO         ((unsigned int) 0x1 << 18)	// (USART) Clock Output Select +#define AT91C_US_OVER         ((unsigned int) 0x1 << 19)	// (USART) Over Sampling Mode +#define AT91C_US_INACK        ((unsigned int) 0x1 << 20)	// (USART) Inhibit Non Acknowledge +#define AT91C_US_DSNACK       ((unsigned int) 0x1 << 21)	// (USART) Disable Successive NACK +#define AT91C_US_MAX_ITER     ((unsigned int) 0x1 << 24)	// (USART) Number of Repetitions +#define AT91C_US_FILTER       ((unsigned int) 0x1 << 28)	// (USART) Receive Line Filter +// -------- US_IER : (USART Offset: 0x8) Debug Unit Interrupt Enable Register --------  +#define AT91C_US_RXBRK        ((unsigned int) 0x1 <<  2)	// (USART) Break Received/End of Break +#define AT91C_US_TIMEOUT      ((unsigned int) 0x1 <<  8)	// (USART) Receiver Time-out +#define AT91C_US_ITERATION    ((unsigned int) 0x1 << 10)	// (USART) Max number of Repetitions Reached +#define AT91C_US_NACK         ((unsigned int) 0x1 << 13)	// (USART) Non Acknowledge +#define AT91C_US_RIIC         ((unsigned int) 0x1 << 16)	// (USART) Ring INdicator Input Change Flag +#define AT91C_US_DSRIC        ((unsigned int) 0x1 << 17)	// (USART) Data Set Ready Input Change Flag +#define AT91C_US_DCDIC        ((unsigned int) 0x1 << 18)	// (USART) Data Carrier Flag +#define AT91C_US_CTSIC        ((unsigned int) 0x1 << 19)	// (USART) Clear To Send Input Change Flag +// -------- US_IDR : (USART Offset: 0xc) Debug Unit Interrupt Disable Register --------  +// -------- US_IMR : (USART Offset: 0x10) Debug Unit Interrupt Mask Register --------  +// -------- US_CSR : (USART Offset: 0x14) Debug Unit Channel Status Register --------  +#define AT91C_US_RI           ((unsigned int) 0x1 << 20)	// (USART) Image of RI Input +#define AT91C_US_DSR          ((unsigned int) 0x1 << 21)	// (USART) Image of DSR Input +#define AT91C_US_DCD          ((unsigned int) 0x1 << 22)	// (USART) Image of DCD Input +#define AT91C_US_CTS          ((unsigned int) 0x1 << 23)	// (USART) Image of CTS Input + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Two-wire Interface +// ***************************************************************************** +typedef struct _AT91S_TWI +{ +  AT91_REG TWI_CR;		// Control Register +  AT91_REG TWI_MMR;		// Master Mode Register +  AT91_REG Reserved0[1];	//  +  AT91_REG TWI_IADR;		// Internal Address Register +  AT91_REG TWI_CWGR;		// Clock Waveform Generator Register +  AT91_REG Reserved1[3];	//  +  AT91_REG TWI_SR;		// Status Register +  AT91_REG TWI_IER;		// Interrupt Enable Register +  AT91_REG TWI_IDR;		// Interrupt Disable Register +  AT91_REG TWI_IMR;		// Interrupt Mask Register +  AT91_REG TWI_RHR;		// Receive Holding Register +  AT91_REG TWI_THR;		// Transmit Holding Register +} AT91S_TWI, *AT91PS_TWI; + +// -------- TWI_CR : (TWI Offset: 0x0) TWI Control Register --------  +#define AT91C_TWI_START       ((unsigned int) 0x1 <<  0)	// (TWI) Send a START Condition +#define AT91C_TWI_STOP        ((unsigned int) 0x1 <<  1)	// (TWI) Send a STOP Condition +#define AT91C_TWI_MSEN        ((unsigned int) 0x1 <<  2)	// (TWI) TWI Master Transfer Enabled +#define AT91C_TWI_MSDIS       ((unsigned int) 0x1 <<  3)	// (TWI) TWI Master Transfer Disabled +#define AT91C_TWI_SWRST       ((unsigned int) 0x1 <<  7)	// (TWI) Software Reset +// -------- TWI_MMR : (TWI Offset: 0x4) TWI Master Mode Register --------  +#define AT91C_TWI_IADRSZ      ((unsigned int) 0x3 <<  8)	// (TWI) Internal Device Address Size +#define 	AT91C_TWI_IADRSZ_NO                   ((unsigned int) 0x0 <<  8)	// (TWI) No internal device address +#define 	AT91C_TWI_IADRSZ_1_BYTE               ((unsigned int) 0x1 <<  8)	// (TWI) One-byte internal device address +#define 	AT91C_TWI_IADRSZ_2_BYTE               ((unsigned int) 0x2 <<  8)	// (TWI) Two-byte internal device address +#define 	AT91C_TWI_IADRSZ_3_BYTE               ((unsigned int) 0x3 <<  8)	// (TWI) Three-byte internal device address +#define AT91C_TWI_MREAD       ((unsigned int) 0x1 << 12)	// (TWI) Master Read Direction +#define AT91C_TWI_DADR        ((unsigned int) 0x7F << 16)	// (TWI) Device Address +// -------- TWI_CWGR : (TWI Offset: 0x10) TWI Clock Waveform Generator Register --------  +#define AT91C_TWI_CLDIV       ((unsigned int) 0xFF <<  0)	// (TWI) Clock Low Divider +#define AT91C_TWI_CHDIV       ((unsigned int) 0xFF <<  8)	// (TWI) Clock High Divider +#define AT91C_TWI_CKDIV       ((unsigned int) 0x7 << 16)	// (TWI) Clock Divider +// -------- TWI_SR : (TWI Offset: 0x20) TWI Status Register --------  +#define AT91C_TWI_TXCOMP      ((unsigned int) 0x1 <<  0)	// (TWI) Transmission Completed +#define AT91C_TWI_RXRDY       ((unsigned int) 0x1 <<  1)	// (TWI) Receive holding register ReaDY +#define AT91C_TWI_TXRDY       ((unsigned int) 0x1 <<  2)	// (TWI) Transmit holding register ReaDY +#define AT91C_TWI_OVRE        ((unsigned int) 0x1 <<  6)	// (TWI) Overrun Error +#define AT91C_TWI_UNRE        ((unsigned int) 0x1 <<  7)	// (TWI) Underrun Error +#define AT91C_TWI_NACK        ((unsigned int) 0x1 <<  8)	// (TWI) Not Acknowledged +// -------- TWI_IER : (TWI Offset: 0x24) TWI Interrupt Enable Register --------  +// -------- TWI_IDR : (TWI Offset: 0x28) TWI Interrupt Disable Register --------  +// -------- TWI_IMR : (TWI Offset: 0x2c) TWI Interrupt Mask Register --------  + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Timer Counter Channel Interface +// ***************************************************************************** +typedef struct _AT91S_TC +{ +  AT91_REG TC_CCR;		// Channel Control Register +  AT91_REG TC_CMR;		// Channel Mode Register (Capture Mode / Waveform Mode) +  AT91_REG Reserved0[2];	//  +  AT91_REG TC_CV;		// Counter Value +  AT91_REG TC_RA;		// Register A +  AT91_REG TC_RB;		// Register B +  AT91_REG TC_RC;		// Register C +  AT91_REG TC_SR;		// Status Register +  AT91_REG TC_IER;		// Interrupt Enable Register +  AT91_REG TC_IDR;		// Interrupt Disable Register +  AT91_REG TC_IMR;		// Interrupt Mask Register +} AT91S_TC, *AT91PS_TC; + +// -------- TC_CCR : (TC Offset: 0x0) TC Channel Control Register --------  +#define AT91C_TC_CLKEN        ((unsigned int) 0x1 <<  0)	// (TC) Counter Clock Enable Command +#define AT91C_TC_CLKDIS       ((unsigned int) 0x1 <<  1)	// (TC) Counter Clock Disable Command +#define AT91C_TC_SWTRG        ((unsigned int) 0x1 <<  2)	// (TC) Software Trigger Command +// -------- TC_CMR : (TC Offset: 0x4) TC Channel Mode Register: Capture Mode / Waveform Mode --------  +#define AT91C_TC_CLKS         ((unsigned int) 0x7 <<  0)	// (TC) Clock Selection +#define 	AT91C_TC_CLKS_TIMER_DIV1_CLOCK     ((unsigned int) 0x0)	// (TC) Clock selected: TIMER_DIV1_CLOCK +#define 	AT91C_TC_CLKS_TIMER_DIV2_CLOCK     ((unsigned int) 0x1)	// (TC) Clock selected: TIMER_DIV2_CLOCK +#define 	AT91C_TC_CLKS_TIMER_DIV3_CLOCK     ((unsigned int) 0x2)	// (TC) Clock selected: TIMER_DIV3_CLOCK +#define 	AT91C_TC_CLKS_TIMER_DIV4_CLOCK     ((unsigned int) 0x3)	// (TC) Clock selected: TIMER_DIV4_CLOCK +#define 	AT91C_TC_CLKS_TIMER_DIV5_CLOCK     ((unsigned int) 0x4)	// (TC) Clock selected: TIMER_DIV5_CLOCK +#define 	AT91C_TC_CLKS_XC0                  ((unsigned int) 0x5)	// (TC) Clock selected: XC0 +#define 	AT91C_TC_CLKS_XC1                  ((unsigned int) 0x6)	// (TC) Clock selected: XC1 +#define 	AT91C_TC_CLKS_XC2                  ((unsigned int) 0x7)	// (TC) Clock selected: XC2 +#define AT91C_TC_CLKI         ((unsigned int) 0x1 <<  3)	// (TC) Clock Invert +#define AT91C_TC_BURST        ((unsigned int) 0x3 <<  4)	// (TC) Burst Signal Selection +#define 	AT91C_TC_BURST_NONE                 ((unsigned int) 0x0 <<  4)	// (TC) The clock is not gated by an external signal +#define 	AT91C_TC_BURST_XC0                  ((unsigned int) 0x1 <<  4)	// (TC) XC0 is ANDed with the selected clock +#define 	AT91C_TC_BURST_XC1                  ((unsigned int) 0x2 <<  4)	// (TC) XC1 is ANDed with the selected clock +#define 	AT91C_TC_BURST_XC2                  ((unsigned int) 0x3 <<  4)	// (TC) XC2 is ANDed with the selected clock +#define AT91C_TC_CPCSTOP      ((unsigned int) 0x1 <<  6)	// (TC) Counter Clock Stopped with RC Compare +#define AT91C_TC_LDBSTOP      ((unsigned int) 0x1 <<  6)	// (TC) Counter Clock Stopped with RB Loading +#define AT91C_TC_CPCDIS       ((unsigned int) 0x1 <<  7)	// (TC) Counter Clock Disable with RC Compare +#define AT91C_TC_LDBDIS       ((unsigned int) 0x1 <<  7)	// (TC) Counter Clock Disabled with RB Loading +#define AT91C_TC_ETRGEDG      ((unsigned int) 0x3 <<  8)	// (TC) External Trigger Edge Selection +#define 	AT91C_TC_ETRGEDG_NONE                 ((unsigned int) 0x0 <<  8)	// (TC) Edge: None +#define 	AT91C_TC_ETRGEDG_RISING               ((unsigned int) 0x1 <<  8)	// (TC) Edge: rising edge +#define 	AT91C_TC_ETRGEDG_FALLING              ((unsigned int) 0x2 <<  8)	// (TC) Edge: falling edge +#define 	AT91C_TC_ETRGEDG_BOTH                 ((unsigned int) 0x3 <<  8)	// (TC) Edge: each edge +#define AT91C_TC_EEVTEDG      ((unsigned int) 0x3 <<  8)	// (TC) External Event Edge Selection +#define 	AT91C_TC_EEVTEDG_NONE                 ((unsigned int) 0x0 <<  8)	// (TC) Edge: None +#define 	AT91C_TC_EEVTEDG_RISING               ((unsigned int) 0x1 <<  8)	// (TC) Edge: rising edge +#define 	AT91C_TC_EEVTEDG_FALLING              ((unsigned int) 0x2 <<  8)	// (TC) Edge: falling edge +#define 	AT91C_TC_EEVTEDG_BOTH                 ((unsigned int) 0x3 <<  8)	// (TC) Edge: each edge +#define AT91C_TC_EEVT         ((unsigned int) 0x3 << 10)	// (TC) External Event  Selection +#define 	AT91C_TC_EEVT_TIOB                 ((unsigned int) 0x0 << 10)	// (TC) Signal selected as external event: TIOB TIOB direction: input +#define 	AT91C_TC_EEVT_XC0                  ((unsigned int) 0x1 << 10)	// (TC) Signal selected as external event: XC0 TIOB direction: output +#define 	AT91C_TC_EEVT_XC1                  ((unsigned int) 0x2 << 10)	// (TC) Signal selected as external event: XC1 TIOB direction: output +#define 	AT91C_TC_EEVT_XC2                  ((unsigned int) 0x3 << 10)	// (TC) Signal selected as external event: XC2 TIOB direction: output +#define AT91C_TC_ABETRG       ((unsigned int) 0x1 << 10)	// (TC) TIOA or TIOB External Trigger Selection +#define AT91C_TC_ENETRG       ((unsigned int) 0x1 << 12)	// (TC) External Event Trigger enable +#define AT91C_TC_WAVESEL      ((unsigned int) 0x3 << 13)	// (TC) Waveform  Selection +#define 	AT91C_TC_WAVESEL_UP                   ((unsigned int) 0x0 << 13)	// (TC) UP mode without atomatic trigger on RC Compare +#define 	AT91C_TC_WAVESEL_UPDOWN               ((unsigned int) 0x1 << 13)	// (TC) UPDOWN mode without automatic trigger on RC Compare +#define 	AT91C_TC_WAVESEL_UP_AUTO              ((unsigned int) 0x2 << 13)	// (TC) UP mode with automatic trigger on RC Compare +#define 	AT91C_TC_WAVESEL_UPDOWN_AUTO          ((unsigned int) 0x3 << 13)	// (TC) UPDOWN mode with automatic trigger on RC Compare +#define AT91C_TC_CPCTRG       ((unsigned int) 0x1 << 14)	// (TC) RC Compare Trigger Enable +#define AT91C_TC_WAVE         ((unsigned int) 0x1 << 15)	// (TC) +#define AT91C_TC_ACPA         ((unsigned int) 0x3 << 16)	// (TC) RA Compare Effect on TIOA +#define 	AT91C_TC_ACPA_NONE                 ((unsigned int) 0x0 << 16)	// (TC) Effect: none +#define 	AT91C_TC_ACPA_SET                  ((unsigned int) 0x1 << 16)	// (TC) Effect: set +#define 	AT91C_TC_ACPA_CLEAR                ((unsigned int) 0x2 << 16)	// (TC) Effect: clear +#define 	AT91C_TC_ACPA_TOGGLE               ((unsigned int) 0x3 << 16)	// (TC) Effect: toggle +#define AT91C_TC_LDRA         ((unsigned int) 0x3 << 16)	// (TC) RA Loading Selection +#define 	AT91C_TC_LDRA_NONE                 ((unsigned int) 0x0 << 16)	// (TC) Edge: None +#define 	AT91C_TC_LDRA_RISING               ((unsigned int) 0x1 << 16)	// (TC) Edge: rising edge of TIOA +#define 	AT91C_TC_LDRA_FALLING              ((unsigned int) 0x2 << 16)	// (TC) Edge: falling edge of TIOA +#define 	AT91C_TC_LDRA_BOTH                 ((unsigned int) 0x3 << 16)	// (TC) Edge: each edge of TIOA +#define AT91C_TC_ACPC         ((unsigned int) 0x3 << 18)	// (TC) RC Compare Effect on TIOA +#define 	AT91C_TC_ACPC_NONE                 ((unsigned int) 0x0 << 18)	// (TC) Effect: none +#define 	AT91C_TC_ACPC_SET                  ((unsigned int) 0x1 << 18)	// (TC) Effect: set +#define 	AT91C_TC_ACPC_CLEAR                ((unsigned int) 0x2 << 18)	// (TC) Effect: clear +#define 	AT91C_TC_ACPC_TOGGLE               ((unsigned int) 0x3 << 18)	// (TC) Effect: toggle +#define AT91C_TC_LDRB         ((unsigned int) 0x3 << 18)	// (TC) RB Loading Selection +#define 	AT91C_TC_LDRB_NONE                 ((unsigned int) 0x0 << 18)	// (TC) Edge: None +#define 	AT91C_TC_LDRB_RISING               ((unsigned int) 0x1 << 18)	// (TC) Edge: rising edge of TIOA +#define 	AT91C_TC_LDRB_FALLING              ((unsigned int) 0x2 << 18)	// (TC) Edge: falling edge of TIOA +#define 	AT91C_TC_LDRB_BOTH                 ((unsigned int) 0x3 << 18)	// (TC) Edge: each edge of TIOA +#define AT91C_TC_AEEVT        ((unsigned int) 0x3 << 20)	// (TC) External Event Effect on TIOA +#define 	AT91C_TC_AEEVT_NONE                 ((unsigned int) 0x0 << 20)	// (TC) Effect: none +#define 	AT91C_TC_AEEVT_SET                  ((unsigned int) 0x1 << 20)	// (TC) Effect: set +#define 	AT91C_TC_AEEVT_CLEAR                ((unsigned int) 0x2 << 20)	// (TC) Effect: clear +#define 	AT91C_TC_AEEVT_TOGGLE               ((unsigned int) 0x3 << 20)	// (TC) Effect: toggle +#define AT91C_TC_ASWTRG       ((unsigned int) 0x3 << 22)	// (TC) Software Trigger Effect on TIOA +#define 	AT91C_TC_ASWTRG_NONE                 ((unsigned int) 0x0 << 22)	// (TC) Effect: none +#define 	AT91C_TC_ASWTRG_SET                  ((unsigned int) 0x1 << 22)	// (TC) Effect: set +#define 	AT91C_TC_ASWTRG_CLEAR                ((unsigned int) 0x2 << 22)	// (TC) Effect: clear +#define 	AT91C_TC_ASWTRG_TOGGLE               ((unsigned int) 0x3 << 22)	// (TC) Effect: toggle +#define AT91C_TC_BCPB         ((unsigned int) 0x3 << 24)	// (TC) RB Compare Effect on TIOB +#define 	AT91C_TC_BCPB_NONE                 ((unsigned int) 0x0 << 24)	// (TC) Effect: none +#define 	AT91C_TC_BCPB_SET                  ((unsigned int) 0x1 << 24)	// (TC) Effect: set +#define 	AT91C_TC_BCPB_CLEAR                ((unsigned int) 0x2 << 24)	// (TC) Effect: clear +#define 	AT91C_TC_BCPB_TOGGLE               ((unsigned int) 0x3 << 24)	// (TC) Effect: toggle +#define AT91C_TC_BCPC         ((unsigned int) 0x3 << 26)	// (TC) RC Compare Effect on TIOB +#define 	AT91C_TC_BCPC_NONE                 ((unsigned int) 0x0 << 26)	// (TC) Effect: none +#define 	AT91C_TC_BCPC_SET                  ((unsigned int) 0x1 << 26)	// (TC) Effect: set +#define 	AT91C_TC_BCPC_CLEAR                ((unsigned int) 0x2 << 26)	// (TC) Effect: clear +#define 	AT91C_TC_BCPC_TOGGLE               ((unsigned int) 0x3 << 26)	// (TC) Effect: toggle +#define AT91C_TC_BEEVT        ((unsigned int) 0x3 << 28)	// (TC) External Event Effect on TIOB +#define 	AT91C_TC_BEEVT_NONE                 ((unsigned int) 0x0 << 28)	// (TC) Effect: none +#define 	AT91C_TC_BEEVT_SET                  ((unsigned int) 0x1 << 28)	// (TC) Effect: set +#define 	AT91C_TC_BEEVT_CLEAR                ((unsigned int) 0x2 << 28)	// (TC) Effect: clear +#define 	AT91C_TC_BEEVT_TOGGLE               ((unsigned int) 0x3 << 28)	// (TC) Effect: toggle +#define AT91C_TC_BSWTRG       ((unsigned int) 0x3 << 30)	// (TC) Software Trigger Effect on TIOB +#define 	AT91C_TC_BSWTRG_NONE                 ((unsigned int) 0x0 << 30)	// (TC) Effect: none +#define 	AT91C_TC_BSWTRG_SET                  ((unsigned int) 0x1 << 30)	// (TC) Effect: set +#define 	AT91C_TC_BSWTRG_CLEAR                ((unsigned int) 0x2 << 30)	// (TC) Effect: clear +#define 	AT91C_TC_BSWTRG_TOGGLE               ((unsigned int) 0x3 << 30)	// (TC) Effect: toggle +// -------- TC_SR : (TC Offset: 0x20) TC Channel Status Register --------  +#define AT91C_TC_COVFS        ((unsigned int) 0x1 <<  0)	// (TC) Counter Overflow +#define AT91C_TC_LOVRS        ((unsigned int) 0x1 <<  1)	// (TC) Load Overrun +#define AT91C_TC_CPAS         ((unsigned int) 0x1 <<  2)	// (TC) RA Compare +#define AT91C_TC_CPBS         ((unsigned int) 0x1 <<  3)	// (TC) RB Compare +#define AT91C_TC_CPCS         ((unsigned int) 0x1 <<  4)	// (TC) RC Compare +#define AT91C_TC_LDRAS        ((unsigned int) 0x1 <<  5)	// (TC) RA Loading +#define AT91C_TC_LDRBS        ((unsigned int) 0x1 <<  6)	// (TC) RB Loading +#define AT91C_TC_ETRGS        ((unsigned int) 0x1 <<  7)	// (TC) External Trigger +#define AT91C_TC_CLKSTA       ((unsigned int) 0x1 << 16)	// (TC) Clock Enabling +#define AT91C_TC_MTIOA        ((unsigned int) 0x1 << 17)	// (TC) TIOA Mirror +#define AT91C_TC_MTIOB        ((unsigned int) 0x1 << 18)	// (TC) TIOA Mirror +// -------- TC_IER : (TC Offset: 0x24) TC Channel Interrupt Enable Register --------  +// -------- TC_IDR : (TC Offset: 0x28) TC Channel Interrupt Disable Register --------  +// -------- TC_IMR : (TC Offset: 0x2c) TC Channel Interrupt Mask Register --------  + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Timer Counter Interface +// ***************************************************************************** +typedef struct _AT91S_TCB +{ +  AT91S_TC TCB_TC0;		// TC Channel 0 +  AT91_REG Reserved0[4];	//  +  AT91S_TC TCB_TC1;		// TC Channel 1 +  AT91_REG Reserved1[4];	//  +  AT91S_TC TCB_TC2;		// TC Channel 2 +  AT91_REG Reserved2[4];	//  +  AT91_REG TCB_BCR;		// TC Block Control Register +  AT91_REG TCB_BMR;		// TC Block Mode Register +} AT91S_TCB, *AT91PS_TCB; + +// -------- TCB_BCR : (TCB Offset: 0xc0) TC Block Control Register --------  +#define AT91C_TCB_SYNC        ((unsigned int) 0x1 <<  0)	// (TCB) Synchro Command +// -------- TCB_BMR : (TCB Offset: 0xc4) TC Block Mode Register --------  +#define AT91C_TCB_TC0XC0S     ((unsigned int) 0x3 <<  0)	// (TCB) External Clock Signal 0 Selection +#define 	AT91C_TCB_TC0XC0S_TCLK0                ((unsigned int) 0x0)	// (TCB) TCLK0 connected to XC0 +#define 	AT91C_TCB_TC0XC0S_NONE                 ((unsigned int) 0x1)	// (TCB) None signal connected to XC0 +#define 	AT91C_TCB_TC0XC0S_TIOA1                ((unsigned int) 0x2)	// (TCB) TIOA1 connected to XC0 +#define 	AT91C_TCB_TC0XC0S_TIOA2                ((unsigned int) 0x3)	// (TCB) TIOA2 connected to XC0 +#define AT91C_TCB_TC1XC1S     ((unsigned int) 0x3 <<  2)	// (TCB) External Clock Signal 1 Selection +#define 	AT91C_TCB_TC1XC1S_TCLK1                ((unsigned int) 0x0 <<  2)	// (TCB) TCLK1 connected to XC1 +#define 	AT91C_TCB_TC1XC1S_NONE                 ((unsigned int) 0x1 <<  2)	// (TCB) None signal connected to XC1 +#define 	AT91C_TCB_TC1XC1S_TIOA0                ((unsigned int) 0x2 <<  2)	// (TCB) TIOA0 connected to XC1 +#define 	AT91C_TCB_TC1XC1S_TIOA2                ((unsigned int) 0x3 <<  2)	// (TCB) TIOA2 connected to XC1 +#define AT91C_TCB_TC2XC2S     ((unsigned int) 0x3 <<  4)	// (TCB) External Clock Signal 2 Selection +#define 	AT91C_TCB_TC2XC2S_TCLK2                ((unsigned int) 0x0 <<  4)	// (TCB) TCLK2 connected to XC2 +#define 	AT91C_TCB_TC2XC2S_NONE                 ((unsigned int) 0x1 <<  4)	// (TCB) None signal connected to XC2 +#define 	AT91C_TCB_TC2XC2S_TIOA0                ((unsigned int) 0x2 <<  4)	// (TCB) TIOA0 connected to XC2 +#define 	AT91C_TCB_TC2XC2S_TIOA1                ((unsigned int) 0x3 <<  4)	// (TCB) TIOA2 connected to XC2 + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR PWMC Channel Interface +// ***************************************************************************** +typedef struct _AT91S_PWMC_CH +{ +  AT91_REG PWMC_CMR;		// Channel Mode Register +  AT91_REG PWMC_CDTYR;		// Channel Duty Cycle Register +  AT91_REG PWMC_CPRDR;		// Channel Period Register +  AT91_REG PWMC_CCNTR;		// Channel Counter Register +  AT91_REG PWMC_CUPDR;		// Channel Update Register +  AT91_REG PWMC_Reserved[3];	// Reserved +} AT91S_PWMC_CH, *AT91PS_PWMC_CH; + +// -------- PWMC_CMR : (PWMC_CH Offset: 0x0) PWMC Channel Mode Register --------  +#define AT91C_PWMC_CPRE       ((unsigned int) 0xF <<  0)	// (PWMC_CH) Channel Pre-scaler : PWMC_CLKx +#define 	AT91C_PWMC_CPRE_MCK                  ((unsigned int) 0x0)	// (PWMC_CH) +#define 	AT91C_PWMC_CPRE_MCKA                 ((unsigned int) 0xB)	// (PWMC_CH) +#define 	AT91C_PWMC_CPRE_MCKB                 ((unsigned int) 0xC)	// (PWMC_CH) +#define AT91C_PWMC_CALG       ((unsigned int) 0x1 <<  8)	// (PWMC_CH) Channel Alignment +#define AT91C_PWMC_CPOL       ((unsigned int) 0x1 <<  9)	// (PWMC_CH) Channel Polarity +#define AT91C_PWMC_CPD        ((unsigned int) 0x1 << 10)	// (PWMC_CH) Channel Update Period +// -------- PWMC_CDTYR : (PWMC_CH Offset: 0x4) PWMC Channel Duty Cycle Register --------  +#define AT91C_PWMC_CDTY       ((unsigned int) 0x0 <<  0)	// (PWMC_CH) Channel Duty Cycle +// -------- PWMC_CPRDR : (PWMC_CH Offset: 0x8) PWMC Channel Period Register --------  +#define AT91C_PWMC_CPRD       ((unsigned int) 0x0 <<  0)	// (PWMC_CH) Channel Period +// -------- PWMC_CCNTR : (PWMC_CH Offset: 0xc) PWMC Channel Counter Register --------  +#define AT91C_PWMC_CCNT       ((unsigned int) 0x0 <<  0)	// (PWMC_CH) Channel Counter +// -------- PWMC_CUPDR : (PWMC_CH Offset: 0x10) PWMC Channel Update Register --------  +#define AT91C_PWMC_CUPD       ((unsigned int) 0x0 <<  0)	// (PWMC_CH) Channel Update + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR Pulse Width Modulation Controller Interface +// ***************************************************************************** +typedef struct _AT91S_PWMC +{ +  AT91_REG PWMC_MR;		// PWMC Mode Register +  AT91_REG PWMC_ENA;		// PWMC Enable Register +  AT91_REG PWMC_DIS;		// PWMC Disable Register +  AT91_REG PWMC_SR;		// PWMC Status Register +  AT91_REG PWMC_IER;		// PWMC Interrupt Enable Register +  AT91_REG PWMC_IDR;		// PWMC Interrupt Disable Register +  AT91_REG PWMC_IMR;		// PWMC Interrupt Mask Register +  AT91_REG PWMC_ISR;		// PWMC Interrupt Status Register +  AT91_REG Reserved0[55];	//  +  AT91_REG PWMC_VR;		// PWMC Version Register +  AT91_REG Reserved1[64];	//  +  AT91S_PWMC_CH PWMC_CH[4];	// PWMC Channel +} AT91S_PWMC, *AT91PS_PWMC; + +// -------- PWMC_MR : (PWMC Offset: 0x0) PWMC Mode Register --------  +#define AT91C_PWMC_DIVA       ((unsigned int) 0xFF <<  0)	// (PWMC) CLKA divide factor. +#define AT91C_PWMC_PREA       ((unsigned int) 0xF <<  8)	// (PWMC) Divider Input Clock Prescaler A +#define 	AT91C_PWMC_PREA_MCK                  ((unsigned int) 0x0 <<  8)	// (PWMC) +#define AT91C_PWMC_DIVB       ((unsigned int) 0xFF << 16)	// (PWMC) CLKB divide factor. +#define AT91C_PWMC_PREB       ((unsigned int) 0xF << 24)	// (PWMC) Divider Input Clock Prescaler B +#define 	AT91C_PWMC_PREB_MCK                  ((unsigned int) 0x0 << 24)	// (PWMC) +// -------- PWMC_ENA : (PWMC Offset: 0x4) PWMC Enable Register --------  +#define AT91C_PWMC_CHID0      ((unsigned int) 0x1 <<  0)	// (PWMC) Channel ID 0 +#define AT91C_PWMC_CHID1      ((unsigned int) 0x1 <<  1)	// (PWMC) Channel ID 1 +#define AT91C_PWMC_CHID2      ((unsigned int) 0x1 <<  2)	// (PWMC) Channel ID 2 +#define AT91C_PWMC_CHID3      ((unsigned int) 0x1 <<  3)	// (PWMC) Channel ID 3 +// -------- PWMC_DIS : (PWMC Offset: 0x8) PWMC Disable Register --------  +// -------- PWMC_SR : (PWMC Offset: 0xc) PWMC Status Register --------  +// -------- PWMC_IER : (PWMC Offset: 0x10) PWMC Interrupt Enable Register --------  +// -------- PWMC_IDR : (PWMC Offset: 0x14) PWMC Interrupt Disable Register --------  +// -------- PWMC_IMR : (PWMC Offset: 0x18) PWMC Interrupt Mask Register --------  +// -------- PWMC_ISR : (PWMC Offset: 0x1c) PWMC Interrupt Status Register --------  + +// ***************************************************************************** +//              SOFTWARE API DEFINITION  FOR USB Device Interface +// ***************************************************************************** +typedef struct _AT91S_UDP +{ +  AT91_REG UDP_NUM;		// Frame Number Register +  AT91_REG UDP_GLBSTATE;	// Global State Register +  AT91_REG UDP_FADDR;		// Function Address Register +  AT91_REG Reserved0[1];	//  +  AT91_REG UDP_IER;		// Interrupt Enable Register +  AT91_REG UDP_IDR;		// Interrupt Disable Register +  AT91_REG UDP_IMR;		// Interrupt Mask Register +  AT91_REG UDP_ISR;		// Interrupt Status Register +  AT91_REG UDP_ICR;		// Interrupt Clear Register +  AT91_REG Reserved1[1];	//  +  AT91_REG UDP_RSTEP;		// Reset Endpoint Register +  AT91_REG Reserved2[1];	//  +  AT91_REG UDP_CSR[4];		// Endpoint Control and Status Register +  AT91_REG Reserved3[4];	//  +  AT91_REG UDP_FDR[4];		// Endpoint FIFO Data Register +  AT91_REG Reserved4[5];	//  +  AT91_REG UDP_TXVC;		// Transceiver Control Register +} AT91S_UDP, *AT91PS_UDP; + +// -------- UDP_FRM_NUM : (UDP Offset: 0x0) USB Frame Number Register --------  +#define AT91C_UDP_FRM_NUM     ((unsigned int) 0x7FF <<  0)	// (UDP) Frame Number as Defined in the Packet Field Formats +#define AT91C_UDP_FRM_ERR     ((unsigned int) 0x1 << 16)	// (UDP) Frame Error +#define AT91C_UDP_FRM_OK      ((unsigned int) 0x1 << 17)	// (UDP) Frame OK +// -------- UDP_GLB_STATE : (UDP Offset: 0x4) USB Global State Register --------  +#define AT91C_UDP_FADDEN      ((unsigned int) 0x1 <<  0)	// (UDP) Function Address Enable +#define AT91C_UDP_CONFG       ((unsigned int) 0x1 <<  1)	// (UDP) Configured +#define AT91C_UDP_ESR         ((unsigned int) 0x1 <<  2)	// (UDP) Enable Send Resume +#define AT91C_UDP_RSMINPR     ((unsigned int) 0x1 <<  3)	// (UDP) A Resume Has Been Sent to the Host +#define AT91C_UDP_RMWUPE      ((unsigned int) 0x1 <<  4)	// (UDP) Remote Wake Up Enable +// -------- UDP_FADDR : (UDP Offset: 0x8) USB Function Address Register --------  +#define AT91C_UDP_FADD        ((unsigned int) 0xFF <<  0)	// (UDP) Function Address Value +#define AT91C_UDP_FEN         ((unsigned int) 0x1 <<  8)	// (UDP) Function Enable +// -------- UDP_IER : (UDP Offset: 0x10) USB Interrupt Enable Register --------  +#define AT91C_UDP_EPINT0      ((unsigned int) 0x1 <<  0)	// (UDP) Endpoint 0 Interrupt +#define AT91C_UDP_EPINT1      ((unsigned int) 0x1 <<  1)	// (UDP) Endpoint 1 Interrupt +#define AT91C_UDP_EPINT2      ((unsigned int) 0x1 <<  2)	// (UDP) Endpoint 2 Interrupt +#define AT91C_UDP_EPINT3      ((unsigned int) 0x1 <<  3)	// (UDP) Endpoint 3 Interrupt +#define AT91C_UDP_RXSUSP      ((unsigned int) 0x1 <<  8)	// (UDP) USB Suspend Interrupt +#define AT91C_UDP_RXRSM       ((unsigned int) 0x1 <<  9)	// (UDP) USB Resume Interrupt +#define AT91C_UDP_EXTRSM      ((unsigned int) 0x1 << 10)	// (UDP) USB External Resume Interrupt +#define AT91C_UDP_SOFINT      ((unsigned int) 0x1 << 11)	// (UDP) USB Start Of frame Interrupt +#define AT91C_UDP_WAKEUP      ((unsigned int) 0x1 << 13)	// (UDP) USB Resume Interrupt +// -------- UDP_IDR : (UDP Offset: 0x14) USB Interrupt Disable Register --------  +// -------- UDP_IMR : (UDP Offset: 0x18) USB Interrupt Mask Register --------  +// -------- UDP_ISR : (UDP Offset: 0x1c) USB Interrupt Status Register --------  +#define AT91C_UDP_ENDBUSRES   ((unsigned int) 0x1 << 12)	// (UDP) USB End Of Bus Reset Interrupt +// -------- UDP_ICR : (UDP Offset: 0x20) USB Interrupt Clear Register --------  +// -------- UDP_RST_EP : (UDP Offset: 0x28) USB Reset Endpoint Register --------  +#define AT91C_UDP_EP0         ((unsigned int) 0x1 <<  0)	// (UDP) Reset Endpoint 0 +#define AT91C_UDP_EP1         ((unsigned int) 0x1 <<  1)	// (UDP) Reset Endpoint 1 +#define AT91C_UDP_EP2         ((unsigned int) 0x1 <<  2)	// (UDP) Reset Endpoint 2 +#define AT91C_UDP_EP3         ((unsigned int) 0x1 <<  3)	// (UDP) Reset Endpoint 3 +// -------- UDP_CSR : (UDP Offset: 0x30) USB Endpoint Control and Status Register --------  +#define AT91C_UDP_TXCOMP      ((unsigned int) 0x1 <<  0)	// (UDP) Generates an IN packet with data previously written in the DPR +#define AT91C_UDP_RX_DATA_BK0 ((unsigned int) 0x1 <<  1)	// (UDP) Receive Data Bank 0 +#define AT91C_UDP_RXSETUP     ((unsigned int) 0x1 <<  2)	// (UDP) Sends STALL to the Host (Control endpoints) +#define AT91C_UDP_ISOERROR    ((unsigned int) 0x1 <<  3)	// (UDP) Isochronous error (Isochronous endpoints) +#define AT91C_UDP_STALLSENT   ((unsigned int) 0x1 <<  3)	// (UDP) Stall Sent (Control endpoints) +#define AT91C_UDP_TXPKTRDY    ((unsigned int) 0x1 <<  4)	// (UDP) Transmit Packet Ready +#define AT91C_UDP_FORCESTALL  ((unsigned int) 0x1 <<  5)	// (UDP) Force Stall (used by Control, Bulk and Isochronous endpoints). +#define AT91C_UDP_RX_DATA_BK1 ((unsigned int) 0x1 <<  6)	// (UDP) Receive Data Bank 1 (only used by endpoints with ping-pong attributes). +#define AT91C_UDP_DIR         ((unsigned int) 0x1 <<  7)	// (UDP) Transfer Direction +#define AT91C_UDP_EPTYPE      ((unsigned int) 0x7 <<  8)	// (UDP) Endpoint type +#define 	AT91C_UDP_EPTYPE_CTRL                 ((unsigned int) 0x0 <<  8)	// (UDP) Control +#define 	AT91C_UDP_EPTYPE_ISO_OUT              ((unsigned int) 0x1 <<  8)	// (UDP) Isochronous OUT +#define 	AT91C_UDP_EPTYPE_BULK_OUT             ((unsigned int) 0x2 <<  8)	// (UDP) Bulk OUT +#define 	AT91C_UDP_EPTYPE_INT_OUT              ((unsigned int) 0x3 <<  8)	// (UDP) Interrupt OUT +#define 	AT91C_UDP_EPTYPE_ISO_IN               ((unsigned int) 0x5 <<  8)	// (UDP) Isochronous IN +#define 	AT91C_UDP_EPTYPE_BULK_IN              ((unsigned int) 0x6 <<  8)	// (UDP) Bulk IN +#define 	AT91C_UDP_EPTYPE_INT_IN               ((unsigned int) 0x7 <<  8)	// (UDP) Interrupt IN +#define AT91C_UDP_DTGLE       ((unsigned int) 0x1 << 11)	// (UDP) Data Toggle +#define AT91C_UDP_EPEDS       ((unsigned int) 0x1 << 15)	// (UDP) Endpoint Enable Disable +#define AT91C_UDP_RXBYTECNT   ((unsigned int) 0x7FF << 16)	// (UDP) Number Of Bytes Available in the FIFO +// -------- UDP_TXVC : (UDP Offset: 0x74) Transceiver Control Register --------  +#define AT91C_UDP_TXVDIS      ((unsigned int) 0x1 <<  8)	// (UDP) + +// ***************************************************************************** +//               REGISTER ADDRESS DEFINITION FOR AT91SAM7S64 +// ***************************************************************************** +// ========== Register definition for SYS peripheral ==========  +// ========== Register definition for AIC peripheral ==========  +#define AT91C_AIC_IVR   ((AT91_REG *) 	0xFFFFF100)	// (AIC) IRQ Vector Register +#define AT91C_AIC_SMR   ((AT91_REG *) 	0xFFFFF000)	// (AIC) Source Mode Register +#define AT91C_AIC_FVR   ((AT91_REG *) 	0xFFFFF104)	// (AIC) FIQ Vector Register +#define AT91C_AIC_DCR   ((AT91_REG *) 	0xFFFFF138)	// (AIC) Debug Control Register (Protect) +#define AT91C_AIC_EOICR ((AT91_REG *) 	0xFFFFF130)	// (AIC) End of Interrupt Command Register +#define AT91C_AIC_SVR   ((AT91_REG *) 	0xFFFFF080)	// (AIC) Source Vector Register +#define AT91C_AIC_FFSR  ((AT91_REG *) 	0xFFFFF148)	// (AIC) Fast Forcing Status Register +#define AT91C_AIC_ICCR  ((AT91_REG *) 	0xFFFFF128)	// (AIC) Interrupt Clear Command Register +#define AT91C_AIC_ISR   ((AT91_REG *) 	0xFFFFF108)	// (AIC) Interrupt Status Register +#define AT91C_AIC_IMR   ((AT91_REG *) 	0xFFFFF110)	// (AIC) Interrupt Mask Register +#define AT91C_AIC_IPR   ((AT91_REG *) 	0xFFFFF10C)	// (AIC) Interrupt Pending Register +#define AT91C_AIC_FFER  ((AT91_REG *) 	0xFFFFF140)	// (AIC) Fast Forcing Enable Register +#define AT91C_AIC_IECR  ((AT91_REG *) 	0xFFFFF120)	// (AIC) Interrupt Enable Command Register +#define AT91C_AIC_ISCR  ((AT91_REG *) 	0xFFFFF12C)	// (AIC) Interrupt Set Command Register +#define AT91C_AIC_FFDR  ((AT91_REG *) 	0xFFFFF144)	// (AIC) Fast Forcing Disable Register +#define AT91C_AIC_CISR  ((AT91_REG *) 	0xFFFFF114)	// (AIC) Core Interrupt Status Register +#define AT91C_AIC_IDCR  ((AT91_REG *) 	0xFFFFF124)	// (AIC) Interrupt Disable Command Register +#define AT91C_AIC_SPU   ((AT91_REG *) 	0xFFFFF134)	// (AIC) Spurious Vector Register +// ========== Register definition for PDC_DBGU peripheral ==========  +#define AT91C_DBGU_TCR  ((AT91_REG *) 	0xFFFFF30C)	// (PDC_DBGU) Transmit Counter Register +#define AT91C_DBGU_RNPR ((AT91_REG *) 	0xFFFFF310)	// (PDC_DBGU) Receive Next Pointer Register +#define AT91C_DBGU_TNPR ((AT91_REG *) 	0xFFFFF318)	// (PDC_DBGU) Transmit Next Pointer Register +#define AT91C_DBGU_TPR  ((AT91_REG *) 	0xFFFFF308)	// (PDC_DBGU) Transmit Pointer Register +#define AT91C_DBGU_RPR  ((AT91_REG *) 	0xFFFFF300)	// (PDC_DBGU) Receive Pointer Register +#define AT91C_DBGU_RCR  ((AT91_REG *) 	0xFFFFF304)	// (PDC_DBGU) Receive Counter Register +#define AT91C_DBGU_RNCR ((AT91_REG *) 	0xFFFFF314)	// (PDC_DBGU) Receive Next Counter Register +#define AT91C_DBGU_PTCR ((AT91_REG *) 	0xFFFFF320)	// (PDC_DBGU) PDC Transfer Control Register +#define AT91C_DBGU_PTSR ((AT91_REG *) 	0xFFFFF324)	// (PDC_DBGU) PDC Transfer Status Register +#define AT91C_DBGU_TNCR ((AT91_REG *) 	0xFFFFF31C)	// (PDC_DBGU) Transmit Next Counter Register +// ========== Register definition for DBGU peripheral ==========  +#define AT91C_DBGU_EXID ((AT91_REG *) 	0xFFFFF244)	// (DBGU) Chip ID Extension Register +#define AT91C_DBGU_BRGR ((AT91_REG *) 	0xFFFFF220)	// (DBGU) Baud Rate Generator Register +#define AT91C_DBGU_IDR  ((AT91_REG *) 	0xFFFFF20C)	// (DBGU) Interrupt Disable Register +#define AT91C_DBGU_CSR  ((AT91_REG *) 	0xFFFFF214)	// (DBGU) Channel Status Register +#define AT91C_DBGU_CIDR ((AT91_REG *) 	0xFFFFF240)	// (DBGU) Chip ID Register +#define AT91C_DBGU_MR   ((AT91_REG *) 	0xFFFFF204)	// (DBGU) Mode Register +#define AT91C_DBGU_IMR  ((AT91_REG *) 	0xFFFFF210)	// (DBGU) Interrupt Mask Register +#define AT91C_DBGU_CR   ((AT91_REG *) 	0xFFFFF200)	// (DBGU) Control Register +#define AT91C_DBGU_FNTR ((AT91_REG *) 	0xFFFFF248)	// (DBGU) Force NTRST Register +#define AT91C_DBGU_THR  ((AT91_REG *) 	0xFFFFF21C)	// (DBGU) Transmitter Holding Register +#define AT91C_DBGU_RHR  ((AT91_REG *) 	0xFFFFF218)	// (DBGU) Receiver Holding Register +#define AT91C_DBGU_IER  ((AT91_REG *) 	0xFFFFF208)	// (DBGU) Interrupt Enable Register +// ========== Register definition for PIOA peripheral ==========  +#define AT91C_PIOA_ODR  ((AT91_REG *) 	0xFFFFF414)	// (PIOA) Output Disable Registerr +#define AT91C_PIOA_SODR ((AT91_REG *) 	0xFFFFF430)	// (PIOA) Set Output Data Register +#define AT91C_PIOA_ISR  ((AT91_REG *) 	0xFFFFF44C)	// (PIOA) Interrupt Status Register +#define AT91C_PIOA_ABSR ((AT91_REG *) 	0xFFFFF478)	// (PIOA) AB Select Status Register +#define AT91C_PIOA_IER  ((AT91_REG *) 	0xFFFFF440)	// (PIOA) Interrupt Enable Register +#define AT91C_PIOA_PPUDR ((AT91_REG *) 	0xFFFFF460)	// (PIOA) Pull-up Disable Register +#define AT91C_PIOA_IMR  ((AT91_REG *) 	0xFFFFF448)	// (PIOA) Interrupt Mask Register +#define AT91C_PIOA_PER  ((AT91_REG *) 	0xFFFFF400)	// (PIOA) PIO Enable Register +#define AT91C_PIOA_IFDR ((AT91_REG *) 	0xFFFFF424)	// (PIOA) Input Filter Disable Register +#define AT91C_PIOA_OWDR ((AT91_REG *) 	0xFFFFF4A4)	// (PIOA) Output Write Disable Register +#define AT91C_PIOA_MDSR ((AT91_REG *) 	0xFFFFF458)	// (PIOA) Multi-driver Status Register +#define AT91C_PIOA_IDR  ((AT91_REG *) 	0xFFFFF444)	// (PIOA) Interrupt Disable Register +#define AT91C_PIOA_ODSR ((AT91_REG *) 	0xFFFFF438)	// (PIOA) Output Data Status Register +#define AT91C_PIOA_PPUSR ((AT91_REG *) 	0xFFFFF468)	// (PIOA) Pull-up Status Register +#define AT91C_PIOA_OWSR ((AT91_REG *) 	0xFFFFF4A8)	// (PIOA) Output Write Status Register +#define AT91C_PIOA_BSR  ((AT91_REG *) 	0xFFFFF474)	// (PIOA) Select B Register +#define AT91C_PIOA_OWER ((AT91_REG *) 	0xFFFFF4A0)	// (PIOA) Output Write Enable Register +#define AT91C_PIOA_IFER ((AT91_REG *) 	0xFFFFF420)	// (PIOA) Input Filter Enable Register +#define AT91C_PIOA_PDSR ((AT91_REG *) 	0xFFFFF43C)	// (PIOA) Pin Data Status Register +#define AT91C_PIOA_PPUER ((AT91_REG *) 	0xFFFFF464)	// (PIOA) Pull-up Enable Register +#define AT91C_PIOA_OSR  ((AT91_REG *) 	0xFFFFF418)	// (PIOA) Output Status Register +#define AT91C_PIOA_ASR  ((AT91_REG *) 	0xFFFFF470)	// (PIOA) Select A Register +#define AT91C_PIOA_MDDR ((AT91_REG *) 	0xFFFFF454)	// (PIOA) Multi-driver Disable Register +#define AT91C_PIOA_CODR ((AT91_REG *) 	0xFFFFF434)	// (PIOA) Clear Output Data Register +#define AT91C_PIOA_MDER ((AT91_REG *) 	0xFFFFF450)	// (PIOA) Multi-driver Enable Register +#define AT91C_PIOA_PDR  ((AT91_REG *) 	0xFFFFF404)	// (PIOA) PIO Disable Register +#define AT91C_PIOA_IFSR ((AT91_REG *) 	0xFFFFF428)	// (PIOA) Input Filter Status Register +#define AT91C_PIOA_OER  ((AT91_REG *) 	0xFFFFF410)	// (PIOA) Output Enable Register +#define AT91C_PIOA_PSR  ((AT91_REG *) 	0xFFFFF408)	// (PIOA) PIO Status Register +// ========== Register definition for CKGR peripheral ==========  +#define AT91C_CKGR_MOR  ((AT91_REG *) 	0xFFFFFC20)	// (CKGR) Main Oscillator Register +#define AT91C_CKGR_PLLR ((AT91_REG *) 	0xFFFFFC2C)	// (CKGR) PLL Register +#define AT91C_CKGR_MCFR ((AT91_REG *) 	0xFFFFFC24)	// (CKGR) Main Clock  Frequency Register +// ========== Register definition for PMC peripheral ==========  +#define AT91C_PMC_IDR   ((AT91_REG *) 	0xFFFFFC64)	// (PMC) Interrupt Disable Register +#define AT91C_PMC_MOR   ((AT91_REG *) 	0xFFFFFC20)	// (PMC) Main Oscillator Register +#define AT91C_PMC_PLLR  ((AT91_REG *) 	0xFFFFFC2C)	// (PMC) PLL Register +#define AT91C_PMC_PCER  ((AT91_REG *) 	0xFFFFFC10)	// (PMC) Peripheral Clock Enable Register +#define AT91C_PMC_PCKR  ((AT91_REG *) 	0xFFFFFC40)	// (PMC) Programmable Clock Register +#define AT91C_PMC_MCKR  ((AT91_REG *) 	0xFFFFFC30)	// (PMC) Master Clock Register +#define AT91C_PMC_SCDR  ((AT91_REG *) 	0xFFFFFC04)	// (PMC) System Clock Disable Register +#define AT91C_PMC_PCDR  ((AT91_REG *) 	0xFFFFFC14)	// (PMC) Peripheral Clock Disable Register +#define AT91C_PMC_SCSR  ((AT91_REG *) 	0xFFFFFC08)	// (PMC) System Clock Status Register +#define AT91C_PMC_PCSR  ((AT91_REG *) 	0xFFFFFC18)	// (PMC) Peripheral Clock Status Register +#define AT91C_PMC_MCFR  ((AT91_REG *) 	0xFFFFFC24)	// (PMC) Main Clock  Frequency Register +#define AT91C_PMC_SCER  ((AT91_REG *) 	0xFFFFFC00)	// (PMC) System Clock Enable Register +#define AT91C_PMC_IMR   ((AT91_REG *) 	0xFFFFFC6C)	// (PMC) Interrupt Mask Register +#define AT91C_PMC_IER   ((AT91_REG *) 	0xFFFFFC60)	// (PMC) Interrupt Enable Register +#define AT91C_PMC_SR    ((AT91_REG *) 	0xFFFFFC68)	// (PMC) Status Register +// ========== Register definition for RSTC peripheral ==========  +#define AT91C_RSTC_RCR  ((AT91_REG *) 	0xFFFFFD00)	// (RSTC) Reset Control Register +#define AT91C_RSTC_RMR  ((AT91_REG *) 	0xFFFFFD08)	// (RSTC) Reset Mode Register +#define AT91C_RSTC_RSR  ((AT91_REG *) 	0xFFFFFD04)	// (RSTC) Reset Status Register +// ========== Register definition for RTTC peripheral ==========  +#define AT91C_RTTC_RTSR ((AT91_REG *) 	0xFFFFFD2C)	// (RTTC) Real-time Status Register +#define AT91C_RTTC_RTMR ((AT91_REG *) 	0xFFFFFD20)	// (RTTC) Real-time Mode Register +#define AT91C_RTTC_RTVR ((AT91_REG *) 	0xFFFFFD28)	// (RTTC) Real-time Value Register +#define AT91C_RTTC_RTAR ((AT91_REG *) 	0xFFFFFD24)	// (RTTC) Real-time Alarm Register +// ========== Register definition for PITC peripheral ==========  +#define AT91C_PITC_PIVR ((AT91_REG *) 	0xFFFFFD38)	// (PITC) Period Interval Value Register +#define AT91C_PITC_PISR ((AT91_REG *) 	0xFFFFFD34)	// (PITC) Period Interval Status Register +#define AT91C_PITC_PIIR ((AT91_REG *) 	0xFFFFFD3C)	// (PITC) Period Interval Image Register +#define AT91C_PITC_PIMR ((AT91_REG *) 	0xFFFFFD30)	// (PITC) Period Interval Mode Register +// ========== Register definition for WDTC peripheral ==========  +#define AT91C_WDTC_WDCR ((AT91_REG *) 	0xFFFFFD40)	// (WDTC) Watchdog Control Register +#define AT91C_WDTC_WDSR ((AT91_REG *) 	0xFFFFFD48)	// (WDTC) Watchdog Status Register +#define AT91C_WDTC_WDMR ((AT91_REG *) 	0xFFFFFD44)	// (WDTC) Watchdog Mode Register +// ========== Register definition for VREG peripheral ==========  +#define AT91C_VREG_MR   ((AT91_REG *) 	0xFFFFFD60)	// (VREG) Voltage Regulator Mode Register +// ========== Register definition for MC peripheral ==========  +#define AT91C_MC_ASR    ((AT91_REG *) 	0xFFFFFF04)	// (MC) MC Abort Status Register +#define AT91C_MC_RCR    ((AT91_REG *) 	0xFFFFFF00)	// (MC) MC Remap Control Register +#define AT91C_MC_FCR    ((AT91_REG *) 	0xFFFFFF64)	// (MC) MC Flash Command Register +#define AT91C_MC_AASR   ((AT91_REG *) 	0xFFFFFF08)	// (MC) MC Abort Address Status Register +#define AT91C_MC_FSR    ((AT91_REG *) 	0xFFFFFF68)	// (MC) MC Flash Status Register +#define AT91C_MC_FMR    ((AT91_REG *) 	0xFFFFFF60)	// (MC) MC Flash Mode Register +// ========== Register definition for PDC_SPI peripheral ==========  +#define AT91C_SPI_PTCR  ((AT91_REG *) 	0xFFFE0120)	// (PDC_SPI) PDC Transfer Control Register +#define AT91C_SPI_TPR   ((AT91_REG *) 	0xFFFE0108)	// (PDC_SPI) Transmit Pointer Register +#define AT91C_SPI_TCR   ((AT91_REG *) 	0xFFFE010C)	// (PDC_SPI) Transmit Counter Register +#define AT91C_SPI_RCR   ((AT91_REG *) 	0xFFFE0104)	// (PDC_SPI) Receive Counter Register +#define AT91C_SPI_PTSR  ((AT91_REG *) 	0xFFFE0124)	// (PDC_SPI) PDC Transfer Status Register +#define AT91C_SPI_RNPR  ((AT91_REG *) 	0xFFFE0110)	// (PDC_SPI) Receive Next Pointer Register +#define AT91C_SPI_RPR   ((AT91_REG *) 	0xFFFE0100)	// (PDC_SPI) Receive Pointer Register +#define AT91C_SPI_TNCR  ((AT91_REG *) 	0xFFFE011C)	// (PDC_SPI) Transmit Next Counter Register +#define AT91C_SPI_RNCR  ((AT91_REG *) 	0xFFFE0114)	// (PDC_SPI) Receive Next Counter Register +#define AT91C_SPI_TNPR  ((AT91_REG *) 	0xFFFE0118)	// (PDC_SPI) Transmit Next Pointer Register +// ========== Register definition for SPI peripheral ==========  +#define AT91C_SPI_IER   ((AT91_REG *) 	0xFFFE0014)	// (SPI) Interrupt Enable Register +#define AT91C_SPI_SR    ((AT91_REG *) 	0xFFFE0010)	// (SPI) Status Register +#define AT91C_SPI_IDR   ((AT91_REG *) 	0xFFFE0018)	// (SPI) Interrupt Disable Register +#define AT91C_SPI_CR    ((AT91_REG *) 	0xFFFE0000)	// (SPI) Control Register +#define AT91C_SPI_MR    ((AT91_REG *) 	0xFFFE0004)	// (SPI) Mode Register +#define AT91C_SPI_IMR   ((AT91_REG *) 	0xFFFE001C)	// (SPI) Interrupt Mask Register +#define AT91C_SPI_TDR   ((AT91_REG *) 	0xFFFE000C)	// (SPI) Transmit Data Register +#define AT91C_SPI_RDR   ((AT91_REG *) 	0xFFFE0008)	// (SPI) Receive Data Register +#define AT91C_SPI_CSR   ((AT91_REG *) 	0xFFFE0030)	// (SPI) Chip Select Register +// ========== Register definition for PDC_ADC peripheral ==========  +#define AT91C_ADC_PTSR  ((AT91_REG *) 	0xFFFD8124)	// (PDC_ADC) PDC Transfer Status Register +#define AT91C_ADC_PTCR  ((AT91_REG *) 	0xFFFD8120)	// (PDC_ADC) PDC Transfer Control Register +#define AT91C_ADC_TNPR  ((AT91_REG *) 	0xFFFD8118)	// (PDC_ADC) Transmit Next Pointer Register +#define AT91C_ADC_TNCR  ((AT91_REG *) 	0xFFFD811C)	// (PDC_ADC) Transmit Next Counter Register +#define AT91C_ADC_RNPR  ((AT91_REG *) 	0xFFFD8110)	// (PDC_ADC) Receive Next Pointer Register +#define AT91C_ADC_RNCR  ((AT91_REG *) 	0xFFFD8114)	// (PDC_ADC) Receive Next Counter Register +#define AT91C_ADC_RPR   ((AT91_REG *) 	0xFFFD8100)	// (PDC_ADC) Receive Pointer Register +#define AT91C_ADC_TCR   ((AT91_REG *) 	0xFFFD810C)	// (PDC_ADC) Transmit Counter Register +#define AT91C_ADC_TPR   ((AT91_REG *) 	0xFFFD8108)	// (PDC_ADC) Transmit Pointer Register +#define AT91C_ADC_RCR   ((AT91_REG *) 	0xFFFD8104)	// (PDC_ADC) Receive Counter Register +// ========== Register definition for ADC peripheral ==========  +#define AT91C_ADC_CDR2  ((AT91_REG *) 	0xFFFD8038)	// (ADC) ADC Channel Data Register 2 +#define AT91C_ADC_CDR3  ((AT91_REG *) 	0xFFFD803C)	// (ADC) ADC Channel Data Register 3 +#define AT91C_ADC_CDR0  ((AT91_REG *) 	0xFFFD8030)	// (ADC) ADC Channel Data Register 0 +#define AT91C_ADC_CDR5  ((AT91_REG *) 	0xFFFD8044)	// (ADC) ADC Channel Data Register 5 +#define AT91C_ADC_CHDR  ((AT91_REG *) 	0xFFFD8014)	// (ADC) ADC Channel Disable Register +#define AT91C_ADC_SR    ((AT91_REG *) 	0xFFFD801C)	// (ADC) ADC Status Register +#define AT91C_ADC_CDR4  ((AT91_REG *) 	0xFFFD8040)	// (ADC) ADC Channel Data Register 4 +#define AT91C_ADC_CDR1  ((AT91_REG *) 	0xFFFD8034)	// (ADC) ADC Channel Data Register 1 +#define AT91C_ADC_LCDR  ((AT91_REG *) 	0xFFFD8020)	// (ADC) ADC Last Converted Data Register +#define AT91C_ADC_IDR   ((AT91_REG *) 	0xFFFD8028)	// (ADC) ADC Interrupt Disable Register +#define AT91C_ADC_CR    ((AT91_REG *) 	0xFFFD8000)	// (ADC) ADC Control Register +#define AT91C_ADC_CDR7  ((AT91_REG *) 	0xFFFD804C)	// (ADC) ADC Channel Data Register 7 +#define AT91C_ADC_CDR6  ((AT91_REG *) 	0xFFFD8048)	// (ADC) ADC Channel Data Register 6 +#define AT91C_ADC_IER   ((AT91_REG *) 	0xFFFD8024)	// (ADC) ADC Interrupt Enable Register +#define AT91C_ADC_CHER  ((AT91_REG *) 	0xFFFD8010)	// (ADC) ADC Channel Enable Register +#define AT91C_ADC_CHSR  ((AT91_REG *) 	0xFFFD8018)	// (ADC) ADC Channel Status Register +#define AT91C_ADC_MR    ((AT91_REG *) 	0xFFFD8004)	// (ADC) ADC Mode Register +#define AT91C_ADC_IMR   ((AT91_REG *) 	0xFFFD802C)	// (ADC) ADC Interrupt Mask Register +// ========== Register definition for PDC_SSC peripheral ==========  +#define AT91C_SSC_TNCR  ((AT91_REG *) 	0xFFFD411C)	// (PDC_SSC) Transmit Next Counter Register +#define AT91C_SSC_RPR   ((AT91_REG *) 	0xFFFD4100)	// (PDC_SSC) Receive Pointer Register +#define AT91C_SSC_RNCR  ((AT91_REG *) 	0xFFFD4114)	// (PDC_SSC) Receive Next Counter Register +#define AT91C_SSC_TPR   ((AT91_REG *) 	0xFFFD4108)	// (PDC_SSC) Transmit Pointer Register +#define AT91C_SSC_PTCR  ((AT91_REG *) 	0xFFFD4120)	// (PDC_SSC) PDC Transfer Control Register +#define AT91C_SSC_TCR   ((AT91_REG *) 	0xFFFD410C)	// (PDC_SSC) Transmit Counter Register +#define AT91C_SSC_RCR   ((AT91_REG *) 	0xFFFD4104)	// (PDC_SSC) Receive Counter Register +#define AT91C_SSC_RNPR  ((AT91_REG *) 	0xFFFD4110)	// (PDC_SSC) Receive Next Pointer Register +#define AT91C_SSC_TNPR  ((AT91_REG *) 	0xFFFD4118)	// (PDC_SSC) Transmit Next Pointer Register +#define AT91C_SSC_PTSR  ((AT91_REG *) 	0xFFFD4124)	// (PDC_SSC) PDC Transfer Status Register +// ========== Register definition for SSC peripheral ==========  +#define AT91C_SSC_RHR   ((AT91_REG *) 	0xFFFD4020)	// (SSC) Receive Holding Register +#define AT91C_SSC_RSHR  ((AT91_REG *) 	0xFFFD4030)	// (SSC) Receive Sync Holding Register +#define AT91C_SSC_TFMR  ((AT91_REG *) 	0xFFFD401C)	// (SSC) Transmit Frame Mode Register +#define AT91C_SSC_IDR   ((AT91_REG *) 	0xFFFD4048)	// (SSC) Interrupt Disable Register +#define AT91C_SSC_THR   ((AT91_REG *) 	0xFFFD4024)	// (SSC) Transmit Holding Register +#define AT91C_SSC_RCMR  ((AT91_REG *) 	0xFFFD4010)	// (SSC) Receive Clock ModeRegister +#define AT91C_SSC_IER   ((AT91_REG *) 	0xFFFD4044)	// (SSC) Interrupt Enable Register +#define AT91C_SSC_TSHR  ((AT91_REG *) 	0xFFFD4034)	// (SSC) Transmit Sync Holding Register +#define AT91C_SSC_SR    ((AT91_REG *) 	0xFFFD4040)	// (SSC) Status Register +#define AT91C_SSC_CMR   ((AT91_REG *) 	0xFFFD4004)	// (SSC) Clock Mode Register +#define AT91C_SSC_TCMR  ((AT91_REG *) 	0xFFFD4018)	// (SSC) Transmit Clock Mode Register +#define AT91C_SSC_CR    ((AT91_REG *) 	0xFFFD4000)	// (SSC) Control Register +#define AT91C_SSC_IMR   ((AT91_REG *) 	0xFFFD404C)	// (SSC) Interrupt Mask Register +#define AT91C_SSC_RFMR  ((AT91_REG *) 	0xFFFD4014)	// (SSC) Receive Frame Mode Register +// ========== Register definition for PDC_US1 peripheral ==========  +#define AT91C_US1_RNCR  ((AT91_REG *) 	0xFFFC4114)	// (PDC_US1) Receive Next Counter Register +#define AT91C_US1_PTCR  ((AT91_REG *) 	0xFFFC4120)	// (PDC_US1) PDC Transfer Control Register +#define AT91C_US1_TCR   ((AT91_REG *) 	0xFFFC410C)	// (PDC_US1) Transmit Counter Register +#define AT91C_US1_PTSR  ((AT91_REG *) 	0xFFFC4124)	// (PDC_US1) PDC Transfer Status Register +#define AT91C_US1_TNPR  ((AT91_REG *) 	0xFFFC4118)	// (PDC_US1) Transmit Next Pointer Register +#define AT91C_US1_RCR   ((AT91_REG *) 	0xFFFC4104)	// (PDC_US1) Receive Counter Register +#define AT91C_US1_RNPR  ((AT91_REG *) 	0xFFFC4110)	// (PDC_US1) Receive Next Pointer Register +#define AT91C_US1_RPR   ((AT91_REG *) 	0xFFFC4100)	// (PDC_US1) Receive Pointer Register +#define AT91C_US1_TNCR  ((AT91_REG *) 	0xFFFC411C)	// (PDC_US1) Transmit Next Counter Register +#define AT91C_US1_TPR   ((AT91_REG *) 	0xFFFC4108)	// (PDC_US1) Transmit Pointer Register +// ========== Register definition for US1 peripheral ==========  +#define AT91C_US1_IF    ((AT91_REG *) 	0xFFFC404C)	// (US1) IRDA_FILTER Register +#define AT91C_US1_NER   ((AT91_REG *) 	0xFFFC4044)	// (US1) Nb Errors Register +#define AT91C_US1_RTOR  ((AT91_REG *) 	0xFFFC4024)	// (US1) Receiver Time-out Register +#define AT91C_US1_CSR   ((AT91_REG *) 	0xFFFC4014)	// (US1) Channel Status Register +#define AT91C_US1_IDR   ((AT91_REG *) 	0xFFFC400C)	// (US1) Interrupt Disable Register +#define AT91C_US1_IER   ((AT91_REG *) 	0xFFFC4008)	// (US1) Interrupt Enable Register +#define AT91C_US1_THR   ((AT91_REG *) 	0xFFFC401C)	// (US1) Transmitter Holding Register +#define AT91C_US1_TTGR  ((AT91_REG *) 	0xFFFC4028)	// (US1) Transmitter Time-guard Register +#define AT91C_US1_RHR   ((AT91_REG *) 	0xFFFC4018)	// (US1) Receiver Holding Register +#define AT91C_US1_BRGR  ((AT91_REG *) 	0xFFFC4020)	// (US1) Baud Rate Generator Register +#define AT91C_US1_IMR   ((AT91_REG *) 	0xFFFC4010)	// (US1) Interrupt Mask Register +#define AT91C_US1_FIDI  ((AT91_REG *) 	0xFFFC4040)	// (US1) FI_DI_Ratio Register +#define AT91C_US1_CR    ((AT91_REG *) 	0xFFFC4000)	// (US1) Control Register +#define AT91C_US1_MR    ((AT91_REG *) 	0xFFFC4004)	// (US1) Mode Register +// ========== Register definition for PDC_US0 peripheral ==========  +#define AT91C_US0_TNPR  ((AT91_REG *) 	0xFFFC0118)	// (PDC_US0) Transmit Next Pointer Register +#define AT91C_US0_RNPR  ((AT91_REG *) 	0xFFFC0110)	// (PDC_US0) Receive Next Pointer Register +#define AT91C_US0_TCR   ((AT91_REG *) 	0xFFFC010C)	// (PDC_US0) Transmit Counter Register +#define AT91C_US0_PTCR  ((AT91_REG *) 	0xFFFC0120)	// (PDC_US0) PDC Transfer Control Register +#define AT91C_US0_PTSR  ((AT91_REG *) 	0xFFFC0124)	// (PDC_US0) PDC Transfer Status Register +#define AT91C_US0_TNCR  ((AT91_REG *) 	0xFFFC011C)	// (PDC_US0) Transmit Next Counter Register +#define AT91C_US0_TPR   ((AT91_REG *) 	0xFFFC0108)	// (PDC_US0) Transmit Pointer Register +#define AT91C_US0_RCR   ((AT91_REG *) 	0xFFFC0104)	// (PDC_US0) Receive Counter Register +#define AT91C_US0_RPR   ((AT91_REG *) 	0xFFFC0100)	// (PDC_US0) Receive Pointer Register +#define AT91C_US0_RNCR  ((AT91_REG *) 	0xFFFC0114)	// (PDC_US0) Receive Next Counter Register +// ========== Register definition for US0 peripheral ==========  +#define AT91C_US0_BRGR  ((AT91_REG *) 	0xFFFC0020)	// (US0) Baud Rate Generator Register +#define AT91C_US0_NER   ((AT91_REG *) 	0xFFFC0044)	// (US0) Nb Errors Register +#define AT91C_US0_CR    ((AT91_REG *) 	0xFFFC0000)	// (US0) Control Register +#define AT91C_US0_IMR   ((AT91_REG *) 	0xFFFC0010)	// (US0) Interrupt Mask Register +#define AT91C_US0_FIDI  ((AT91_REG *) 	0xFFFC0040)	// (US0) FI_DI_Ratio Register +#define AT91C_US0_TTGR  ((AT91_REG *) 	0xFFFC0028)	// (US0) Transmitter Time-guard Register +#define AT91C_US0_MR    ((AT91_REG *) 	0xFFFC0004)	// (US0) Mode Register +#define AT91C_US0_RTOR  ((AT91_REG *) 	0xFFFC0024)	// (US0) Receiver Time-out Register +#define AT91C_US0_CSR   ((AT91_REG *) 	0xFFFC0014)	// (US0) Channel Status Register +#define AT91C_US0_RHR   ((AT91_REG *) 	0xFFFC0018)	// (US0) Receiver Holding Register +#define AT91C_US0_IDR   ((AT91_REG *) 	0xFFFC000C)	// (US0) Interrupt Disable Register +#define AT91C_US0_THR   ((AT91_REG *) 	0xFFFC001C)	// (US0) Transmitter Holding Register +#define AT91C_US0_IF    ((AT91_REG *) 	0xFFFC004C)	// (US0) IRDA_FILTER Register +#define AT91C_US0_IER   ((AT91_REG *) 	0xFFFC0008)	// (US0) Interrupt Enable Register +// ========== Register definition for TWI peripheral ==========  +#define AT91C_TWI_IER   ((AT91_REG *) 	0xFFFB8024)	// (TWI) Interrupt Enable Register +#define AT91C_TWI_CR    ((AT91_REG *) 	0xFFFB8000)	// (TWI) Control Register +#define AT91C_TWI_SR    ((AT91_REG *) 	0xFFFB8020)	// (TWI) Status Register +#define AT91C_TWI_IMR   ((AT91_REG *) 	0xFFFB802C)	// (TWI) Interrupt Mask Register +#define AT91C_TWI_THR   ((AT91_REG *) 	0xFFFB8034)	// (TWI) Transmit Holding Register +#define AT91C_TWI_IDR   ((AT91_REG *) 	0xFFFB8028)	// (TWI) Interrupt Disable Register +#define AT91C_TWI_IADR  ((AT91_REG *) 	0xFFFB800C)	// (TWI) Internal Address Register +#define AT91C_TWI_MMR   ((AT91_REG *) 	0xFFFB8004)	// (TWI) Master Mode Register +#define AT91C_TWI_CWGR  ((AT91_REG *) 	0xFFFB8010)	// (TWI) Clock Waveform Generator Register +#define AT91C_TWI_RHR   ((AT91_REG *) 	0xFFFB8030)	// (TWI) Receive Holding Register +// ========== Register definition for TC0 peripheral ==========  +#define AT91C_TC0_SR    ((AT91_REG *) 	0xFFFA0020)	// (TC0) Status Register +#define AT91C_TC0_RC    ((AT91_REG *) 	0xFFFA001C)	// (TC0) Register C +#define AT91C_TC0_RB    ((AT91_REG *) 	0xFFFA0018)	// (TC0) Register B +#define AT91C_TC0_CCR   ((AT91_REG *) 	0xFFFA0000)	// (TC0) Channel Control Register +#define AT91C_TC0_CMR   ((AT91_REG *) 	0xFFFA0004)	// (TC0) Channel Mode Register (Capture Mode / Waveform Mode) +#define AT91C_TC0_IER   ((AT91_REG *) 	0xFFFA0024)	// (TC0) Interrupt Enable Register +#define AT91C_TC0_RA    ((AT91_REG *) 	0xFFFA0014)	// (TC0) Register A +#define AT91C_TC0_IDR   ((AT91_REG *) 	0xFFFA0028)	// (TC0) Interrupt Disable Register +#define AT91C_TC0_CV    ((AT91_REG *) 	0xFFFA0010)	// (TC0) Counter Value +#define AT91C_TC0_IMR   ((AT91_REG *) 	0xFFFA002C)	// (TC0) Interrupt Mask Register +// ========== Register definition for TC1 peripheral ==========  +#define AT91C_TC1_RB    ((AT91_REG *) 	0xFFFA0058)	// (TC1) Register B +#define AT91C_TC1_CCR   ((AT91_REG *) 	0xFFFA0040)	// (TC1) Channel Control Register +#define AT91C_TC1_IER   ((AT91_REG *) 	0xFFFA0064)	// (TC1) Interrupt Enable Register +#define AT91C_TC1_IDR   ((AT91_REG *) 	0xFFFA0068)	// (TC1) Interrupt Disable Register +#define AT91C_TC1_SR    ((AT91_REG *) 	0xFFFA0060)	// (TC1) Status Register +#define AT91C_TC1_CMR   ((AT91_REG *) 	0xFFFA0044)	// (TC1) Channel Mode Register (Capture Mode / Waveform Mode) +#define AT91C_TC1_RA    ((AT91_REG *) 	0xFFFA0054)	// (TC1) Register A +#define AT91C_TC1_RC    ((AT91_REG *) 	0xFFFA005C)	// (TC1) Register C +#define AT91C_TC1_IMR   ((AT91_REG *) 	0xFFFA006C)	// (TC1) Interrupt Mask Register +#define AT91C_TC1_CV    ((AT91_REG *) 	0xFFFA0050)	// (TC1) Counter Value +// ========== Register definition for TC2 peripheral ==========  +#define AT91C_TC2_CMR   ((AT91_REG *) 	0xFFFA0084)	// (TC2) Channel Mode Register (Capture Mode / Waveform Mode) +#define AT91C_TC2_CCR   ((AT91_REG *) 	0xFFFA0080)	// (TC2) Channel Control Register +#define AT91C_TC2_CV    ((AT91_REG *) 	0xFFFA0090)	// (TC2) Counter Value +#define AT91C_TC2_RA    ((AT91_REG *) 	0xFFFA0094)	// (TC2) Register A +#define AT91C_TC2_RB    ((AT91_REG *) 	0xFFFA0098)	// (TC2) Register B +#define AT91C_TC2_IDR   ((AT91_REG *) 	0xFFFA00A8)	// (TC2) Interrupt Disable Register +#define AT91C_TC2_IMR   ((AT91_REG *) 	0xFFFA00AC)	// (TC2) Interrupt Mask Register +#define AT91C_TC2_RC    ((AT91_REG *) 	0xFFFA009C)	// (TC2) Register C +#define AT91C_TC2_IER   ((AT91_REG *) 	0xFFFA00A4)	// (TC2) Interrupt Enable Register +#define AT91C_TC2_SR    ((AT91_REG *) 	0xFFFA00A0)	// (TC2) Status Register +// ========== Register definition for TCB peripheral ==========  +#define AT91C_TCB_BMR   ((AT91_REG *) 	0xFFFA00C4)	// (TCB) TC Block Mode Register +#define AT91C_TCB_BCR   ((AT91_REG *) 	0xFFFA00C0)	// (TCB) TC Block Control Register +// ========== Register definition for PWMC_CH3 peripheral ==========  +#define AT91C_PWMC_CH3_CUPDR ((AT91_REG *) 	0xFFFCC270)	// (PWMC_CH3) Channel Update Register +#define AT91C_PWMC_CH3_Reserved ((AT91_REG *) 	0xFFFCC274)	// (PWMC_CH3) Reserved +#define AT91C_PWMC_CH3_CPRDR ((AT91_REG *) 	0xFFFCC268)	// (PWMC_CH3) Channel Period Register +#define AT91C_PWMC_CH3_CDTYR ((AT91_REG *) 	0xFFFCC264)	// (PWMC_CH3) Channel Duty Cycle Register +#define AT91C_PWMC_CH3_CCNTR ((AT91_REG *) 	0xFFFCC26C)	// (PWMC_CH3) Channel Counter Register +#define AT91C_PWMC_CH3_CMR ((AT91_REG *) 	0xFFFCC260)	// (PWMC_CH3) Channel Mode Register +// ========== Register definition for PWMC_CH2 peripheral ==========  +#define AT91C_PWMC_CH2_Reserved ((AT91_REG *) 	0xFFFCC254)	// (PWMC_CH2) Reserved +#define AT91C_PWMC_CH2_CMR ((AT91_REG *) 	0xFFFCC240)	// (PWMC_CH2) Channel Mode Register +#define AT91C_PWMC_CH2_CCNTR ((AT91_REG *) 	0xFFFCC24C)	// (PWMC_CH2) Channel Counter Register +#define AT91C_PWMC_CH2_CPRDR ((AT91_REG *) 	0xFFFCC248)	// (PWMC_CH2) Channel Period Register +#define AT91C_PWMC_CH2_CUPDR ((AT91_REG *) 	0xFFFCC250)	// (PWMC_CH2) Channel Update Register +#define AT91C_PWMC_CH2_CDTYR ((AT91_REG *) 	0xFFFCC244)	// (PWMC_CH2) Channel Duty Cycle Register +// ========== Register definition for PWMC_CH1 peripheral ==========  +#define AT91C_PWMC_CH1_Reserved ((AT91_REG *) 	0xFFFCC234)	// (PWMC_CH1) Reserved +#define AT91C_PWMC_CH1_CUPDR ((AT91_REG *) 	0xFFFCC230)	// (PWMC_CH1) Channel Update Register +#define AT91C_PWMC_CH1_CPRDR ((AT91_REG *) 	0xFFFCC228)	// (PWMC_CH1) Channel Period Register +#define AT91C_PWMC_CH1_CCNTR ((AT91_REG *) 	0xFFFCC22C)	// (PWMC_CH1) Channel Counter Register +#define AT91C_PWMC_CH1_CDTYR ((AT91_REG *) 	0xFFFCC224)	// (PWMC_CH1) Channel Duty Cycle Register +#define AT91C_PWMC_CH1_CMR ((AT91_REG *) 	0xFFFCC220)	// (PWMC_CH1) Channel Mode Register +// ========== Register definition for PWMC_CH0 peripheral ==========  +#define AT91C_PWMC_CH0_Reserved ((AT91_REG *) 	0xFFFCC214)	// (PWMC_CH0) Reserved +#define AT91C_PWMC_CH0_CPRDR ((AT91_REG *) 	0xFFFCC208)	// (PWMC_CH0) Channel Period Register +#define AT91C_PWMC_CH0_CDTYR ((AT91_REG *) 	0xFFFCC204)	// (PWMC_CH0) Channel Duty Cycle Register +#define AT91C_PWMC_CH0_CMR ((AT91_REG *) 	0xFFFCC200)	// (PWMC_CH0) Channel Mode Register +#define AT91C_PWMC_CH0_CUPDR ((AT91_REG *) 	0xFFFCC210)	// (PWMC_CH0) Channel Update Register +#define AT91C_PWMC_CH0_CCNTR ((AT91_REG *) 	0xFFFCC20C)	// (PWMC_CH0) Channel Counter Register +// ========== Register definition for PWMC peripheral ==========  +#define AT91C_PWMC_IDR  ((AT91_REG *) 	0xFFFCC014)	// (PWMC) PWMC Interrupt Disable Register +#define AT91C_PWMC_DIS  ((AT91_REG *) 	0xFFFCC008)	// (PWMC) PWMC Disable Register +#define AT91C_PWMC_IER  ((AT91_REG *) 	0xFFFCC010)	// (PWMC) PWMC Interrupt Enable Register +#define AT91C_PWMC_VR   ((AT91_REG *) 	0xFFFCC0FC)	// (PWMC) PWMC Version Register +#define AT91C_PWMC_ISR  ((AT91_REG *) 	0xFFFCC01C)	// (PWMC) PWMC Interrupt Status Register +#define AT91C_PWMC_SR   ((AT91_REG *) 	0xFFFCC00C)	// (PWMC) PWMC Status Register +#define AT91C_PWMC_IMR  ((AT91_REG *) 	0xFFFCC018)	// (PWMC) PWMC Interrupt Mask Register +#define AT91C_PWMC_MR   ((AT91_REG *) 	0xFFFCC000)	// (PWMC) PWMC Mode Register +#define AT91C_PWMC_ENA  ((AT91_REG *) 	0xFFFCC004)	// (PWMC) PWMC Enable Register +// ========== Register definition for UDP peripheral ==========  +#define AT91C_UDP_IMR   ((AT91_REG *) 	0xFFFB0018)	// (UDP) Interrupt Mask Register +#define AT91C_UDP_FADDR ((AT91_REG *) 	0xFFFB0008)	// (UDP) Function Address Register +#define AT91C_UDP_NUM   ((AT91_REG *) 	0xFFFB0000)	// (UDP) Frame Number Register +#define AT91C_UDP_FDR   ((AT91_REG *) 	0xFFFB0050)	// (UDP) Endpoint FIFO Data Register +#define AT91C_UDP_ISR   ((AT91_REG *) 	0xFFFB001C)	// (UDP) Interrupt Status Register +#define AT91C_UDP_CSR   ((AT91_REG *) 	0xFFFB0030)	// (UDP) Endpoint Control and Status Register +#define AT91C_UDP_IDR   ((AT91_REG *) 	0xFFFB0014)	// (UDP) Interrupt Disable Register +#define AT91C_UDP_ICR   ((AT91_REG *) 	0xFFFB0020)	// (UDP) Interrupt Clear Register +#define AT91C_UDP_RSTEP ((AT91_REG *) 	0xFFFB0028)	// (UDP) Reset Endpoint Register +#define AT91C_UDP_TXVC  ((AT91_REG *) 	0xFFFB0074)	// (UDP) Transceiver Control Register +#define AT91C_UDP_GLBSTATE ((AT91_REG *) 	0xFFFB0004)	// (UDP) Global State Register +#define AT91C_UDP_IER   ((AT91_REG *) 	0xFFFB0010)	// (UDP) Interrupt Enable Register + +// ***************************************************************************** +//               PIO DEFINITIONS FOR AT91SAM7S64 +// ***************************************************************************** +#define AT91C_PIO_PA0        ((unsigned int) 1 <<  0)	// Pin Controlled by PA0 +#define AT91C_PA0_PWM0     ((unsigned int) AT91C_PIO_PA0)	//  PWM Channel 0 +#define AT91C_PA0_TIOA0    ((unsigned int) AT91C_PIO_PA0)	//  Timer Counter 0 Multipurpose Timer I/O Pin A +#define AT91C_PIO_PA1        ((unsigned int) 1 <<  1)	// Pin Controlled by PA1 +#define AT91C_PA1_PWM1     ((unsigned int) AT91C_PIO_PA1)	//  PWM Channel 1 +#define AT91C_PA1_TIOB0    ((unsigned int) AT91C_PIO_PA1)	//  Timer Counter 0 Multipurpose Timer I/O Pin B +#define AT91C_PIO_PA10       ((unsigned int) 1 << 10)	// Pin Controlled by PA10 +#define AT91C_PA10_DTXD     ((unsigned int) AT91C_PIO_PA10)	//  DBGU Debug Transmit Data +#define AT91C_PA10_NPCS2    ((unsigned int) AT91C_PIO_PA10)	//  SPI Peripheral Chip Select 2 +#define AT91C_PIO_PA11       ((unsigned int) 1 << 11)	// Pin Controlled by PA11 +#define AT91C_PA11_NPCS0    ((unsigned int) AT91C_PIO_PA11)	//  SPI Peripheral Chip Select 0 +#define AT91C_PA11_PWM0     ((unsigned int) AT91C_PIO_PA11)	//  PWM Channel 0 +#define AT91C_PIO_PA12       ((unsigned int) 1 << 12)	// Pin Controlled by PA12 +#define AT91C_PA12_MISO     ((unsigned int) AT91C_PIO_PA12)	//  SPI Master In Slave +#define AT91C_PA12_PWM1     ((unsigned int) AT91C_PIO_PA12)	//  PWM Channel 1 +#define AT91C_PIO_PA13       ((unsigned int) 1 << 13)	// Pin Controlled by PA13 +#define AT91C_PA13_MOSI     ((unsigned int) AT91C_PIO_PA13)	//  SPI Master Out Slave +#define AT91C_PA13_PWM2     ((unsigned int) AT91C_PIO_PA13)	//  PWM Channel 2 +#define AT91C_PIO_PA14       ((unsigned int) 1 << 14)	// Pin Controlled by PA14 +#define AT91C_PA14_SPCK     ((unsigned int) AT91C_PIO_PA14)	//  SPI Serial Clock +#define AT91C_PA14_PWM3     ((unsigned int) AT91C_PIO_PA14)	//  PWM Channel 3 +#define AT91C_PIO_PA15       ((unsigned int) 1 << 15)	// Pin Controlled by PA15 +#define AT91C_PA15_TF       ((unsigned int) AT91C_PIO_PA15)	//  SSC Transmit Frame Sync +#define AT91C_PA15_TIOA1    ((unsigned int) AT91C_PIO_PA15)	//  Timer Counter 1 Multipurpose Timer I/O Pin A +#define AT91C_PIO_PA16       ((unsigned int) 1 << 16)	// Pin Controlled by PA16 +#define AT91C_PA16_TK       ((unsigned int) AT91C_PIO_PA16)	//  SSC Transmit Clock +#define AT91C_PA16_TIOB1    ((unsigned int) AT91C_PIO_PA16)	//  Timer Counter 1 Multipurpose Timer I/O Pin B +#define AT91C_PIO_PA17       ((unsigned int) 1 << 17)	// Pin Controlled by PA17 +#define AT91C_PA17_TD       ((unsigned int) AT91C_PIO_PA17)	//  SSC Transmit data +#define AT91C_PA17_PCK1     ((unsigned int) AT91C_PIO_PA17)	//  PMC Programmable Clock Output 1 +#define AT91C_PIO_PA18       ((unsigned int) 1 << 18)	// Pin Controlled by PA18 +#define AT91C_PA18_RD       ((unsigned int) AT91C_PIO_PA18)	//  SSC Receive Data +#define AT91C_PA18_PCK2     ((unsigned int) AT91C_PIO_PA18)	//  PMC Programmable Clock Output 2 +#define AT91C_PIO_PA19       ((unsigned int) 1 << 19)	// Pin Controlled by PA19 +#define AT91C_PA19_RK       ((unsigned int) AT91C_PIO_PA19)	//  SSC Receive Clock +#define AT91C_PA19_FIQ      ((unsigned int) AT91C_PIO_PA19)	//  AIC Fast Interrupt Input +#define AT91C_PIO_PA2        ((unsigned int) 1 <<  2)	// Pin Controlled by PA2 +#define AT91C_PA2_PWM2     ((unsigned int) AT91C_PIO_PA2)	//  PWM Channel 2 +#define AT91C_PA2_SCK0     ((unsigned int) AT91C_PIO_PA2)	//  USART 0 Serial Clock +#define AT91C_PIO_PA20       ((unsigned int) 1 << 20)	// Pin Controlled by PA20 +#define AT91C_PA20_RF       ((unsigned int) AT91C_PIO_PA20)	//  SSC Receive Frame Sync +#define AT91C_PA20_IRQ0     ((unsigned int) AT91C_PIO_PA20)	//  External Interrupt 0 +#define AT91C_PIO_PA21       ((unsigned int) 1 << 21)	// Pin Controlled by PA21 +#define AT91C_PA21_RXD1     ((unsigned int) AT91C_PIO_PA21)	//  USART 1 Receive Data +#define AT91C_PA21_PCK1     ((unsigned int) AT91C_PIO_PA21)	//  PMC Programmable Clock Output 1 +#define AT91C_PIO_PA22       ((unsigned int) 1 << 22)	// Pin Controlled by PA22 +#define AT91C_PA22_TXD1     ((unsigned int) AT91C_PIO_PA22)	//  USART 1 Transmit Data +#define AT91C_PA22_NPCS3    ((unsigned int) AT91C_PIO_PA22)	//  SPI Peripheral Chip Select 3 +#define AT91C_PIO_PA23       ((unsigned int) 1 << 23)	// Pin Controlled by PA23 +#define AT91C_PA23_SCK1     ((unsigned int) AT91C_PIO_PA23)	//  USART 1 Serial Clock +#define AT91C_PA23_PWM0     ((unsigned int) AT91C_PIO_PA23)	//  PWM Channel 0 +#define AT91C_PIO_PA24       ((unsigned int) 1 << 24)	// Pin Controlled by PA24 +#define AT91C_PA24_RTS1     ((unsigned int) AT91C_PIO_PA24)	//  USART 1 Ready To Send +#define AT91C_PA24_PWM1     ((unsigned int) AT91C_PIO_PA24)	//  PWM Channel 1 +#define AT91C_PIO_PA25       ((unsigned int) 1 << 25)	// Pin Controlled by PA25 +#define AT91C_PA25_CTS1     ((unsigned int) AT91C_PIO_PA25)	//  USART 1 Clear To Send +#define AT91C_PA25_PWM2     ((unsigned int) AT91C_PIO_PA25)	//  PWM Channel 2 +#define AT91C_PIO_PA26       ((unsigned int) 1 << 26)	// Pin Controlled by PA26 +#define AT91C_PA26_DCD1     ((unsigned int) AT91C_PIO_PA26)	//  USART 1 Data Carrier Detect +#define AT91C_PA26_TIOA2    ((unsigned int) AT91C_PIO_PA26)	//  Timer Counter 2 Multipurpose Timer I/O Pin A +#define AT91C_PIO_PA27       ((unsigned int) 1 << 27)	// Pin Controlled by PA27 +#define AT91C_PA27_DTR1     ((unsigned int) AT91C_PIO_PA27)	//  USART 1 Data Terminal ready +#define AT91C_PA27_TIOB2    ((unsigned int) AT91C_PIO_PA27)	//  Timer Counter 2 Multipurpose Timer I/O Pin B +#define AT91C_PIO_PA28       ((unsigned int) 1 << 28)	// Pin Controlled by PA28 +#define AT91C_PA28_DSR1     ((unsigned int) AT91C_PIO_PA28)	//  USART 1 Data Set ready +#define AT91C_PA28_TCLK1    ((unsigned int) AT91C_PIO_PA28)	//  Timer Counter 1 external clock input +#define AT91C_PIO_PA29       ((unsigned int) 1 << 29)	// Pin Controlled by PA29 +#define AT91C_PA29_RI1      ((unsigned int) AT91C_PIO_PA29)	//  USART 1 Ring Indicator +#define AT91C_PA29_TCLK2    ((unsigned int) AT91C_PIO_PA29)	//  Timer Counter 2 external clock input +#define AT91C_PIO_PA3        ((unsigned int) 1 <<  3)	// Pin Controlled by PA3 +#define AT91C_PA3_TWD      ((unsigned int) AT91C_PIO_PA3)	//  TWI Two-wire Serial Data +#define AT91C_PA3_NPCS3    ((unsigned int) AT91C_PIO_PA3)	//  SPI Peripheral Chip Select 3 +#define AT91C_PIO_PA30       ((unsigned int) 1 << 30)	// Pin Controlled by PA30 +#define AT91C_PA30_IRQ1     ((unsigned int) AT91C_PIO_PA30)	//  External Interrupt 1 +#define AT91C_PA30_NPCS2    ((unsigned int) AT91C_PIO_PA30)	//  SPI Peripheral Chip Select 2 +#define AT91C_PIO_PA31       ((unsigned int) 1 << 31)	// Pin Controlled by PA31 +#define AT91C_PA31_NPCS1    ((unsigned int) AT91C_PIO_PA31)	//  SPI Peripheral Chip Select 1 +#define AT91C_PA31_PCK2     ((unsigned int) AT91C_PIO_PA31)	//  PMC Programmable Clock Output 2 +#define AT91C_PIO_PA4        ((unsigned int) 1 <<  4)	// Pin Controlled by PA4 +#define AT91C_PA4_TWCK     ((unsigned int) AT91C_PIO_PA4)	//  TWI Two-wire Serial Clock +#define AT91C_PA4_TCLK0    ((unsigned int) AT91C_PIO_PA4)	//  Timer Counter 0 external clock input +#define AT91C_PIO_PA5        ((unsigned int) 1 <<  5)	// Pin Controlled by PA5 +#define AT91C_PA5_RXD0     ((unsigned int) AT91C_PIO_PA5)	//  USART 0 Receive Data +#define AT91C_PA5_NPCS3    ((unsigned int) AT91C_PIO_PA5)	//  SPI Peripheral Chip Select 3 +#define AT91C_PIO_PA6        ((unsigned int) 1 <<  6)	// Pin Controlled by PA6 +#define AT91C_PA6_TXD0     ((unsigned int) AT91C_PIO_PA6)	//  USART 0 Transmit Data +#define AT91C_PA6_PCK0     ((unsigned int) AT91C_PIO_PA6)	//  PMC Programmable Clock Output 0 +#define AT91C_PIO_PA7        ((unsigned int) 1 <<  7)	// Pin Controlled by PA7 +#define AT91C_PA7_RTS0     ((unsigned int) AT91C_PIO_PA7)	//  USART 0 Ready To Send +#define AT91C_PA7_PWM3     ((unsigned int) AT91C_PIO_PA7)	//  PWM Channel 3 +#define AT91C_PIO_PA8        ((unsigned int) 1 <<  8)	// Pin Controlled by PA8 +#define AT91C_PA8_CTS0     ((unsigned int) AT91C_PIO_PA8)	//  USART 0 Clear To Send +#define AT91C_PA8_ADTRG    ((unsigned int) AT91C_PIO_PA8)	//  ADC External Trigger +#define AT91C_PIO_PA9        ((unsigned int) 1 <<  9)	// Pin Controlled by PA9 +#define AT91C_PA9_DRXD     ((unsigned int) AT91C_PIO_PA9)	//  DBGU Debug Receive Data +#define AT91C_PA9_NPCS1    ((unsigned int) AT91C_PIO_PA9)	//  SPI Peripheral Chip Select 1 + +// ***************************************************************************** +//               PERIPHERAL ID DEFINITIONS FOR AT91SAM7S +// ***************************************************************************** +#define AT91C_ID_FIQ    ((unsigned int)  0)	// Advanced Interrupt Controller (FIQ) +#define AT91C_ID_SYS    ((unsigned int)  1)	// System Peripheral +#define AT91C_ID_PIOA   ((unsigned int)  2)	// Parallel IO Controller +#define AT91C_ID_PIOB   ((unsigned int)  3)	// Parallel IO Controller B +#define AT91C_ID_ADC    ((unsigned int)  4)	// Analog-to-Digital Converter +#define AT91C_ID_SPI    ((unsigned int)  5)	// Serial Peripheral Interface +#define AT91C_ID_US0    ((unsigned int)  6)	// USART 0 +#define AT91C_ID_US1    ((unsigned int)  7)	// USART 1 +#define AT91C_ID_SSC    ((unsigned int)  8)	// Serial Synchronous Controller +#define AT91C_ID_TWI    ((unsigned int)  9)	// Two-Wire Interface +#define AT91C_ID_PWMC   ((unsigned int) 10)	// PWM Controller +#define AT91C_ID_UDP    ((unsigned int) 11)	// USB Device Port +#define AT91C_ID_TC0    ((unsigned int) 12)	// Timer Counter 0 +#define AT91C_ID_TC1    ((unsigned int) 13)	// Timer Counter 1 +#define AT91C_ID_TC2    ((unsigned int) 14)	// Timer Counter 2 +#define AT91C_ID_15_Reserved ((unsigned int) 15)	// Reserved +#define AT91C_ID_16_Reserved ((unsigned int) 16)	// Reserved +#define AT91C_ID_17_Reserved ((unsigned int) 17)	// Reserved +#define AT91C_ID_18_Reserved ((unsigned int) 18)	// Reserved +#define AT91C_ID_19_Reserved ((unsigned int) 19)	// Reserved +#define AT91C_ID_20_Reserved ((unsigned int) 20)	// Reserved +#define AT91C_ID_21_Reserved ((unsigned int) 21)	// Reserved +#define AT91C_ID_22_Reserved ((unsigned int) 22)	// Reserved +#define AT91C_ID_23_Reserved ((unsigned int) 23)	// Reserved +#define AT91C_ID_24_Reserved ((unsigned int) 24)	// Reserved +#define AT91C_ID_25_Reserved ((unsigned int) 25)	// Reserved +#define AT91C_ID_26_Reserved ((unsigned int) 26)	// Reserved +#define AT91C_ID_27_Reserved ((unsigned int) 27)	// Reserved +#define AT91C_ID_28_Reserved ((unsigned int) 28)	// Reserved +#define AT91C_ID_29_Reserved ((unsigned int) 29)	// Reserved +#define AT91C_ID_IRQ0   ((unsigned int) 30)	// Advanced Interrupt Controller (IRQ0) +#define AT91C_ID_IRQ1   ((unsigned int) 31)	// Advanced Interrupt Controller (IRQ1) +#define AT91C_ALL_INT   ((unsigned int) 0xC0007FF7)	// ALL VALID INTERRUPTS + +// ***************************************************************************** +//               BASE ADDRESS DEFINITIONS FOR AT91SAM7S64 +// ***************************************************************************** +#define AT91C_BASE_SYS       ((AT91PS_SYS) 	0xFFFFF000)	// (SYS) Base Address +#define AT91C_BASE_AIC       ((AT91PS_AIC) 	0xFFFFF000)	// (AIC) Base Address +#define AT91C_BASE_PDC_DBGU  ((AT91PS_PDC) 	0xFFFFF300)	// (PDC_DBGU) Base Address +#define AT91C_BASE_DBGU      ((AT91PS_DBGU) 	0xFFFFF200)	// (DBGU) Base Address +#define AT91C_BASE_PIOA      ((AT91PS_PIO) 	0xFFFFF400)	// (PIOA) Base Address +#define AT91C_BASE_CKGR      ((AT91PS_CKGR) 	0xFFFFFC20)	// (CKGR) Base Address +#define AT91C_BASE_PMC       ((AT91PS_PMC) 	0xFFFFFC00)	// (PMC) Base Address +#define AT91C_BASE_RSTC      ((AT91PS_RSTC) 	0xFFFFFD00)	// (RSTC) Base Address +#define AT91C_BASE_RTTC      ((AT91PS_RTTC) 	0xFFFFFD20)	// (RTTC) Base Address +#define AT91C_BASE_PITC      ((AT91PS_PITC) 	0xFFFFFD30)	// (PITC) Base Address +#define AT91C_BASE_WDTC      ((AT91PS_WDTC) 	0xFFFFFD40)	// (WDTC) Base Address +#define AT91C_BASE_VREG      ((AT91PS_VREG) 	0xFFFFFD60)	// (VREG) Base Address +#define AT91C_BASE_MC        ((AT91PS_MC) 	0xFFFFFF00)	// (MC) Base Address +#define AT91C_BASE_PDC_SPI   ((AT91PS_PDC) 	0xFFFE0100)	// (PDC_SPI) Base Address +#define AT91C_BASE_SPI       ((AT91PS_SPI) 	0xFFFE0000)	// (SPI) Base Address +#define AT91C_BASE_PDC_ADC   ((AT91PS_PDC) 	0xFFFD8100)	// (PDC_ADC) Base Address +#define AT91C_BASE_ADC       ((AT91PS_ADC) 	0xFFFD8000)	// (ADC) Base Address +#define AT91C_BASE_PDC_SSC   ((AT91PS_PDC) 	0xFFFD4100)	// (PDC_SSC) Base Address +#define AT91C_BASE_SSC       ((AT91PS_SSC) 	0xFFFD4000)	// (SSC) Base Address +#define AT91C_BASE_PDC_US1   ((AT91PS_PDC) 	0xFFFC4100)	// (PDC_US1) Base Address +#define AT91C_BASE_US1       ((AT91PS_USART) 	0xFFFC4000)	// (US1) Base Address +#define AT91C_BASE_PDC_US0   ((AT91PS_PDC) 	0xFFFC0100)	// (PDC_US0) Base Address +#define AT91C_BASE_US0       ((AT91PS_USART) 	0xFFFC0000)	// (US0) Base Address +#define AT91C_BASE_TWI       ((AT91PS_TWI) 	0xFFFB8000)	// (TWI) Base Address +#define AT91C_BASE_TC0       ((AT91PS_TC) 	0xFFFA0000)	// (TC0) Base Address +#define AT91C_BASE_TC1       ((AT91PS_TC) 	0xFFFA0040)	// (TC1) Base Address +#define AT91C_BASE_TC2       ((AT91PS_TC) 	0xFFFA0080)	// (TC2) Base Address +#define AT91C_BASE_TCB       ((AT91PS_TCB) 	0xFFFA0000)	// (TCB) Base Address +#define AT91C_BASE_PWMC_CH3  ((AT91PS_PWMC_CH) 	0xFFFCC260)	// (PWMC_CH3) Base Address +#define AT91C_BASE_PWMC_CH2  ((AT91PS_PWMC_CH) 	0xFFFCC240)	// (PWMC_CH2) Base Address +#define AT91C_BASE_PWMC_CH1  ((AT91PS_PWMC_CH) 	0xFFFCC220)	// (PWMC_CH1) Base Address +#define AT91C_BASE_PWMC_CH0  ((AT91PS_PWMC_CH) 	0xFFFCC200)	// (PWMC_CH0) Base Address +#define AT91C_BASE_PWMC      ((AT91PS_PWMC) 	0xFFFCC000)	// (PWMC) Base Address +#define AT91C_BASE_UDP       ((AT91PS_UDP) 	0xFFFB0000)	// (UDP) Base Address + +// ***************************************************************************** +//               MEMORY MAPPING DEFINITIONS FOR AT91SAM7S64 +// ***************************************************************************** +// ISRAM +#define AT91C_ISRAM	 ((char *) 	0x00200000)	// Internal SRAM base address +// IFLASH +#define AT91C_IFLASH	 ((char *) 	0x00100000)	// Internal FLASH base address + +#if defined(__AT91SAM7S32__) +#define AT91C_ISRAM_SIZE	 ((unsigned int) 0x00002000)	// Internal SRAM size in byte (8 Kbytes) +#define AT91C_IFLASH_SIZE	 ((unsigned int) 0x00008000)	// Internal FLASH size in byte (32 Kbytes) +#define AT91C_IFLASH_PAGE_SIZE	 ((unsigned int) 128)	// Internal FLASH Page Size: 128 bytes +#define AT91C_IFLASH_PAGE_SHIFT		 7 +#define AT91C_IFLASH_NB_OF_LOCK_BITS	 ((unsigned int) 8)	// Internal FLASH Number of Lock Bits: 8 +#elif defined(__AT91SAM7S64__) +#define AT91C_ISRAM_SIZE	 ((unsigned int) 0x00004000)	// Internal SRAM size in byte (16 Kbytes) +#define AT91C_IFLASH_SIZE	 ((unsigned int) 0x00010000)	// Internal FLASH size in byte (64 Kbytes) +#define AT91C_IFLASH_PAGE_SIZE	 ((unsigned int) 128)	// Internal FLASH Page Size: 128 bytes +#define AT91C_IFLASH_PAGE_SHIFT		 7 +#define AT91C_IFLASH_NB_OF_LOCK_BITS	 ((unsigned int) 16)	// Internal FLASH Number of Lock Bits: 16 +#elif defined(__AT91SAM7S128__) +#define AT91C_ISRAM_SIZE	 ((unsigned int) 0x00008000)	// Internal SRAM size in byte (32 Kbytes) +#define AT91C_IFLASH_SIZE	 ((unsigned int) 0x00020000)	// Internal FLASH size in byte (128 Kbytes) +#define AT91C_IFLASH_PAGE_SIZE	 ((unsigned int) 256)	// Internal FLASH Page Size: 256 bytes +#define AT91C_IFLASH_PAGE_SHIFT		 8 +#define AT91C_IFLASH_NB_OF_LOCK_BITS	 ((unsigned int) 8)	// Internal FLASH Number of Lock Bits: 8 +#elif defined(__AT91SAM7S256__) +#define AT91C_ISRAM_SIZE	 ((unsigned int) 0x00010000)	// Internal SRAM size in byte (64 Kbytes) +#define AT91C_IFLASH_SIZE	 ((unsigned int) 0x00040000)	// Internal FLASH size in byte (256 Kbytes) +#define AT91C_IFLASH_PAGE_SIZE	 ((unsigned int) 256)	// Internal FLASH Page Size: 256 bytes +#define AT91C_IFLASH_PAGE_SHIFT		 8 +#define AT91C_IFLASH_NB_OF_LOCK_BITS	 ((unsigned int) 16)	// Internal FLASH Number of Lock Bits: 16 +#else +#error Have to define which __AT91SAM7Sxxx__ type +#endif + +#define AT91C_IFLASH_NB_OF_PAGES	 (AT91C_IFLASH_SIZE>>AT91C_IFLASH_PAGE_SHIFT) +#define AT91C_IFLASH_LOCK_REGION_SIZE	 (AT91C_IFLASH_SIZE/AT91C_IFLASH_NB_OF_LOCK_BITS) + +#endif/*__AT91SAM7_H__*/ diff --git a/openpicc/os/core/ARM7_AT91SAM7S/lib_AT91SAM7.c b/openpicc/os/core/ARM7_AT91SAM7S/lib_AT91SAM7.c new file mode 100644 index 0000000..bf9ae6d --- /dev/null +++ b/openpicc/os/core/ARM7_AT91SAM7S/lib_AT91SAM7.c @@ -0,0 +1,424 @@ +//* ---------------------------------------------------------------------------- +//*         ATMEL Microcontroller Software Support  -  ROUSSET  - +//* ---------------------------------------------------------------------------- +//* DISCLAIMER:  THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR +//* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +//* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE +//* DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR ANY DIRECT, INDIRECT, +//* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +//* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, +//* OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF +//* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING +//* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, +//* EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +//* ---------------------------------------------------------------------------- +//* File Name           : lib_AT91SAM7S64.h +//* Object              : AT91SAM7S64 inlined functions +//* Generated           : AT91 SW Application Group  08/30/2005 (15:52:59) +//* + +#include <sys/types.h> +#include <AT91SAM7.h> +#include <lib_AT91SAM7.h> + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_ConfigureIt +//* \brief Interrupt Handler Initialization +//*---------------------------------------------------------------------------- +unsigned int +AT91F_AIC_ConfigureIt (unsigned int irq_id,	// \arg interrupt number to initialize +		       unsigned int priority,	// \arg priority to give to the interrupt +		       unsigned int src_type,	// \arg activation and sense of activation +		       THandler handler)	// \arg address of the interrupt handler +{ +  unsigned int oldHandler; +  unsigned int mask; + +  oldHandler = AT91C_BASE_AIC->AIC_SVR[irq_id]; + +  mask = 0x1 << irq_id; +  //* Disable the interrupt on the interrupt controller +  AT91C_BASE_AIC->AIC_IDCR = mask; +  //* Save the interrupt handler routine pointer and the interrupt priority +  AT91C_BASE_AIC->AIC_SVR[irq_id] = (unsigned int) handler; +  //* Store the Source Mode Register +  AT91C_BASE_AIC->AIC_SMR[irq_id] = src_type | priority; +  //* Clear the interrupt on the interrupt controller +  AT91C_BASE_AIC->AIC_ICCR = mask; + +  return (unsigned int) handler; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_SetExceptionVector +//* \brief Configure vector handler +//*---------------------------------------------------------------------------- +unsigned int +AT91F_AIC_SetExceptionVector (unsigned int *pVector,	// \arg pointer to the AIC registers +			      THandler Handler)	// \arg Interrupt Handler +{ +  unsigned int oldVector = *pVector; + +  if ((unsigned int) Handler == (unsigned int) AT91C_AIC_BRANCH_OPCODE) +    *pVector = (unsigned int) AT91C_AIC_BRANCH_OPCODE; +  else +    *pVector = +      (((((unsigned int) Handler) - ((unsigned int) pVector) - +	 0x8) >> 2) & 0x00FFFFFF) | 0xEA000000; + +  return oldVector; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_Open +//* \brief Set exception vectors and AIC registers to default values +//*---------------------------------------------------------------------------- +void +AT91F_AIC_Open (THandler IrqHandler,	// \arg Default IRQ vector exception +		THandler FiqHandler,	// \arg Default FIQ vector exception +		THandler DefaultHandler,	// \arg Default Handler set in ISR +		THandler SpuriousHandler,	// \arg Default Spurious Handler +		unsigned int protectMode)	// \arg Debug Control Register +{ +  int i; + +  // Disable all interrupts and set IVR to the default handler +  for (i = 0; i < 32; ++i) +    { +      AT91F_AIC_DisableIt (i); +      AT91F_AIC_ConfigureIt (i, AT91C_AIC_PRIOR_LOWEST, +			     AT91C_AIC_SRCTYPE_HIGH_LEVEL, DefaultHandler); +    } + +  // Set the IRQ exception vector +  AT91F_AIC_SetExceptionVector ((unsigned int *) 0x18, IrqHandler); +  // Set the Fast Interrupt exception vector +  AT91F_AIC_SetExceptionVector ((unsigned int *) 0x1C, FiqHandler); + +  AT91C_BASE_AIC->AIC_SPU = (unsigned int) SpuriousHandler; +  AT91C_BASE_AIC->AIC_DCR = protectMode; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_Open +//* \brief Open PDC: disable TX and RX reset transfer descriptors, re-enable RX and TX +//*---------------------------------------------------------------------------- +void +AT91F_PDC_Open (AT91PS_PDC pPDC)	// \arg pointer to a PDC controller +{ +  //* Disable the RX and TX PDC transfer requests +  AT91F_PDC_DisableRx (pPDC); +  AT91F_PDC_DisableTx (pPDC); + +  //* Reset all Counter register Next buffer first +  AT91F_PDC_SetNextTx (pPDC, NULL, 0); +  AT91F_PDC_SetNextRx (pPDC, NULL, 0); +  AT91F_PDC_SetTx (pPDC, NULL, 0); +  AT91F_PDC_SetRx (pPDC, NULL, 0); + +  //* Enable the RX and TX PDC transfer requests +  AT91F_PDC_EnableRx (pPDC); +  AT91F_PDC_EnableTx (pPDC); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_Close +//* \brief Close PDC: disable TX and RX reset transfer descriptors +//*---------------------------------------------------------------------------- +void +AT91F_PDC_Close (AT91PS_PDC pPDC)	// \arg pointer to a PDC controller +{ +  //* Disable the RX and TX PDC transfer requests +  AT91F_PDC_DisableRx (pPDC); +  AT91F_PDC_DisableTx (pPDC); + +  //* Reset all Counter register Next buffer first +  AT91F_PDC_SetNextTx (pPDC, NULL, 0); +  AT91F_PDC_SetNextRx (pPDC, NULL, 0); +  AT91F_PDC_SetTx (pPDC, NULL, 0); +  AT91F_PDC_SetRx (pPDC, NULL, 0); + +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_SendFrame +//* \brief Close PDC: disable TX and RX reset transfer descriptors +//*---------------------------------------------------------------------------- +unsigned int +AT91F_PDC_SendFrame (AT91PS_PDC pPDC, +		     const unsigned char *pBuffer, +		     unsigned int szBuffer, +		     const unsigned char *pNextBuffer, +		     unsigned int szNextBuffer) +{ +  if (AT91F_PDC_IsTxEmpty (pPDC)) +    { +      //* Buffer and next buffer can be initialized +      AT91F_PDC_SetTx (pPDC, pBuffer, szBuffer); +      AT91F_PDC_SetNextTx (pPDC, pNextBuffer, szNextBuffer); +      return 2; +    } +  else if (AT91F_PDC_IsNextTxEmpty (pPDC)) +    { +      //* Only one buffer can be initialized +      AT91F_PDC_SetNextTx (pPDC, pBuffer, szBuffer); +      return 1; +    } +  else +    { +      //* All buffer are in use... +      return 0; +    } +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_ReceiveFrame +//* \brief Close PDC: disable TX and RX reset transfer descriptors +//*---------------------------------------------------------------------------- +unsigned int +AT91F_PDC_ReceiveFrame (AT91PS_PDC pPDC, +			unsigned char *pBuffer, +			unsigned int szBuffer, +			unsigned char *pNextBuffer, unsigned int szNextBuffer) +{ +  if (AT91F_PDC_IsRxEmpty (pPDC)) +    { +      //* Buffer and next buffer can be initialized +      AT91F_PDC_SetRx (pPDC, pBuffer, szBuffer); +      AT91F_PDC_SetNextRx (pPDC, pNextBuffer, szNextBuffer); +      return 2; +    } +  else if (AT91F_PDC_IsNextRxEmpty (pPDC)) +    { +      //* Only one buffer can be initialized +      AT91F_PDC_SetNextRx (pPDC, pBuffer, szBuffer); +      return 1; +    } +  else +    { +      //* All buffer are in use... +      return 0; +    } +} + +//*------------------------------------------------------------------------------ +//* \fn    AT91F_PMC_GetMasterClock +//* \brief Return master clock in Hz which correponds to processor clock for ARM7 +//*------------------------------------------------------------------------------ +unsigned int +AT91F_PMC_GetMasterClock (AT91PS_PMC pPMC,	// \arg pointer to PMC controller +			  AT91PS_CKGR pCKGR,	// \arg pointer to CKGR controller +			  unsigned int slowClock)	// \arg slowClock in Hz +{ +  unsigned int reg = pPMC->PMC_MCKR; +  unsigned int prescaler = (1 << ((reg & AT91C_PMC_PRES) >> 2)); +  unsigned int pllDivider, pllMultiplier; + +  switch (reg & AT91C_PMC_CSS) +    { +    case AT91C_PMC_CSS_SLOW_CLK:	// Slow clock selected +      return slowClock / prescaler; +    case AT91C_PMC_CSS_MAIN_CLK:	// Main clock is selected +      return AT91F_CKGR_GetMainClock (pCKGR, slowClock) / prescaler; +    case AT91C_PMC_CSS_PLL_CLK:	// PLLB clock is selected +      reg = pCKGR->CKGR_PLLR; +      pllDivider = (reg & AT91C_CKGR_DIV); +      pllMultiplier = ((reg & AT91C_CKGR_MUL) >> 16) + 1; +      return AT91F_CKGR_GetMainClock (pCKGR, +				      slowClock) / pllDivider * +	pllMultiplier / prescaler; +    } +  return 0; +} + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTT_ReadValue() +//* \brief  Read the RTT value +//*-------------------------------------------------------------------------------------- +unsigned int +AT91F_RTTReadValue (AT91PS_RTTC pRTTC) +{ +  register volatile unsigned int val1, val2; +  do +    { +      val1 = pRTTC->RTTC_RTVR; +      val2 = pRTTC->RTTC_RTVR; +    } +  while (val1 != val2); +  return (val1); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_Close +//* \brief Close SPI: disable IT disable transfert, close PDC +//*---------------------------------------------------------------------------- +void +AT91F_SPI_Close (AT91PS_SPI pSPI)	// \arg pointer to a SPI controller +{ +  //* Reset all the Chip Select register +  pSPI->SPI_CSR[0] = 0; +  pSPI->SPI_CSR[1] = 0; +  pSPI->SPI_CSR[2] = 0; +  pSPI->SPI_CSR[3] = 0; + +  //* Reset the SPI mode +  pSPI->SPI_MR = 0; + +  //* Disable all interrupts +  pSPI->SPI_IDR = 0xFFFFFFFF; + +  //* Abort the Peripheral Data Transfers +  AT91F_PDC_Close ((AT91PS_PDC) & (pSPI->SPI_RPR)); + +  //* Disable receiver and transmitter and stop any activity immediately +  pSPI->SPI_CR = AT91C_SPI_SPIDIS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_CfgTimings +//* \brief Configure the different necessary timings of the ADC controller +//*---------------------------------------------------------------------------- +void +AT91F_ADC_CfgTimings (AT91PS_ADC pADC,	// pointer to a ADC controller +		      unsigned int mck_clock,	// in MHz  +		      unsigned int adc_clock,	// in MHz  +		      unsigned int startup_time,	// in us  +		      unsigned int sample_and_hold_time)	// in ns   +{ +  unsigned int prescal, startup, shtim; + +  prescal = mck_clock / (2 * adc_clock) - 1; +  startup = adc_clock * startup_time / 8 - 1; +  shtim = adc_clock * sample_and_hold_time / 1000 - 1; + +  //* Write to the MR register +  pADC->ADC_MR = +    ((prescal << 8) & AT91C_ADC_PRESCAL) | ((startup << 16) & +					    AT91C_ADC_STARTUP) | ((shtim << +								   24) & +								  AT91C_ADC_SHTIM); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_SetBaudrate +//* \brief Set the baudrate according to the CPU clock +//*---------------------------------------------------------------------------- +void +AT91F_SSC_SetBaudrate (AT91PS_SSC pSSC,	// \arg pointer to a SSC controller +		       unsigned int mainClock,	// \arg peripheral clock +		       unsigned int speed)	// \arg SSC baudrate +{ +  unsigned int baud_value; +  //* Define the baud rate divisor register +  if (speed == 0) +    baud_value = 0; +  else +    { +      baud_value = (unsigned int) (mainClock * 10) / (2 * speed); +      if ((baud_value % 10) >= 5) +	baud_value = (baud_value / 10) + 1; +      else +	baud_value /= 10; +    } + +  pSSC->SSC_CMR = baud_value; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_Configure +//* \brief Configure SSC +//*---------------------------------------------------------------------------- +void +AT91F_SSC_Configure (AT91PS_SSC pSSC,	// \arg pointer to a SSC controller +		     unsigned int syst_clock,	// \arg System Clock Frequency +		     unsigned int baud_rate,	// \arg Expected Baud Rate Frequency +		     unsigned int clock_rx,	// \arg Receiver Clock Parameters +		     unsigned int mode_rx,	// \arg mode Register to be programmed +		     unsigned int clock_tx,	// \arg Transmitter Clock Parameters +		     unsigned int mode_tx)	// \arg mode Register to be programmed +{ +  //* Disable interrupts +  pSSC->SSC_IDR = (unsigned int) -1; + +  //* Reset receiver and transmitter +  pSSC->SSC_CR = AT91C_SSC_SWRST | AT91C_SSC_RXDIS | AT91C_SSC_TXDIS; + +  //* Define the Clock Mode Register +  AT91F_SSC_SetBaudrate (pSSC, syst_clock, baud_rate); + +  //* Write the Receive Clock Mode Register +  pSSC->SSC_RCMR = clock_rx; + +  //* Write the Transmit Clock Mode Register +  pSSC->SSC_TCMR = clock_tx; + +  //* Write the Receive Frame Mode Register +  pSSC->SSC_RFMR = mode_rx; + +  //* Write the Transmit Frame Mode Register +  pSSC->SSC_TFMR = mode_tx; + +  //* Clear Transmit and Receive Counters +  AT91F_PDC_Open ((AT91PS_PDC) & (pSSC->SSC_RPR)); + + +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_Configure +//* \brief Configure USART +//*---------------------------------------------------------------------------- +void +AT91F_US_Configure (AT91PS_USART pUSART,	// \arg pointer to a USART controller +		    unsigned int mainClock,	// \arg peripheral clock +		    unsigned int mode,	// \arg mode Register to be programmed +		    unsigned int baudRate,	// \arg baudrate to be programmed +		    unsigned int timeguard)	// \arg timeguard to be programmed +{ +  //* Disable interrupts +  pUSART->US_IDR = (unsigned int) -1; + +  //* Reset receiver and transmitter +  pUSART->US_CR = +    AT91C_US_RSTRX | AT91C_US_RSTTX | AT91C_US_RXDIS | AT91C_US_TXDIS; + +  //* Define the baud rate divisor register +  AT91F_US_SetBaudrate (pUSART, mainClock, baudRate); + +  //* Write the Timeguard Register +  AT91F_US_SetTimeguard (pUSART, timeguard); + +  //* Clear Transmit and Receive Counters +  AT91F_PDC_Open ((AT91PS_PDC) & (pUSART->US_RPR)); + +  //* Define the USART mode +  pUSART->US_MR = mode; + +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_Close +//* \brief Close USART: disable IT disable receiver and transmitter, close PDC +//*---------------------------------------------------------------------------- +void +AT91F_US_Close (AT91PS_USART pUSART)	// \arg pointer to a USART controller +{ +  //* Reset the baud rate divisor register +  pUSART->US_BRGR = 0; + +  //* Reset the USART mode +  pUSART->US_MR = 0; + +  //* Reset the Timeguard Register +  pUSART->US_TTGR = 0; + +  //* Disable all interrupts +  pUSART->US_IDR = 0xFFFFFFFF; + +  //* Abort the Peripheral Data Transfers +  AT91F_PDC_Close ((AT91PS_PDC) & (pUSART->US_RPR)); + +  //* Disable receiver and transmitter and stop any activity immediately +  pUSART->US_CR = +    AT91C_US_TXDIS | AT91C_US_RXDIS | AT91C_US_RSTTX | AT91C_US_RSTRX; +} diff --git a/openpicc/os/core/ARM7_AT91SAM7S/lib_AT91SAM7.h b/openpicc/os/core/ARM7_AT91SAM7S/lib_AT91SAM7.h new file mode 100644 index 0000000..4f58088 --- /dev/null +++ b/openpicc/os/core/ARM7_AT91SAM7S/lib_AT91SAM7.h @@ -0,0 +1,3417 @@ +//* ---------------------------------------------------------------------------- +//*         ATMEL Microcontroller Software Support  -  ROUSSET  - +//* ---------------------------------------------------------------------------- +//* DISCLAIMER:  THIS SOFTWARE IS PROVIDED BY ATMEL "AS IS" AND ANY EXPRESS OR +//* IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED WARRANTIES OF +//* MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NON-INFRINGEMENT ARE +//* DISCLAIMED. IN NO EVENT SHALL ATMEL BE LIABLE FOR ANY DIRECT, INDIRECT, +//* INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT +//* LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, +//* OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY OF +//* LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT (INCLUDING +//* NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS SOFTWARE, +//* EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. +//* ---------------------------------------------------------------------------- +//* File Name           : lib_AT91SAM7S64.h +//* Object              : AT91SAM7S64 inlined functions +//* Generated           : AT91 SW Application Group  08/30/2005 (15:52:59) +//* +//* CVS Reference       : /lib_dbgu.h/1.1/Thu Aug 25 12:56:22 2005// +//* CVS Reference       : /lib_pmc_SAM7S.h/1.4/Tue Aug 30 13:00:43 2005// +//* CVS Reference       : /lib_VREG_6085B.h/1.1/Tue Feb  1 16:20:47 2005// +//* CVS Reference       : /lib_rstc_6098A.h/1.1/Wed Oct  6 10:39:20 2004// +//* CVS Reference       : /lib_ssc.h/1.4/Fri Jan 31 12:19:20 2003// +//* CVS Reference       : /lib_wdtc_6080A.h/1.1/Wed Oct  6 10:38:30 2004// +//* CVS Reference       : /lib_usart.h/1.5/Thu Nov 21 16:01:54 2002// +//* CVS Reference       : /lib_spi2.h/1.2/Tue Aug 23 15:37:28 2005// +//* CVS Reference       : /lib_pitc_6079A.h/1.2/Tue Nov  9 14:43:56 2004// +//* CVS Reference       : /lib_aic_6075b.h/1.2/Thu Jul  7 07:48:22 2005// +//* CVS Reference       : /lib_twi.h/1.3/Mon Jul 19 14:27:58 2004// +//* CVS Reference       : /lib_adc.h/1.6/Fri Oct 17 09:12:38 2003// +//* CVS Reference       : /lib_rttc_6081A.h/1.1/Wed Oct  6 10:39:38 2004// +//* CVS Reference       : /lib_udp.h/1.5/Tue Aug 30 12:13:47 2005// +//* CVS Reference       : /lib_tc_1753b.h/1.1/Fri Jan 31 12:20:02 2003// +//* CVS Reference       : /lib_MC_SAM7S.h/1.1/Thu Mar 25 15:19:14 2004// +//* CVS Reference       : /lib_pio.h/1.3/Fri Jan 31 12:18:56 2003// +//* CVS Reference       : /lib_PWM_SAM.h/1.3/Thu Jan 22 10:10:50 2004// +//* CVS Reference       : /lib_pdc.h/1.2/Tue Jul  2 13:29:40 2002// +//* ---------------------------------------------------------------------------- + +#ifndef lib_AT91SAM7_H +#define lib_AT91SAM7_H + +#include <AT91SAM7.h> + +typedef void (*THandler) (void); + +/* ***************************************************************************** +                SOFTWARE API FOR AIC +   ***************************************************************************** */ +#define AT91C_AIC_BRANCH_OPCODE ((void (*) ()) 0xE51FFF20)	// ldr, pc, [pc, #-&F20] + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_ConfigureIt +//* \brief Interrupt Handler Initialization +//*---------------------------------------------------------------------------- +extern unsigned int AT91F_AIC_ConfigureIt (unsigned int irq_id,	// \arg interrupt number to initialize +					   unsigned int priority,	// \arg priority to give to the interrupt +					   unsigned int src_type,	// \arg activation and sense of activation +					   THandler handler);	// \arg address of the interrupt handler + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_EnableIt +//* \brief Enable corresponding IT number +//*---------------------------------------------------------------------------- +static inline void +AT91F_AIC_EnableIt (unsigned int irq_id)	// \arg interrupt number to initialize +{ +  //* Enable the interrupt on the interrupt controller +  AT91C_BASE_AIC->AIC_IECR = 0x1 << irq_id; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_DisableIt +//* \brief Disable corresponding IT number +//*---------------------------------------------------------------------------- +static inline void +AT91F_AIC_DisableIt (unsigned int irq_id)	// \arg interrupt number to initialize +{ +  unsigned int mask = 0x1 << irq_id; +  //* Disable the interrupt on the interrupt controller +  AT91C_BASE_AIC->AIC_IDCR = mask; +  //* Clear the interrupt on the Interrupt Controller ( if one is pending ) +  AT91C_BASE_AIC->AIC_ICCR = mask; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_ClearIt +//* \brief Clear corresponding IT number +//*---------------------------------------------------------------------------- +static inline void +AT91F_AIC_ClearIt (unsigned int irq_id)	// \arg interrupt number to initialize +{ +  //* Clear the interrupt on the Interrupt Controller ( if one is pending ) +  AT91C_BASE_AIC->AIC_ICCR = (0x1 << irq_id); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_AcknowledgeIt +//* \brief Acknowledge corresponding IT number +//*---------------------------------------------------------------------------- +static inline void +AT91F_AIC_AcknowledgeIt (void) +{ +  AT91C_BASE_AIC->AIC_EOICR = AT91C_BASE_AIC->AIC_EOICR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_SetExceptionVector +//* \brief Configure vector handler +//*---------------------------------------------------------------------------- +extern unsigned int AT91F_AIC_SetExceptionVector (unsigned int *pVector,	// \arg pointer to the AIC registers +						  THandler Handler);	// \arg Interrupt Handler + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_Trig +//* \brief Trig an IT +//*---------------------------------------------------------------------------- +static inline void +AT91F_AIC_Trig (AT91PS_AIC pAic,	// \arg pointer to the AIC registers +		unsigned int irq_id)	// \arg interrupt number +{ +  pAic->AIC_ISCR = (0x1 << irq_id); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_IsActive +//* \brief Test if an IT is active +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_AIC_IsActive (AT91PS_AIC pAic,	// \arg pointer to the AIC registers +		    unsigned int irq_id)	// \arg Interrupt Number +{ +  return (pAic->AIC_ISR & (0x1 << irq_id)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_IsPending +//* \brief Test if an IT is pending +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_AIC_IsPending (AT91PS_AIC pAic,	// \arg pointer to the AIC registers +		     unsigned int irq_id)	// \arg Interrupt Number +{ +  return (pAic->AIC_IPR & (0x1 << irq_id)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_Open +//* \brief Set exception vectors and AIC registers to default values +//*---------------------------------------------------------------------------- +extern void AT91F_AIC_Open (THandler IrqHandler,	// \arg Default IRQ vector exception +			    THandler FiqHandler,	// \arg Default FIQ vector exception +			    THandler DefaultHandler,	// \arg Default Handler set in ISR +			    THandler SpuriousHandler,	// \arg Default Spurious Handler +			    unsigned int protectMode);	// \arg Debug Control Register + +/* ***************************************************************************** +                SOFTWARE API FOR PDC +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_SetNextRx +//* \brief Set the next receive transfer descriptor +//*---------------------------------------------------------------------------- +static inline void +AT91F_PDC_SetNextRx (AT91PS_PDC pPDC,	// \arg pointer to a PDC controller +		     unsigned char *address,	// \arg address to the next bloc to be received +		     unsigned int bytes)	// \arg number of bytes to be received +{ +  pPDC->PDC_RNPR = (unsigned int) address; +  pPDC->PDC_RNCR = bytes; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_SetNextTx +//* \brief Set the next transmit transfer descriptor +//*---------------------------------------------------------------------------- +static inline void +AT91F_PDC_SetNextTx (AT91PS_PDC pPDC,	// \arg pointer to a PDC controller +		     const unsigned char *address,	// \arg address to the next bloc to be transmitted +		     unsigned int bytes)	// \arg number of bytes to be transmitted +{ +  pPDC->PDC_TNPR = (unsigned int) address; +  pPDC->PDC_TNCR = bytes; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_SetRx +//* \brief Set the receive transfer descriptor +//*---------------------------------------------------------------------------- +static inline void +AT91F_PDC_SetRx (AT91PS_PDC pPDC,	// \arg pointer to a PDC controller +		 unsigned char *address,	// \arg address to the next bloc to be received +		 unsigned int bytes)	// \arg number of bytes to be received +{ +  pPDC->PDC_RPR = (unsigned int) address; +  pPDC->PDC_RCR = bytes; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_SetTx +//* \brief Set the transmit transfer descriptor +//*---------------------------------------------------------------------------- +static inline void +AT91F_PDC_SetTx (AT91PS_PDC pPDC,	// \arg pointer to a PDC controller +		 const unsigned char *address,	// \arg address to the next bloc to be transmitted +		 unsigned int bytes)	// \arg number of bytes to be transmitted +{ +  pPDC->PDC_TPR = (unsigned int) address; +  pPDC->PDC_TCR = bytes; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_EnableTx +//* \brief Enable transmit +//*---------------------------------------------------------------------------- +static inline void +AT91F_PDC_EnableTx (AT91PS_PDC pPDC)	// \arg pointer to a PDC controller +{ +  pPDC->PDC_PTCR = AT91C_PDC_TXTEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_EnableRx +//* \brief Enable receive +//*---------------------------------------------------------------------------- +static inline void +AT91F_PDC_EnableRx (AT91PS_PDC pPDC)	// \arg pointer to a PDC controller +{ +  pPDC->PDC_PTCR = AT91C_PDC_RXTEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_DisableTx +//* \brief Disable transmit +//*---------------------------------------------------------------------------- +static inline void +AT91F_PDC_DisableTx (AT91PS_PDC pPDC)	// \arg pointer to a PDC controller +{ +  pPDC->PDC_PTCR = AT91C_PDC_TXTDIS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_DisableRx +//* \brief Disable receive +//*---------------------------------------------------------------------------- +static inline void +AT91F_PDC_DisableRx (AT91PS_PDC pPDC)	// \arg pointer to a PDC controller +{ +  pPDC->PDC_PTCR = AT91C_PDC_RXTDIS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_IsTxEmpty +//* \brief Test if the current transfer descriptor has been sent +//*---------------------------------------------------------------------------- +static inline int +AT91F_PDC_IsTxEmpty (		// \return return 1 if transfer is complete +		      AT91PS_PDC pPDC)	// \arg pointer to a PDC controller +{ +  return !(pPDC->PDC_TCR); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_IsNextTxEmpty +//* \brief Test if the next transfer descriptor has been moved to the current td +//*---------------------------------------------------------------------------- +static inline int +AT91F_PDC_IsNextTxEmpty (	// \return return 1 if transfer is complete +			  AT91PS_PDC pPDC)	// \arg pointer to a PDC controller +{ +  return !(pPDC->PDC_TNCR); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_IsRxEmpty +//* \brief Test if the current transfer descriptor has been filled +//*---------------------------------------------------------------------------- +static inline int +AT91F_PDC_IsRxEmpty (		// \return return 1 if transfer is complete +		      AT91PS_PDC pPDC)	// \arg pointer to a PDC controller +{ +  return !(pPDC->PDC_RCR); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_IsNextRxEmpty +//* \brief Test if the next transfer descriptor has been moved to the current td +//*---------------------------------------------------------------------------- +static inline int +AT91F_PDC_IsNextRxEmpty (	// \return return 1 if transfer is complete +			  AT91PS_PDC pPDC)	// \arg pointer to a PDC controller +{ +  return !(pPDC->PDC_RNCR); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_Open +//* \brief Open PDC: disable TX and RX reset transfer descriptors, re-enable RX and TX +//*---------------------------------------------------------------------------- +extern void AT91F_PDC_Open (AT91PS_PDC pPDC);	// \arg pointer to a PDC controller + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_Close +//* \brief Close PDC: disable TX and RX reset transfer descriptors +//*---------------------------------------------------------------------------- +extern void AT91F_PDC_Close (AT91PS_PDC pPDC);	// \arg pointer to a PDC controller + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_SendFrame +//* \brief Close PDC: disable TX and RX reset transfer descriptors +//*---------------------------------------------------------------------------- +extern unsigned int AT91F_PDC_SendFrame (AT91PS_PDC pPDC, +					 const unsigned char *pBuffer, +					 unsigned int szBuffer, +					 const unsigned char *pNextBuffer, +					 unsigned int szNextBuffer); + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PDC_ReceiveFrame +//* \brief Close PDC: disable TX and RX reset transfer descriptors +//*---------------------------------------------------------------------------- +extern unsigned int AT91F_PDC_ReceiveFrame (AT91PS_PDC pPDC, +					    unsigned char *pBuffer, +					    unsigned int szBuffer, +					    unsigned char *pNextBuffer, +					    unsigned int szNextBuffer); + +/* ***************************************************************************** +                SOFTWARE API FOR DBGU +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_DBGU_InterruptEnable +//* \brief Enable DBGU Interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_DBGU_InterruptEnable (AT91PS_DBGU pDbgu,	// \arg  pointer to a DBGU controller +			    unsigned int flag)	// \arg  dbgu interrupt to be enabled +{ +  pDbgu->DBGU_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_DBGU_InterruptDisable +//* \brief Disable DBGU Interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_DBGU_InterruptDisable (AT91PS_DBGU pDbgu,	// \arg  pointer to a DBGU controller +			     unsigned int flag)	// \arg  dbgu interrupt to be disabled +{ +  pDbgu->DBGU_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_DBGU_GetInterruptMaskStatus +//* \brief Return DBGU Interrupt Mask Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_DBGU_GetInterruptMaskStatus (	// \return DBGU Interrupt Mask Status +				    AT91PS_DBGU pDbgu)	// \arg  pointer to a DBGU controller +{ +  return pDbgu->DBGU_IMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_DBGU_IsInterruptMasked +//* \brief Test if DBGU Interrupt is Masked  +//*---------------------------------------------------------------------------- +static inline int +AT91F_DBGU_IsInterruptMasked (AT91PS_DBGU pDbgu,	// \arg  pointer to a DBGU controller +			      unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_DBGU_GetInterruptMaskStatus (pDbgu) & flag); +} + +/* ***************************************************************************** +                SOFTWARE API FOR PIO +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_CfgPeriph +//* \brief Enable pins to be drived by peripheral +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_CfgPeriph (AT91PS_PIO pPio,	// \arg pointer to a PIO controller +		     unsigned int periphAEnable,	// \arg PERIPH A to enable +		     unsigned int periphBEnable)	// \arg PERIPH B to enable +{ +  pPio->PIO_ASR = periphAEnable; +  pPio->PIO_BSR = periphBEnable; +  pPio->PIO_PDR = (periphAEnable | periphBEnable);	// Set in Periph mode +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_CfgOutput +//* \brief Enable PIO in output mode +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_CfgOutput (AT91PS_PIO pPio,	// \arg pointer to a PIO controller +		     unsigned int pioEnable)	// \arg PIO to be enabled +{ +  pPio->PIO_PER = pioEnable;	// Set in PIO mode +  pPio->PIO_OER = pioEnable;	// Configure in Output +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_CfgInput +//* \brief Enable PIO in input mode +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_CfgInput (AT91PS_PIO pPio,	// \arg pointer to a PIO controller +		    unsigned int inputEnable)	// \arg PIO to be enabled +{ +  // Disable output +  pPio->PIO_ODR = inputEnable; +  pPio->PIO_PER = inputEnable; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_CfgOpendrain +//* \brief Configure PIO in open drain +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_CfgOpendrain (AT91PS_PIO pPio,	// \arg pointer to a PIO controller +			unsigned int multiDrvEnable)	// \arg pio to be configured in open drain +{ +  // Configure the multi-drive option +  pPio->PIO_MDDR = ~multiDrvEnable; +  pPio->PIO_MDER = multiDrvEnable; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_CfgPullup +//* \brief Enable pullup on PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_CfgPullup (AT91PS_PIO pPio,	// \arg pointer to a PIO controller +		     unsigned int pullupEnable)	// \arg enable pullup on PIO +{ +  // Connect or not Pullup +  pPio->PIO_PPUDR = ~pullupEnable; +  pPio->PIO_PPUER = pullupEnable; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_CfgDirectDrive +//* \brief Enable direct drive on PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_CfgDirectDrive (AT91PS_PIO pPio,	// \arg pointer to a PIO controller +			  unsigned int directDrive)	// \arg PIO to be configured with direct drive +{ +  // Configure the Direct Drive +  pPio->PIO_OWDR = ~directDrive; +  pPio->PIO_OWER = directDrive; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_CfgInputFilter +//* \brief Enable input filter on input PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_CfgInputFilter (AT91PS_PIO pPio,	// \arg pointer to a PIO controller +			  unsigned int inputFilter)	// \arg PIO to be configured with input filter +{ +  // Configure the Direct Drive +  pPio->PIO_IFDR = ~inputFilter; +  pPio->PIO_IFER = inputFilter; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_GetInput +//* \brief Return PIO input value +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_GetInput (		// \return PIO input +		     AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_PDSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsInputSet +//* \brief Test if PIO is input flag is active +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsInputSet (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +		      unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PIO_GetInput (pPio) & flag); +} + + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_SetOutput +//* \brief Set to 1 output PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_SetOutput (const AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +		     const unsigned int flag)	// \arg  output to be set +{ +  pPio->PIO_SODR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_ClearOutput +//* \brief Set to 0 output PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_ClearOutput (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +		       unsigned int flag)	// \arg  output to be cleared +{ +  pPio->PIO_CODR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_ForceOutput +//* \brief Force output when Direct drive option is enabled +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_ForceOutput (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +		       unsigned int flag)	// \arg  output to be forced +{ +  pPio->PIO_ODSR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_Enable +//* \brief Enable PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_Enable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +		  unsigned int flag)	// \arg  pio to be enabled  +{ +  pPio->PIO_PER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_Disable +//* \brief Disable PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_Disable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +		   unsigned int flag)	// \arg  pio to be disabled  +{ +  pPio->PIO_PDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_GetStatus +//* \brief Return PIO Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_GetStatus (		// \return PIO Status +		      AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_PSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsSet +//* \brief Test if PIO is Set +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsSet (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +		 unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PIO_GetStatus (pPio) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_OutputEnable +//* \brief Output Enable PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_OutputEnable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			unsigned int flag)	// \arg  pio output to be enabled +{ +  pPio->PIO_OER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_OutputDisable +//* \brief Output Enable PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_OutputDisable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			 unsigned int flag)	// \arg  pio output to be disabled +{ +  pPio->PIO_ODR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_GetOutputStatus +//* \brief Return PIO Output Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_GetOutputStatus (	// \return PIO Output Status +			    AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_OSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsOuputSet +//* \brief Test if PIO Output is Set +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsOutputSet (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +		       unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PIO_GetOutputStatus (pPio) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_InputFilterEnable +//* \brief Input Filter Enable PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_InputFilterEnable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			     unsigned int flag)	// \arg  pio input filter to be enabled +{ +  pPio->PIO_IFER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_InputFilterDisable +//* \brief Input Filter Disable PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_InputFilterDisable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			      unsigned int flag)	// \arg  pio input filter to be disabled +{ +  pPio->PIO_IFDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_GetInputFilterStatus +//* \brief Return PIO Input Filter Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_GetInputFilterStatus (	// \return PIO Input Filter Status +				 AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_IFSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsInputFilterSet +//* \brief Test if PIO Input filter is Set +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsInputFilterSet (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			    unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PIO_GetInputFilterStatus (pPio) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_GetOutputDataStatus +//* \brief Return PIO Output Data Status  +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_GetOutputDataStatus (	// \return PIO Output Data Status  +				AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_ODSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_InterruptEnable +//* \brief Enable PIO Interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_InterruptEnable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			   unsigned int flag)	// \arg  pio interrupt to be enabled +{ +  pPio->PIO_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_InterruptDisable +//* \brief Disable PIO Interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_InterruptDisable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			    unsigned int flag)	// \arg  pio interrupt to be disabled +{ +  pPio->PIO_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_GetInterruptMaskStatus +//* \brief Return PIO Interrupt Mask Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_GetInterruptMaskStatus (	// \return PIO Interrupt Mask Status +				   AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_IMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_GetInterruptStatus +//* \brief Return PIO Interrupt Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_GetInterruptStatus (	// \return PIO Interrupt Status +			       AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_ISR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsInterruptMasked +//* \brief Test if PIO Interrupt is Masked  +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsInterruptMasked (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			     unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PIO_GetInterruptMaskStatus (pPio) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsInterruptSet +//* \brief Test if PIO Interrupt is Set +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsInterruptSet (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			  unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PIO_GetInterruptStatus (pPio) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_MultiDriverEnable +//* \brief Multi Driver Enable PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_MultiDriverEnable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			     unsigned int flag)	// \arg  pio to be enabled +{ +  pPio->PIO_MDER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_MultiDriverDisable +//* \brief Multi Driver Disable PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_MultiDriverDisable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			      unsigned int flag)	// \arg  pio to be disabled +{ +  pPio->PIO_MDDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_GetMultiDriverStatus +//* \brief Return PIO Multi Driver Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_GetMultiDriverStatus (	// \return PIO Multi Driver Status +				 AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_MDSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsMultiDriverSet +//* \brief Test if PIO MultiDriver is Set +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsMultiDriverSet (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			    unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PIO_GetMultiDriverStatus (pPio) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_A_RegisterSelection +//* \brief PIO A Register Selection  +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_A_RegisterSelection (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			       unsigned int flag)	// \arg  pio A register selection +{ +  pPio->PIO_ASR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_B_RegisterSelection +//* \brief PIO B Register Selection  +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_B_RegisterSelection (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			       unsigned int flag)	// \arg  pio B register selection  +{ +  pPio->PIO_BSR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_Get_AB_RegisterStatus +//* \brief Return PIO Interrupt Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_Get_AB_RegisterStatus (	// \return PIO AB Register Status +				  AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_ABSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsAB_RegisterSet +//* \brief Test if PIO AB Register is Set +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsAB_RegisterSet (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			    unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PIO_Get_AB_RegisterStatus (pPio) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_OutputWriteEnable +//* \brief Output Write Enable PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_OutputWriteEnable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			     unsigned int flag)	// \arg  pio output write to be enabled +{ +  pPio->PIO_OWER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_OutputWriteDisable +//* \brief Output Write Disable PIO +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIO_OutputWriteDisable (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			      unsigned int flag)	// \arg  pio output write to be disabled +{ +  pPio->PIO_OWDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_GetOutputWriteStatus +//* \brief Return PIO Output Write Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_GetOutputWriteStatus (	// \return PIO Output Write Status +				 AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_OWSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsOutputWriteSet +//* \brief Test if PIO OutputWrite is Set +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsOutputWriteSet (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +			    unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PIO_GetOutputWriteStatus (pPio) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_GetCfgPullup +//* \brief Return PIO Configuration Pullup +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PIO_GetCfgPullup (	// \return PIO Configuration Pullup  +			 AT91PS_PIO pPio)	// \arg  pointer to a PIO controller +{ +  return pPio->PIO_PPUSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsOutputDataStatusSet +//* \brief Test if PIO Output Data Status is Set  +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsOutputDataStatusSet (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +				 unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PIO_GetOutputDataStatus (pPio) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIO_IsCfgPullupStatusSet +//* \brief Test if PIO Configuration Pullup Status is Set +//*---------------------------------------------------------------------------- +static inline int +AT91F_PIO_IsCfgPullupStatusSet (AT91PS_PIO pPio,	// \arg  pointer to a PIO controller +				unsigned int flag)	// \arg  flag to be tested +{ +  return (~AT91F_PIO_GetCfgPullup (pPio) & flag); +} + +/* ***************************************************************************** +                SOFTWARE API FOR PMC +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_CfgSysClkEnableReg +//* \brief Configure the System Clock Enable Register of the PMC controller +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_CfgSysClkEnableReg (AT91PS_PMC pPMC,	// \arg pointer to PMC controller +			      unsigned int mode) +{ +  //* Write to the SCER register +  pPMC->PMC_SCER = mode; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_CfgSysClkDisableReg +//* \brief Configure the System Clock Disable Register of the PMC controller +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_CfgSysClkDisableReg (AT91PS_PMC pPMC,	// \arg pointer to PMC controller +			       unsigned int mode) +{ +  //* Write to the SCDR register +  pPMC->PMC_SCDR = mode; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_GetSysClkStatusReg +//* \brief Return the System Clock Status Register of the PMC controller +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PMC_GetSysClkStatusReg (AT91PS_PMC pPMC	// pointer to a CAN controller +  ) +{ +  return pPMC->PMC_SCSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_EnablePeriphClock +//* \brief Enable peripheral clock +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_EnablePeriphClock (AT91PS_PMC pPMC,	// \arg pointer to PMC controller +			     unsigned int periphIds)	// \arg IDs of peripherals to enable +{ +  pPMC->PMC_PCER = periphIds; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_DisablePeriphClock +//* \brief Disable peripheral clock +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_DisablePeriphClock (AT91PS_PMC pPMC,	// \arg pointer to PMC controller +			      unsigned int periphIds)	// \arg IDs of peripherals to enable +{ +  pPMC->PMC_PCDR = periphIds; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_GetPeriphClock +//* \brief Get peripheral clock status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PMC_GetPeriphClock (AT91PS_PMC pPMC)	// \arg pointer to PMC controller +{ +  return pPMC->PMC_PCSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_CKGR_CfgMainOscillatorReg +//* \brief Cfg the main oscillator +//*---------------------------------------------------------------------------- +static inline void +AT91F_CKGR_CfgMainOscillatorReg (AT91PS_CKGR pCKGR,	// \arg pointer to CKGR controller +				 unsigned int mode) +{ +  pCKGR->CKGR_MOR = mode; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_CKGR_GetMainOscillatorReg +//* \brief Cfg the main oscillator +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_CKGR_GetMainOscillatorReg (AT91PS_CKGR pCKGR)	// \arg pointer to CKGR controller +{ +  return pCKGR->CKGR_MOR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_CKGR_EnableMainOscillator +//* \brief Enable the main oscillator +//*---------------------------------------------------------------------------- +static inline void +AT91F_CKGR_EnableMainOscillator (AT91PS_CKGR pCKGR)	// \arg pointer to CKGR controller +{ +  pCKGR->CKGR_MOR |= AT91C_CKGR_MOSCEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_CKGR_DisableMainOscillator +//* \brief Disable the main oscillator +//*---------------------------------------------------------------------------- +static inline void +AT91F_CKGR_DisableMainOscillator (AT91PS_CKGR pCKGR)	// \arg pointer to CKGR controller +{ +  pCKGR->CKGR_MOR &= ~AT91C_CKGR_MOSCEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_CKGR_CfgMainOscStartUpTime +//* \brief Cfg MOR Register according to the main osc startup time +//*---------------------------------------------------------------------------- +static inline void +AT91F_CKGR_CfgMainOscStartUpTime (AT91PS_CKGR pCKGR,	// \arg pointer to CKGR controller +				  unsigned int startup_time,	// \arg main osc startup time in microsecond (us) +				  unsigned int slowClock)	// \arg slowClock in Hz +{ +  pCKGR->CKGR_MOR &= ~AT91C_CKGR_OSCOUNT; +  pCKGR->CKGR_MOR |= ((slowClock * startup_time) / (8 * 1000000)) << 8; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_CKGR_GetMainClockFreqReg +//* \brief Cfg the main oscillator +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_CKGR_GetMainClockFreqReg (AT91PS_CKGR pCKGR)	// \arg pointer to CKGR controller +{ +  return pCKGR->CKGR_MCFR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_CKGR_GetMainClock +//* \brief Return Main clock in Hz +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_CKGR_GetMainClock (AT91PS_CKGR pCKGR,	// \arg pointer to CKGR controller +			 unsigned int slowClock)	// \arg slowClock in Hz +{ +  return ((pCKGR->CKGR_MCFR & AT91C_CKGR_MAINF) * slowClock) >> 4; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_CfgMCKReg +//* \brief Cfg Master Clock Register +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_CfgMCKReg (AT91PS_PMC pPMC,	// \arg pointer to PMC controller +		     unsigned int mode) +{ +  pPMC->PMC_MCKR = mode; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_GetMCKReg +//* \brief Return Master Clock Register +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PMC_GetMCKReg (AT91PS_PMC pPMC)	// \arg pointer to PMC controller +{ +  return pPMC->PMC_MCKR; +} + +//*------------------------------------------------------------------------------ +//* \fn    AT91F_PMC_GetMasterClock +//* \brief Return master clock in Hz which correponds to processor clock for ARM7 +//*------------------------------------------------------------------------------ +extern unsigned int AT91F_PMC_GetMasterClock (AT91PS_PMC pPMC,	// \arg pointer to PMC controller +					      AT91PS_CKGR pCKGR,	// \arg pointer to CKGR controller +					      unsigned int slowClock);	// \arg slowClock in Hz + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_EnablePCK +//* \brief Enable peripheral clock +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_EnablePCK (AT91PS_PMC pPMC,	// \arg pointer to PMC controller +		     unsigned int pck,	// \arg Peripheral clock identifier 0 .. 7 +		     unsigned int mode) +{ +  pPMC->PMC_PCKR[pck] = mode; +  pPMC->PMC_SCER = (1 << pck) << 8; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_DisablePCK +//* \brief Enable peripheral clock +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_DisablePCK (AT91PS_PMC pPMC,	// \arg pointer to PMC controller +		      unsigned int pck)	// \arg Peripheral clock identifier 0 .. 7 +{ +  pPMC->PMC_SCDR = (1 << pck) << 8; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_EnableIt +//* \brief Enable PMC interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_EnableIt (AT91PS_PMC pPMC,	// pointer to a PMC controller +		    unsigned int flag)	// IT to be enabled +{ +  //* Write to the IER register +  pPMC->PMC_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_DisableIt +//* \brief Disable PMC interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_DisableIt (AT91PS_PMC pPMC,	// pointer to a PMC controller +		     unsigned int flag)	// IT to be disabled +{ +  //* Write to the IDR register +  pPMC->PMC_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_GetStatus +//* \brief Return PMC Interrupt Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PMC_GetStatus (		// \return PMC Interrupt Status +		      AT91PS_PMC pPMC)	// pointer to a PMC controller +{ +  return pPMC->PMC_SR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_GetInterruptMaskStatus +//* \brief Return PMC Interrupt Mask Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PMC_GetInterruptMaskStatus (	// \return PMC Interrupt Mask Status +				   AT91PS_PMC pPMC)	// pointer to a PMC controller +{ +  return pPMC->PMC_IMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_IsInterruptMasked +//* \brief Test if PMC Interrupt is Masked +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PMC_IsInterruptMasked (AT91PS_PMC pPMC,	// \arg  pointer to a PMC controller +			     unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PMC_GetInterruptMaskStatus (pPMC) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_IsStatusSet +//* \brief Test if PMC Status is Set +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PMC_IsStatusSet (AT91PS_PMC pPMC,	// \arg  pointer to a PMC controller +		       unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PMC_GetStatus (pPMC) & flag); +} + +// ---------------------------------------------------------------------------- +//  \fn    AT91F_CKGR_CfgPLLReg +//  \brief Cfg the PLL Register +// ---------------------------------------------------------------------------- +static inline void +AT91F_CKGR_CfgPLLReg (AT91PS_CKGR pCKGR,	// \arg pointer to CKGR controller +		      unsigned int mode) +{ +  pCKGR->CKGR_PLLR = mode; +} + +// ---------------------------------------------------------------------------- +//  \fn    AT91F_CKGR_GetPLLReg +//  \brief Get the PLL Register +// ---------------------------------------------------------------------------- +static inline unsigned int +AT91F_CKGR_GetPLLReg (AT91PS_CKGR pCKGR)	// \arg pointer to CKGR controller +{ +  return pCKGR->CKGR_PLLR; +} + + + +/* ***************************************************************************** +                SOFTWARE API FOR RSTC +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_RSTSoftReset +//* \brief Start Software Reset +//*---------------------------------------------------------------------------- +static inline void +AT91F_RSTSoftReset (AT91PS_RSTC pRSTC, unsigned int reset) +{ +  pRSTC->RSTC_RCR = (0xA5000000 | reset); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_RSTSetMode +//* \brief Set Reset Mode +//*---------------------------------------------------------------------------- +static inline void +AT91F_RSTSetMode (AT91PS_RSTC pRSTC, unsigned int mode) +{ +  pRSTC->RSTC_RMR = (0xA5000000 | mode); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_RSTGetMode +//* \brief Get Reset Mode +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_RSTGetMode (AT91PS_RSTC pRSTC) +{ +  return (pRSTC->RSTC_RMR); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_RSTGetStatus +//* \brief Get Reset Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_RSTGetStatus (AT91PS_RSTC pRSTC) +{ +  return (pRSTC->RSTC_RSR); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_RSTIsSoftRstActive +//* \brief Return !=0 if software reset is still not completed +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_RSTIsSoftRstActive (AT91PS_RSTC pRSTC) +{ +  return ((pRSTC->RSTC_RSR) & AT91C_RSTC_SRCMP); +} + +/* ***************************************************************************** +                SOFTWARE API FOR RTTC +   ***************************************************************************** */ +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_SetRTT_TimeBase() +//* \brief  Set the RTT prescaler according to the TimeBase in ms +//*-------------------------------------------------------------------------------------- +static inline unsigned int +AT91F_RTTSetTimeBase (AT91PS_RTTC pRTTC, unsigned int ms) +{ +  if (ms > 2000) +    return 1;			// AT91C_TIME_OUT_OF_RANGE +  pRTTC->RTTC_RTMR &= ~0xFFFF; +  pRTTC->RTTC_RTMR |= (((ms << 15) / 1000) & 0xFFFF); +  return 0; +} + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTTSetPrescaler() +//* \brief  Set the new prescaler value +//*-------------------------------------------------------------------------------------- +static inline unsigned int +AT91F_RTTSetPrescaler (AT91PS_RTTC pRTTC, unsigned int rtpres) +{ +  pRTTC->RTTC_RTMR &= ~0xFFFF; +  pRTTC->RTTC_RTMR |= (rtpres & 0xFFFF); +  return (pRTTC->RTTC_RTMR); +} + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTTRestart() +//* \brief  Restart the RTT prescaler +//*-------------------------------------------------------------------------------------- +static inline void +AT91F_RTTRestart (AT91PS_RTTC pRTTC) +{ +  pRTTC->RTTC_RTMR |= AT91C_RTTC_RTTRST; +} + + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTT_SetAlarmINT() +//* \brief  Enable RTT Alarm Interrupt +//*-------------------------------------------------------------------------------------- +static inline void +AT91F_RTTSetAlarmINT (AT91PS_RTTC pRTTC) +{ +  pRTTC->RTTC_RTMR |= AT91C_RTTC_ALMIEN; +} + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTT_ClearAlarmINT() +//* \brief  Disable RTT Alarm Interrupt +//*-------------------------------------------------------------------------------------- +static inline void +AT91F_RTTClearAlarmINT (AT91PS_RTTC pRTTC) +{ +  pRTTC->RTTC_RTMR &= ~AT91C_RTTC_ALMIEN; +} + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTT_SetRttIncINT() +//* \brief  Enable RTT INC Interrupt +//*-------------------------------------------------------------------------------------- +static inline void +AT91F_RTTSetRttIncINT (AT91PS_RTTC pRTTC) +{ +  pRTTC->RTTC_RTMR |= AT91C_RTTC_RTTINCIEN; +} + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTT_ClearRttIncINT() +//* \brief  Disable RTT INC Interrupt +//*-------------------------------------------------------------------------------------- +static inline void +AT91F_RTTClearRttIncINT (AT91PS_RTTC pRTTC) +{ +  pRTTC->RTTC_RTMR &= ~AT91C_RTTC_RTTINCIEN; +} + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTT_SetAlarmValue() +//* \brief  Set RTT Alarm Value +//*-------------------------------------------------------------------------------------- +static inline void +AT91F_RTTSetAlarmValue (AT91PS_RTTC pRTTC, unsigned int _alarm) +{ +  pRTTC->RTTC_RTAR = _alarm; +} + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTT_GetAlarmValue() +//* \brief  Get RTT Alarm Value +//*-------------------------------------------------------------------------------------- +static inline unsigned int +AT91F_RTTGetAlarmValue (AT91PS_RTTC pRTTC) +{ +  return (pRTTC->RTTC_RTAR); +} + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTTGetStatus() +//* \brief  Read the RTT status +//*-------------------------------------------------------------------------------------- +static inline unsigned int +AT91F_RTTGetStatus (AT91PS_RTTC pRTTC) +{ +  return (pRTTC->RTTC_RTSR); +} + +//*-------------------------------------------------------------------------------------- +//* \fn     AT91F_RTT_ReadValue() +//* \brief  Read the RTT value +//*-------------------------------------------------------------------------------------- +extern unsigned int AT91F_RTTReadValue (AT91PS_RTTC pRTTC); + +/* ***************************************************************************** +                SOFTWARE API FOR PITC +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PITInit +//* \brief System timer init : period in ‘second, system clock freq in MHz +//*---------------------------------------------------------------------------- +static inline void +AT91F_PITInit (AT91PS_PITC pPITC, +	       unsigned int period, unsigned int pit_frequency) +{ +  pPITC->PITC_PIMR = period ? (period * pit_frequency + 8) >> 4 : 0;	// +8 to avoid %10 and /10 +  pPITC->PITC_PIMR |= AT91C_PITC_PITEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PITSetPIV +//* \brief Set the PIT Periodic Interval Value  +//*---------------------------------------------------------------------------- +static inline void +AT91F_PITSetPIV (AT91PS_PITC pPITC, unsigned int piv) +{ +  pPITC->PITC_PIMR = +    piv | (pPITC->PITC_PIMR & (AT91C_PITC_PITEN | AT91C_PITC_PITIEN)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PITEnableInt +//* \brief Enable PIT periodic interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_PITEnableInt (AT91PS_PITC pPITC) +{ +  pPITC->PITC_PIMR |= AT91C_PITC_PITIEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PITDisableInt +//* \brief Disable PIT periodic interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_PITDisableInt (AT91PS_PITC pPITC) +{ +  pPITC->PITC_PIMR &= ~AT91C_PITC_PITIEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PITGetMode +//* \brief Read PIT mode register +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PITGetMode (AT91PS_PITC pPITC) +{ +  return (pPITC->PITC_PIMR); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PITGetStatus +//* \brief Read PIT status register +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PITGetStatus (AT91PS_PITC pPITC) +{ +  return (pPITC->PITC_PISR); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PITGetPIIR +//* \brief Read PIT CPIV and PICNT without ressetting the counters +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PITGetPIIR (AT91PS_PITC pPITC) +{ +  return (pPITC->PITC_PIIR); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PITGetPIVR +//* \brief Read System timer CPIV and PICNT without ressetting the counters +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PITGetPIVR (AT91PS_PITC pPITC) +{ +  return (pPITC->PITC_PIVR); +} + +/* ***************************************************************************** +                SOFTWARE API FOR WDTC +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_WDTSetMode +//* \brief Set Watchdog Mode Register +//*---------------------------------------------------------------------------- +static inline void +AT91F_WDTSetMode (AT91PS_WDTC pWDTC, unsigned int Mode) +{ +  pWDTC->WDTC_WDMR = Mode; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_WDTRestart +//* \brief Restart Watchdog +//*---------------------------------------------------------------------------- +static inline void +AT91F_WDTRestart (AT91PS_WDTC pWDTC) +{ +  pWDTC->WDTC_WDCR = 0xA5000001; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_WDTSGettatus +//* \brief Get Watchdog Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_WDTSGettatus (AT91PS_WDTC pWDTC) +{ +  return (pWDTC->WDTC_WDSR & 0x3); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_WDTGetPeriod +//* \brief Translate ms into Watchdog Compatible value +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_WDTGetPeriod (unsigned int ms) +{ +  if ((ms < 4) || (ms > 16000)) +    return 0; +  return ((ms << 8) / 1000); +} + +/* ***************************************************************************** +                SOFTWARE API FOR VREG +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_VREG_Enable_LowPowerMode +//* \brief Enable VREG Low Power Mode +//*---------------------------------------------------------------------------- +static inline void +AT91F_VREG_Enable_LowPowerMode (AT91PS_VREG pVREG) +{ +  pVREG->VREG_MR |= AT91C_VREG_PSTDBY; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_VREG_Disable_LowPowerMode +//* \brief Disable VREG Low Power Mode +//*---------------------------------------------------------------------------- +static inline void +AT91F_VREG_Disable_LowPowerMode (AT91PS_VREG pVREG) +{ +  pVREG->VREG_MR &= ~AT91C_VREG_PSTDBY; +}				/* ***************************************************************************** +				   SOFTWARE API FOR MC +				   ***************************************************************************** */ + +#define AT91C_MC_CORRECT_KEY  ((unsigned int) 0x5A << 24)	// (MC) Correct Protect Key + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_MC_Remap +//* \brief Make Remap +//*---------------------------------------------------------------------------- +static inline void +AT91F_MC_Remap (void)		//   +{ +  AT91PS_MC pMC = (AT91PS_MC) AT91C_BASE_MC; + +  pMC->MC_RCR = AT91C_MC_RCB; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_MC_EFC_CfgModeReg +//* \brief Configure the EFC Mode Register of the MC controller +//*---------------------------------------------------------------------------- +static inline void +AT91F_MC_EFC_CfgModeReg (AT91PS_MC pMC,	// pointer to a MC controller +			 unsigned int mode)	// mode register  +{ +  // Write to the FMR register +  pMC->MC_FMR = mode; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_MC_EFC_GetModeReg +//* \brief Return MC EFC Mode Regsiter +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_MC_EFC_GetModeReg (AT91PS_MC pMC)	// pointer to a MC controller +{ +  return pMC->MC_FMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_MC_EFC_ComputeFMCN +//* \brief Return MC EFC Mode Regsiter +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_MC_EFC_ComputeFMCN (int master_clock)	// master clock in Hz +{ +  return (master_clock / 1000000 + 2); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_MC_EFC_PerformCmd +//* \brief Perform EFC Command +//*---------------------------------------------------------------------------- +static inline void +AT91F_MC_EFC_PerformCmd (AT91PS_MC pMC,	// pointer to a MC controller +			 unsigned int transfer_cmd) +{ +  pMC->MC_FCR = transfer_cmd; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_MC_EFC_GetStatus +//* \brief Return MC EFC Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_MC_EFC_GetStatus (AT91PS_MC pMC)	// pointer to a MC controller +{ +  return pMC->MC_FSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_MC_EFC_IsInterruptMasked +//* \brief Test if EFC MC Interrupt is Masked  +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_MC_EFC_IsInterruptMasked (AT91PS_MC pMC,	// \arg  pointer to a MC controller +				unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_MC_EFC_GetModeReg (pMC) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_MC_EFC_IsInterruptSet +//* \brief Test if EFC MC Interrupt is Set +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_MC_EFC_IsInterruptSet (AT91PS_MC pMC,	// \arg  pointer to a MC controller +			     unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_MC_EFC_GetStatus (pMC) & flag); +} + +/* ***************************************************************************** +                SOFTWARE API FOR SPI +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_CfgCs +//* \brief Configure SPI chip select register +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_CfgCs (AT91PS_SPI pSPI,	// pointer to a SPI controller +		 int cs,	// SPI cs number (0 to 3) +		 int val)	//  chip select register +{ +  //* Write to the CSR register +  *(pSPI->SPI_CSR + cs) = val; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_EnableIt +//* \brief Enable SPI interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_EnableIt (AT91PS_SPI pSPI,	// pointer to a SPI controller +		    unsigned int flag)	// IT to be enabled +{ +  //* Write to the IER register +  pSPI->SPI_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_DisableIt +//* \brief Disable SPI interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_DisableIt (AT91PS_SPI pSPI,	// pointer to a SPI controller +		     unsigned int flag)	// IT to be disabled +{ +  //* Write to the IDR register +  pSPI->SPI_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_Reset +//* \brief Reset the SPI controller +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_Reset (AT91PS_SPI pSPI	// pointer to a SPI controller +  ) +{ +  //* Write to the CR register +  pSPI->SPI_CR = AT91C_SPI_SWRST; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_Enable +//* \brief Enable the SPI controller +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_Enable (AT91PS_SPI pSPI	// pointer to a SPI controller +  ) +{ +  //* Write to the CR register +  pSPI->SPI_CR = AT91C_SPI_SPIEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_Disable +//* \brief Disable the SPI controller +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_Disable (AT91PS_SPI pSPI	// pointer to a SPI controller +  ) +{ +  //* Write to the CR register +  pSPI->SPI_CR = AT91C_SPI_SPIDIS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_CfgMode +//* \brief Enable the SPI controller +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_CfgMode (AT91PS_SPI pSPI,	// pointer to a SPI controller +		   int mode)	// mode register  +{ +  //* Write to the MR register +  pSPI->SPI_MR = mode; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_CfgPCS +//* \brief Switch to the correct PCS of SPI Mode Register : Fixed Peripheral Selected +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_CfgPCS (AT91PS_SPI pSPI,	// pointer to a SPI controller +		  char PCS_Device)	// PCS of the Device +{ +  //* Write to the MR register +  pSPI->SPI_MR &= 0xFFF0FFFF; +  pSPI->SPI_MR |= ((PCS_Device << 16) & AT91C_SPI_PCS); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_ReceiveFrame +//* \brief Return 2 if PDC has been initialized with Buffer and Next Buffer, 1 if PDC has been initializaed with Next Buffer, 0 if PDC is busy +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_SPI_ReceiveFrame (AT91PS_SPI pSPI, +			unsigned char *pBuffer, +			unsigned int szBuffer, +			unsigned char *pNextBuffer, unsigned int szNextBuffer) +{ +  return AT91F_PDC_ReceiveFrame ((AT91PS_PDC) & (pSPI->SPI_RPR), +				 pBuffer, +				 szBuffer, pNextBuffer, szNextBuffer); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_SendFrame +//* \brief Return 2 if PDC has been initialized with Buffer and Next Buffer, 1 if PDC has been initializaed with Next Buffer, 0 if PDC is bSPIy +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_SPI_SendFrame (AT91PS_SPI pSPI, +		     const unsigned char *pBuffer, +		     unsigned int szBuffer, +		     const unsigned char *pNextBuffer, +		     unsigned int szNextBuffer) +{ +  return AT91F_PDC_SendFrame ((AT91PS_PDC) & (pSPI->SPI_RPR), +			      pBuffer, szBuffer, pNextBuffer, szNextBuffer); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_Close +//* \brief Close SPI: disable IT disable transfert, close PDC +//*---------------------------------------------------------------------------- +extern void AT91F_SPI_Close (AT91PS_SPI pSPI);	// \arg pointer to a SPI controller + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_PutChar +//* \brief Send a character,does not check if ready to send +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_PutChar (AT91PS_SPI pSPI, +		   unsigned int character, unsigned int cs_number) +{ +  unsigned int value_for_cs; +  value_for_cs = (~(1 << cs_number)) & 0xF;	//Place a zero among a 4 ONEs number +  pSPI->SPI_TDR = (character & 0xFFFF) | (value_for_cs << 16); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_GetChar +//* \brief Receive a character,does not check if a character is available +//*---------------------------------------------------------------------------- +static inline int +AT91F_SPI_GetChar (const AT91PS_SPI pSPI) +{ +  return ((pSPI->SPI_RDR) & 0xFFFF); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_GetInterruptMaskStatus +//* \brief Return SPI Interrupt Mask Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_SPI_GetInterruptMaskStatus (	// \return SPI Interrupt Mask Status +				   AT91PS_SPI pSpi)	// \arg  pointer to a SPI controller +{ +  return pSpi->SPI_IMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_IsInterruptMasked +//* \brief Test if SPI Interrupt is Masked  +//*---------------------------------------------------------------------------- +static inline int +AT91F_SPI_IsInterruptMasked (AT91PS_SPI pSpi,	// \arg  pointer to a SPI controller +			     unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_SPI_GetInterruptMaskStatus (pSpi) & flag); +} + +/* ***************************************************************************** +                SOFTWARE API FOR ADC +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_EnableIt +//* \brief Enable ADC interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_ADC_EnableIt (AT91PS_ADC pADC,	// pointer to a ADC controller +		    unsigned int flag)	// IT to be enabled +{ +  //* Write to the IER register +  pADC->ADC_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_DisableIt +//* \brief Disable ADC interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_ADC_DisableIt (AT91PS_ADC pADC,	// pointer to a ADC controller +		     unsigned int flag)	// IT to be disabled +{ +  //* Write to the IDR register +  pADC->ADC_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetStatus +//* \brief Return ADC Interrupt Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetStatus (		// \return ADC Interrupt Status +		      AT91PS_ADC pADC)	// pointer to a ADC controller +{ +  return pADC->ADC_SR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetInterruptMaskStatus +//* \brief Return ADC Interrupt Mask Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetInterruptMaskStatus (	// \return ADC Interrupt Mask Status +				   AT91PS_ADC pADC)	// pointer to a ADC controller +{ +  return pADC->ADC_IMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_IsInterruptMasked +//* \brief Test if ADC Interrupt is Masked  +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_IsInterruptMasked (AT91PS_ADC pADC,	// \arg  pointer to a ADC controller +			     unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_ADC_GetInterruptMaskStatus (pADC) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_IsStatusSet +//* \brief Test if ADC Status is Set +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_IsStatusSet (AT91PS_ADC pADC,	// \arg  pointer to a ADC controller +		       unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_ADC_GetStatus (pADC) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_CfgModeReg +//* \brief Configure the Mode Register of the ADC controller +//*---------------------------------------------------------------------------- +static inline void +AT91F_ADC_CfgModeReg (AT91PS_ADC pADC,	// pointer to a ADC controller +		      unsigned int mode)	// mode register  +{ +  //* Write to the MR register +  pADC->ADC_MR = mode; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetModeReg +//* \brief Return the Mode Register of the ADC controller value +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetModeReg (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_MR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_CfgTimings +//* \brief Configure the different necessary timings of the ADC controller +//*---------------------------------------------------------------------------- +extern void AT91F_ADC_CfgTimings (AT91PS_ADC pADC,	// pointer to a ADC controller +				  unsigned int mck_clock,	// in MHz  +				  unsigned int adc_clock,	// in MHz  +				  unsigned int startup_time,	// in us  +				  unsigned int sample_and_hold_time);	// in ns   + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_EnableChannel +//* \brief Return ADC Timer Register Value +//*---------------------------------------------------------------------------- +static inline void +AT91F_ADC_EnableChannel (AT91PS_ADC pADC,	// pointer to a ADC controller +			 unsigned int channel)	// mode register  +{ +  //* Write to the CHER register +  pADC->ADC_CHER = channel; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_DisableChannel +//* \brief Return ADC Timer Register Value +//*---------------------------------------------------------------------------- +static inline void +AT91F_ADC_DisableChannel (AT91PS_ADC pADC,	// pointer to a ADC controller +			  unsigned int channel)	// mode register  +{ +  //* Write to the CHDR register +  pADC->ADC_CHDR = channel; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetChannelStatus +//* \brief Return ADC Timer Register Value +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetChannelStatus (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_CHSR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_StartConversion +//* \brief Software request for a analog to digital conversion  +//*---------------------------------------------------------------------------- +static inline void +AT91F_ADC_StartConversion (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  pADC->ADC_CR = AT91C_ADC_START; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_SoftReset +//* \brief Software reset +//*---------------------------------------------------------------------------- +static inline void +AT91F_ADC_SoftReset (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  pADC->ADC_CR = AT91C_ADC_SWRST; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetLastConvertedData +//* \brief Return the Last Converted Data +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetLastConvertedData (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_LCDR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetConvertedDataCH0 +//* \brief Return the Channel 0 Converted Data +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetConvertedDataCH0 (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_CDR0; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetConvertedDataCH1 +//* \brief Return the Channel 1 Converted Data +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetConvertedDataCH1 (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_CDR1; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetConvertedDataCH2 +//* \brief Return the Channel 2 Converted Data +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetConvertedDataCH2 (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_CDR2; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetConvertedDataCH3 +//* \brief Return the Channel 3 Converted Data +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetConvertedDataCH3 (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_CDR3; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetConvertedDataCH4 +//* \brief Return the Channel 4 Converted Data +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetConvertedDataCH4 (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_CDR4; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetConvertedDataCH5 +//* \brief Return the Channel 5 Converted Data +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetConvertedDataCH5 (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_CDR5; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetConvertedDataCH6 +//* \brief Return the Channel 6 Converted Data +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetConvertedDataCH6 (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_CDR6; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_GetConvertedDataCH7 +//* \brief Return the Channel 7 Converted Data +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_ADC_GetConvertedDataCH7 (AT91PS_ADC pADC	// pointer to a ADC controller +  ) +{ +  return pADC->ADC_CDR7; +} + +/* ***************************************************************************** +                SOFTWARE API FOR SSC +   ***************************************************************************** */ +//* Define the standard I2S mode configuration + +//* Configuration to set in the SSC Transmit Clock Mode Register +//* Parameters :  nb_bit_by_slot : 8, 16 or 32 bits +//*                       nb_slot_by_frame : number of channels +#define AT91C_I2S_ASY_MASTER_TX_SETTING(nb_bit_by_slot, nb_slot_by_frame)( +\ +									   AT91C_SSC_CKS_DIV   +\ +                            		   AT91C_SSC_CKO_CONTINOUS      +\ +                            		   AT91C_SSC_CKG_NONE    +\ +                                       AT91C_SSC_START_FALL_RF +\ +                           			   AT91C_SSC_STTOUT  +\ +                            		   ((1<<16) & AT91C_SSC_STTDLY) +\ +                            		   ((((nb_bit_by_slot*nb_slot_by_frame)/2)-1) <<24)) + + +//* Configuration to set in the SSC Transmit Frame Mode Register +//* Parameters : nb_bit_by_slot : 8, 16 or 32 bits +//*                      nb_slot_by_frame : number of channels +#define AT91C_I2S_ASY_TX_FRAME_SETTING(nb_bit_by_slot, nb_slot_by_frame)( +\ +									(nb_bit_by_slot-1)  +\ +                            		AT91C_SSC_MSBF   +\ +                            		(((nb_slot_by_frame-1)<<8) & AT91C_SSC_DATNB)  +\ +                            		(((nb_bit_by_slot-1)<<16) & AT91C_SSC_FSLEN) +\ +                            		AT91C_SSC_FSOS_NEGATIVE) + + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_SetBaudrate +//* \brief Set the baudrate according to the CPU clock +//*---------------------------------------------------------------------------- +extern void AT91F_SSC_SetBaudrate (AT91PS_SSC pSSC,	// \arg pointer to a SSC controller +				   unsigned int mainClock,	// \arg peripheral clock +				   unsigned int speed);	// \arg SSC baudrate + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_Configure +//* \brief Configure SSC +//*---------------------------------------------------------------------------- +extern void AT91F_SSC_Configure (AT91PS_SSC pSSC,	// \arg pointer to a SSC controller +				 unsigned int syst_clock,	// \arg System Clock Frequency +				 unsigned int baud_rate,	// \arg Expected Baud Rate Frequency +				 unsigned int clock_rx,	// \arg Receiver Clock Parameters +				 unsigned int mode_rx,	// \arg mode Register to be programmed +				 unsigned int clock_tx,	// \arg Transmitter Clock Parameters +				 unsigned int mode_tx);	// \arg mode Register to be programmed + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_EnableRx +//* \brief Enable receiving datas +//*---------------------------------------------------------------------------- +static inline void +AT91F_SSC_EnableRx (AT91PS_SSC pSSC)	// \arg pointer to a SSC controller +{ +  //* Enable receiver +  pSSC->SSC_CR = AT91C_SSC_RXEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_DisableRx +//* \brief Disable receiving datas +//*---------------------------------------------------------------------------- +static inline void +AT91F_SSC_DisableRx (AT91PS_SSC pSSC)	// \arg pointer to a SSC controller +{ +  //* Disable receiver +  pSSC->SSC_CR = AT91C_SSC_RXDIS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_EnableTx +//* \brief Enable sending datas +//*---------------------------------------------------------------------------- +static inline void +AT91F_SSC_EnableTx (AT91PS_SSC pSSC)	// \arg pointer to a SSC controller +{ +  //* Enable  transmitter +  pSSC->SSC_CR = AT91C_SSC_TXEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_DisableTx +//* \brief Disable sending datas +//*---------------------------------------------------------------------------- +static inline void +AT91F_SSC_DisableTx (AT91PS_SSC pSSC)	// \arg pointer to a SSC controller +{ +  //* Disable  transmitter +  pSSC->SSC_CR = AT91C_SSC_TXDIS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_EnableIt +//* \brief Enable SSC IT +//*---------------------------------------------------------------------------- +static inline void +AT91F_SSC_EnableIt (AT91PS_SSC pSSC,	// \arg pointer to a SSC controller +		    unsigned int flag)	// \arg IT to be enabled +{ +  //* Write to the IER register +  pSSC->SSC_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_DisableIt +//* \brief Disable SSC IT +//*---------------------------------------------------------------------------- +static inline void +AT91F_SSC_DisableIt (AT91PS_SSC pSSC,	// \arg pointer to a SSC controller +		     unsigned int flag)	// \arg IT to be disabled +{ +  //* Write to the IDR register +  pSSC->SSC_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_ReceiveFrame +//* \brief Return 2 if PDC has been initialized with Buffer and Next Buffer, 1 if PDC has been initialized with Next Buffer, 0 if PDC is busy +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_SSC_ReceiveFrame (AT91PS_SSC pSSC, +			unsigned char *pBuffer, +			unsigned int szBuffer, +			unsigned char *pNextBuffer, unsigned int szNextBuffer) +{ +  return AT91F_PDC_ReceiveFrame ((AT91PS_PDC) & (pSSC->SSC_RPR), +				 pBuffer, +				 szBuffer, pNextBuffer, szNextBuffer); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_SendFrame +//* \brief Return 2 if PDC has been initialized with Buffer and Next Buffer, 1 if PDC has been initialized with Next Buffer, 0 if PDC is busy +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_SSC_SendFrame (AT91PS_SSC pSSC, +		     const unsigned char *pBuffer, +		     unsigned int szBuffer, +		     const unsigned char *pNextBuffer, +		     unsigned int szNextBuffer) +{ +  return AT91F_PDC_SendFrame ((AT91PS_PDC) & (pSSC->SSC_RPR), +			      pBuffer, szBuffer, pNextBuffer, szNextBuffer); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_GetInterruptMaskStatus +//* \brief Return SSC Interrupt Mask Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_SSC_GetInterruptMaskStatus (	// \return SSC Interrupt Mask Status +				   AT91PS_SSC pSsc)	// \arg  pointer to a SSC controller +{ +  return pSsc->SSC_IMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_IsInterruptMasked +//* \brief Test if SSC Interrupt is Masked  +//*---------------------------------------------------------------------------- +static inline int +AT91F_SSC_IsInterruptMasked (AT91PS_SSC pSsc,	// \arg  pointer to a SSC controller +			     unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_SSC_GetInterruptMaskStatus (pSsc) & flag); +} + +/* ***************************************************************************** +                SOFTWARE API FOR USART +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_Baudrate +//* \brief Calculate the baudrate +//* Standard Asynchronous Mode : 8 bits , 1 stop , no parity +#define AT91C_US_ASYNC_MODE ( AT91C_US_USMODE_NORMAL + \ +                        AT91C_US_NBSTOP_1_BIT + \ +                        AT91C_US_PAR_NONE + \ +                        AT91C_US_CHRL_8_BITS + \ +                        AT91C_US_CLKS_CLOCK ) + +//* Standard External Asynchronous Mode : 8 bits , 1 stop , no parity +#define AT91C_US_ASYNC_SCK_MODE ( AT91C_US_USMODE_NORMAL + \ +                            AT91C_US_NBSTOP_1_BIT + \ +                            AT91C_US_PAR_NONE + \ +                            AT91C_US_CHRL_8_BITS + \ +                            AT91C_US_CLKS_EXT ) + +//* Standard Synchronous Mode : 8 bits , 1 stop , no parity +#define AT91C_US_SYNC_MODE ( AT91C_US_SYNC + \ +                       AT91C_US_USMODE_NORMAL + \ +                       AT91C_US_NBSTOP_1_BIT + \ +                       AT91C_US_PAR_NONE + \ +                       AT91C_US_CHRL_8_BITS + \ +                       AT91C_US_CLKS_CLOCK ) + +//* SCK used Label +#define AT91C_US_SCK_USED (AT91C_US_CKLO | AT91C_US_CLKS_EXT) + +//* Standard ISO T=0 Mode : 8 bits , 1 stop , parity +#define AT91C_US_ISO_READER_MODE ( AT91C_US_USMODE_ISO7816_0 + \ +					   		 AT91C_US_CLKS_CLOCK +\ +                       		 AT91C_US_NBSTOP_1_BIT + \ +                       		 AT91C_US_PAR_EVEN + \ +                       		 AT91C_US_CHRL_8_BITS + \ +                       		 AT91C_US_CKLO +\ +                       		 AT91C_US_OVER) + +//* Standard IRDA mode +#define AT91C_US_ASYNC_IRDA_MODE (  AT91C_US_USMODE_IRDA + \ +                            AT91C_US_NBSTOP_1_BIT + \ +                            AT91C_US_PAR_NONE + \ +                            AT91C_US_CHRL_8_BITS + \ +                            AT91C_US_CLKS_CLOCK ) + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_Baudrate +//* \brief Caluculate baud_value according to the main clock and the baud rate +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_US_Baudrate (const unsigned int main_clock,	// \arg peripheral clock +		   const unsigned int baud_rate)	// \arg UART baudrate +{ +  unsigned int baud_value = ((main_clock * 10) / (baud_rate * 16)); +  if ((baud_value % 10) >= 5) +    baud_value = (baud_value / 10) + 1; +  else +    baud_value /= 10; +  return baud_value; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_SetBaudrate +//* \brief Set the baudrate according to the CPU clock +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_SetBaudrate (AT91PS_USART pUSART,	// \arg pointer to a USART controller +		      unsigned int mainClock,	// \arg peripheral clock +		      unsigned int speed)	// \arg UART baudrate +{ +  //* Define the baud rate divisor register +  pUSART->US_BRGR = AT91F_US_Baudrate (mainClock, speed); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_SetTimeguard +//* \brief Set USART timeguard +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_SetTimeguard (AT91PS_USART pUSART,	// \arg pointer to a USART controller +		       unsigned int timeguard)	// \arg timeguard value +{ +  //* Write the Timeguard Register +  pUSART->US_TTGR = timeguard; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_EnableIt +//* \brief Enable USART IT +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_EnableIt (AT91PS_USART pUSART,	// \arg pointer to a USART controller +		   unsigned int flag)	// \arg IT to be enabled +{ +  //* Write to the IER register +  pUSART->US_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_DisableIt +//* \brief Disable USART IT +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_DisableIt (AT91PS_USART pUSART,	// \arg pointer to a USART controller +		    unsigned int flag)	// \arg IT to be disabled +{ +  //* Write to the IER register +  pUSART->US_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_Configure +//* \brief Configure USART +//*---------------------------------------------------------------------------- +extern void AT91F_US_Configure (AT91PS_USART pUSART,	// \arg pointer to a USART controller +				unsigned int mainClock,	// \arg peripheral clock +				unsigned int mode,	// \arg mode Register to be programmed +				unsigned int baudRate,	// \arg baudrate to be programmed +				unsigned int timeguard);	// \arg timeguard to be programmed + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_EnableRx +//* \brief Enable receiving characters +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_EnableRx (AT91PS_USART pUSART)	// \arg pointer to a USART controller +{ +  //* Enable receiver +  pUSART->US_CR = AT91C_US_RXEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_EnableTx +//* \brief Enable sending characters +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_EnableTx (AT91PS_USART pUSART)	// \arg pointer to a USART controller +{ +  //* Enable  transmitter +  pUSART->US_CR = AT91C_US_TXEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_ResetRx +//* \brief Reset Receiver and re-enable it +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_ResetRx (AT91PS_USART pUSART)	// \arg pointer to a USART controller +{ +  //* Reset receiver +  pUSART->US_CR = AT91C_US_RSTRX; +  //* Re-Enable receiver +  pUSART->US_CR = AT91C_US_RXEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_ResetTx +//* \brief Reset Transmitter and re-enable it +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_ResetTx (AT91PS_USART pUSART)	// \arg pointer to a USART controller +{ +  //* Reset transmitter +  pUSART->US_CR = AT91C_US_RSTTX; +  //* Enable transmitter +  pUSART->US_CR = AT91C_US_TXEN; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_DisableRx +//* \brief Disable Receiver +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_DisableRx (AT91PS_USART pUSART)	// \arg pointer to a USART controller +{ +  //* Disable receiver +  pUSART->US_CR = AT91C_US_RXDIS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_DisableTx +//* \brief Disable Transmitter +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_DisableTx (AT91PS_USART pUSART)	// \arg pointer to a USART controller +{ +  //* Disable transmitter +  pUSART->US_CR = AT91C_US_TXDIS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_Close +//* \brief Close USART: disable IT disable receiver and transmitter, close PDC +//*---------------------------------------------------------------------------- +extern void AT91F_US_Close (AT91PS_USART pUSART);	// \arg pointer to a USART controller + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_TxReady +//* \brief Return 1 if a character can be written in US_THR +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_US_TxReady (AT91PS_USART pUSART)	// \arg pointer to a USART controller +{ +  return (pUSART->US_CSR & AT91C_US_TXRDY); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_RxReady +//* \brief Return 1 if a character can be read in US_RHR +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_US_RxReady (AT91PS_USART pUSART)	// \arg pointer to a USART controller +{ +  return (pUSART->US_CSR & AT91C_US_RXRDY); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_Error +//* \brief Return the error flag +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_US_Error (AT91PS_USART pUSART)	// \arg pointer to a USART controller +{ +  return (pUSART->US_CSR & (AT91C_US_OVRE |	// Overrun error +			    AT91C_US_FRAME |	// Framing error +			    AT91C_US_PARE));	// Parity error +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_PutChar +//* \brief Send a character,does not check if ready to send +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_PutChar (AT91PS_USART pUSART, int character) +{ +  pUSART->US_THR = (character & 0x1FF); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_GetChar +//* \brief Receive a character,does not check if a character is available +//*---------------------------------------------------------------------------- +static inline int +AT91F_US_GetChar (const AT91PS_USART pUSART) +{ +  return ((pUSART->US_RHR) & 0x1FF); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_SendFrame +//* \brief Return 2 if PDC has been initialized with Buffer and Next Buffer, 1 if PDC has been initializaed with Next Buffer, 0 if PDC is busy +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_US_SendFrame (AT91PS_USART pUSART, +		    const unsigned char *pBuffer, +		    unsigned int szBuffer, +		    const unsigned char *pNextBuffer, +		    unsigned int szNextBuffer) +{ +  return AT91F_PDC_SendFrame ((AT91PS_PDC) & (pUSART->US_RPR), +			      pBuffer, szBuffer, pNextBuffer, szNextBuffer); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_ReceiveFrame +//* \brief Return 2 if PDC has been initialized with Buffer and Next Buffer, 1 if PDC has been initializaed with Next Buffer, 0 if PDC is busy +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_US_ReceiveFrame (AT91PS_USART pUSART, +		       unsigned char *pBuffer, +		       unsigned int szBuffer, +		       unsigned char *pNextBuffer, unsigned int szNextBuffer) +{ +  return AT91F_PDC_ReceiveFrame ((AT91PS_PDC) & (pUSART->US_RPR), +				 pBuffer, +				 szBuffer, pNextBuffer, szNextBuffer); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US_SetIrdaFilter +//* \brief Set the value of IrDa filter tregister +//*---------------------------------------------------------------------------- +static inline void +AT91F_US_SetIrdaFilter (AT91PS_USART pUSART, unsigned char value) +{ +  pUSART->US_IF = value; +} + +/* ***************************************************************************** +                SOFTWARE API FOR TWI +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TWI_EnableIt +//* \brief Enable TWI IT +//*---------------------------------------------------------------------------- +static inline void +AT91F_TWI_EnableIt (AT91PS_TWI pTWI,	// \arg pointer to a TWI controller +		    unsigned int flag)	// \arg IT to be enabled +{ +  //* Write to the IER register +  pTWI->TWI_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TWI_DisableIt +//* \brief Disable TWI IT +//*---------------------------------------------------------------------------- +static inline void +AT91F_TWI_DisableIt (AT91PS_TWI pTWI,	// \arg pointer to a TWI controller +		     unsigned int flag)	// \arg IT to be disabled +{ +  //* Write to the IDR register +  pTWI->TWI_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TWI_Configure +//* \brief Configure TWI in master mode +//*---------------------------------------------------------------------------- +static inline void +AT91F_TWI_Configure (AT91PS_TWI pTWI)	// \arg pointer to a TWI controller +{ +  //* Disable interrupts +  pTWI->TWI_IDR = (unsigned int) -1; + +  //* Reset peripheral +  pTWI->TWI_CR = AT91C_TWI_SWRST; + +  //* Set Master mode +  pTWI->TWI_CR = AT91C_TWI_MSEN; + +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TWI_GetInterruptMaskStatus +//* \brief Return TWI Interrupt Mask Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_TWI_GetInterruptMaskStatus (	// \return TWI Interrupt Mask Status +				   AT91PS_TWI pTwi)	// \arg  pointer to a TWI controller +{ +  return pTwi->TWI_IMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TWI_IsInterruptMasked +//* \brief Test if TWI Interrupt is Masked  +//*---------------------------------------------------------------------------- +static inline int +AT91F_TWI_IsInterruptMasked (AT91PS_TWI pTwi,	// \arg  pointer to a TWI controller +			     unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_TWI_GetInterruptMaskStatus (pTwi) & flag); +} + +/* ***************************************************************************** +                SOFTWARE API FOR TC +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TC_InterruptEnable +//* \brief Enable TC Interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_TC_InterruptEnable (AT91PS_TC pTc,	// \arg  pointer to a TC controller +			  unsigned int flag)	// \arg  TC interrupt to be enabled +{ +  pTc->TC_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TC_InterruptDisable +//* \brief Disable TC Interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_TC_InterruptDisable (AT91PS_TC pTc,	// \arg  pointer to a TC controller +			   unsigned int flag)	// \arg  TC interrupt to be disabled +{ +  pTc->TC_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TC_GetInterruptMaskStatus +//* \brief Return TC Interrupt Mask Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_TC_GetInterruptMaskStatus (	// \return TC Interrupt Mask Status +				  AT91PS_TC pTc)	// \arg  pointer to a TC controller +{ +  return pTc->TC_IMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TC_IsInterruptMasked +//* \brief Test if TC Interrupt is Masked  +//*---------------------------------------------------------------------------- +static inline int +AT91F_TC_IsInterruptMasked (AT91PS_TC pTc,	// \arg  pointer to a TC controller +			    unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_TC_GetInterruptMaskStatus (pTc) & flag); +} + +/* ***************************************************************************** +                SOFTWARE API FOR PWMC +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWM_GetStatus +//* \brief Return PWM Interrupt Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PWMC_GetStatus (		// \return PWM Interrupt Status +		       AT91PS_PWMC pPWM)	// pointer to a PWM controller +{ +  return pPWM->PWMC_SR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWM_InterruptEnable +//* \brief Enable PWM Interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_InterruptEnable (AT91PS_PWMC pPwm,	// \arg  pointer to a PWM controller +			    unsigned int flag)	// \arg  PWM interrupt to be enabled +{ +  pPwm->PWMC_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWM_InterruptDisable +//* \brief Disable PWM Interrupt +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_InterruptDisable (AT91PS_PWMC pPwm,	// \arg  pointer to a PWM controller +			     unsigned int flag)	// \arg  PWM interrupt to be disabled +{ +  pPwm->PWMC_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWM_GetInterruptMaskStatus +//* \brief Return PWM Interrupt Mask Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PWMC_GetInterruptMaskStatus (	// \return PWM Interrupt Mask Status +				    AT91PS_PWMC pPwm)	// \arg  pointer to a PWM controller +{ +  return pPwm->PWMC_IMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWM_IsInterruptMasked +//* \brief Test if PWM Interrupt is Masked +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PWMC_IsInterruptMasked (AT91PS_PWMC pPWM,	// \arg  pointer to a PWM controller +			      unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PWMC_GetInterruptMaskStatus (pPWM) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWM_IsStatusSet +//* \brief Test if PWM Interrupt is Set +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_PWMC_IsStatusSet (AT91PS_PWMC pPWM,	// \arg  pointer to a PWM controller +			unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_PWMC_GetStatus (pPWM) & flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWM_CfgChannel +//* \brief Test if PWM Interrupt is Set +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_CfgChannel (AT91PS_PWMC pPWM,	// \arg  pointer to a PWM controller +		       unsigned int channelId,	// \arg PWM channel ID +		       unsigned int mode,	// \arg  PWM mode +		       unsigned int period,	// \arg PWM period +		       unsigned int duty)	// \arg PWM duty cycle +{ +  pPWM->PWMC_CH[channelId].PWMC_CMR = mode; +  pPWM->PWMC_CH[channelId].PWMC_CDTYR = duty; +  pPWM->PWMC_CH[channelId].PWMC_CPRDR = period; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWM_StartChannel +//* \brief Enable channel +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_StartChannel (AT91PS_PWMC pPWM,	// \arg  pointer to a PWM controller +			 unsigned int flag)	// \arg  Channels IDs to be enabled +{ +  pPWM->PWMC_ENA = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWM_StopChannel +//* \brief Disable channel +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_StopChannel (AT91PS_PWMC pPWM,	// \arg  pointer to a PWM controller +			unsigned int flag)	// \arg  Channels IDs to be enabled +{ +  pPWM->PWMC_DIS = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWM_UpdateChannel +//* \brief Update Period or Duty Cycle +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_UpdateChannel (AT91PS_PWMC pPWM,	// \arg  pointer to a PWM controller +			  unsigned int channelId,	// \arg PWM channel ID +			  unsigned int update)	// \arg  Channels IDs to be enabled +{ +  pPWM->PWMC_CH[channelId].PWMC_CUPDR = update; +} + +/* ***************************************************************************** +                SOFTWARE API FOR UDP +   ***************************************************************************** */ +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_EnableIt +//* \brief Enable UDP IT +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_EnableIt (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		    unsigned int flag)	// \arg IT to be enabled +{ +  //* Write to the IER register +  pUDP->UDP_IER = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_DisableIt +//* \brief Disable UDP IT +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_DisableIt (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		     unsigned int flag)	// \arg IT to be disabled +{ +  //* Write to the IDR register +  pUDP->UDP_IDR = flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_SetAddress +//* \brief Set UDP functional address +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_SetAddress (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		      unsigned char address)	// \arg new UDP address +{ +  pUDP->UDP_FADDR = (AT91C_UDP_FEN | address); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_EnableEp +//* \brief Enable Endpoint +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_EnableEp (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		    unsigned char endpoint)	// \arg endpoint number +{ +  pUDP->UDP_CSR[endpoint] |= AT91C_UDP_EPEDS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_DisableEp +//* \brief Enable Endpoint +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_DisableEp (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		     unsigned char endpoint)	// \arg endpoint number +{ +  pUDP->UDP_CSR[endpoint] &= ~AT91C_UDP_EPEDS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_SetState +//* \brief Set UDP Device state +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_SetState (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		    unsigned int flag)	// \arg new UDP address +{ +  pUDP->UDP_GLBSTATE &= ~(AT91C_UDP_FADDEN | AT91C_UDP_CONFG); +  pUDP->UDP_GLBSTATE |= flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_GetState +//* \brief return UDP Device state +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_UDP_GetState (		// \return the UDP device state +		     AT91PS_UDP pUDP)	// \arg pointer to a UDP controller +{ +  return (pUDP->UDP_GLBSTATE & (AT91C_UDP_FADDEN | AT91C_UDP_CONFG)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_ResetEp +//* \brief Reset UDP endpoint +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_ResetEp (		// \return the UDP device state +		    AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		    unsigned int flag)	// \arg Endpoints to be reset +{ +  pUDP->UDP_RSTEP = flag; +  pUDP->UDP_RSTEP = 0; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_EpStall +//* \brief Endpoint will STALL requests +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_EpStall (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		   unsigned char endpoint)	// \arg endpoint number +{ +  pUDP->UDP_CSR[endpoint] |= AT91C_UDP_FORCESTALL; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_EpWrite +//* \brief Write value in the DPR +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_EpWrite (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		   unsigned char endpoint,	// \arg endpoint number +		   unsigned char value)	// \arg value to be written in the DPR +{ +  pUDP->UDP_FDR[endpoint] = value; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_EpRead +//* \brief Return value from the DPR +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_UDP_EpRead (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		  unsigned char endpoint)	// \arg endpoint number +{ +  return pUDP->UDP_FDR[endpoint]; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_EpEndOfWr +//* \brief Notify the UDP that values in DPR are ready to be sent +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_EpEndOfWr (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		     unsigned char endpoint)	// \arg endpoint number +{ +  pUDP->UDP_CSR[endpoint] |= AT91C_UDP_TXPKTRDY; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_EpClear +//* \brief Clear flag in the endpoint CSR register +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_EpClear (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		   unsigned char endpoint,	// \arg endpoint number +		   unsigned int flag)	// \arg flag to be cleared +{ +  pUDP->UDP_CSR[endpoint] &= ~(flag); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_EpSet +//* \brief Set flag in the endpoint CSR register +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_EpSet (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		 unsigned char endpoint,	// \arg endpoint number +		 unsigned int flag)	// \arg flag to be cleared +{ +  pUDP->UDP_CSR[endpoint] |= flag; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_EpStatus +//* \brief Return the endpoint CSR register +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_UDP_EpStatus (AT91PS_UDP pUDP,	// \arg pointer to a UDP controller +		    unsigned char endpoint)	// \arg endpoint number +{ +  return pUDP->UDP_CSR[endpoint]; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_GetInterruptMaskStatus +//* \brief Return UDP Interrupt Mask Status +//*---------------------------------------------------------------------------- +static inline unsigned int +AT91F_UDP_GetInterruptMaskStatus (AT91PS_UDP pUdp)	// \arg  pointer to a UDP controller +{ +  return pUdp->UDP_IMR; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_IsInterruptMasked +//* \brief Test if UDP Interrupt is Masked  +//*---------------------------------------------------------------------------- +static inline int +AT91F_UDP_IsInterruptMasked (AT91PS_UDP pUdp,	// \arg  pointer to a UDP controller +			     unsigned int flag)	// \arg  flag to be tested +{ +  return (AT91F_UDP_GetInterruptMaskStatus (pUdp) & flag); +} + +// ---------------------------------------------------------------------------- +//  \fn    AT91F_UDP_InterruptStatusRegister +//  \brief Return the Interrupt Status Register +// ---------------------------------------------------------------------------- +static inline unsigned int +AT91F_UDP_InterruptStatusRegister (AT91PS_UDP pUDP)	// \arg  pointer to a UDP controller +{ +  return pUDP->UDP_ISR; +} + +// ---------------------------------------------------------------------------- +//  \fn    AT91F_UDP_InterruptClearRegister +//  \brief Clear Interrupt Register +// ---------------------------------------------------------------------------- +static inline void +AT91F_UDP_InterruptClearRegister (AT91PS_UDP pUDP,	// \arg pointer to UDP controller +				  unsigned int flag)	// \arg IT to be cleat +{ +  pUDP->UDP_ICR = flag; +} + +// ---------------------------------------------------------------------------- +//  \fn    AT91F_UDP_EnableTransceiver +//  \brief Enable transceiver +// ---------------------------------------------------------------------------- +static inline void +AT91F_UDP_EnableTransceiver (AT91PS_UDP pUDP)	// \arg  pointer to a UDP controller +{ +  pUDP->UDP_TXVC &= ~AT91C_UDP_TXVDIS; +} + +// ---------------------------------------------------------------------------- +//  \fn    AT91F_UDP_DisableTransceiver +//  \brief Disable transceiver +// ---------------------------------------------------------------------------- +static inline void +AT91F_UDP_DisableTransceiver (AT91PS_UDP pUDP)	// \arg  pointer to a UDP controller +{ +  pUDP->UDP_TXVC = AT91C_UDP_TXVDIS; +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_DBGU_CfgPMC +//* \brief Enable Peripheral clock in PMC for  DBGU +//*---------------------------------------------------------------------------- +static inline void +AT91F_DBGU_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_SYS)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_DBGU_CfgPIO +//* \brief Configure PIO controllers to drive DBGU signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_DBGU_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       ((unsigned int) AT91C_PA9_DRXD) | ((unsigned int) AT91C_PA10_DTXD),	// Peripheral A +		       0);	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_CfgPMC +//* \brief Enable Peripheral clock in PMC for  PMC +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_SYS)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PMC_CfgPIO +//* \brief Configure PIO controllers to drive PMC signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_PMC_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       0,	// Peripheral A +		       ((unsigned int) AT91C_PA6_PCK0) | ((unsigned int) AT91C_PA18_PCK2) | ((unsigned int) AT91C_PA31_PCK2) | ((unsigned int) AT91C_PA21_PCK1) | ((unsigned int) AT91C_PA17_PCK1));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_VREG_CfgPMC +//* \brief Enable Peripheral clock in PMC for  VREG +//*---------------------------------------------------------------------------- +static inline void +AT91F_VREG_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_SYS)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_RSTC_CfgPMC +//* \brief Enable Peripheral clock in PMC for  RSTC +//*---------------------------------------------------------------------------- +static inline void +AT91F_RSTC_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_SYS)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_CfgPMC +//* \brief Enable Peripheral clock in PMC for  SSC +//*---------------------------------------------------------------------------- +static inline void +AT91F_SSC_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_SSC)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SSC_CfgPIO +//* \brief Configure PIO controllers to drive SSC signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_SSC_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       ((unsigned int) AT91C_PA19_RK) | ((unsigned int) AT91C_PA16_TK) | ((unsigned int) AT91C_PA15_TF) | ((unsigned int) AT91C_PA18_RD) | ((unsigned int) AT91C_PA20_RF) | ((unsigned int) AT91C_PA17_TD),	// Peripheral A +		       0);	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_WDTC_CfgPMC +//* \brief Enable Peripheral clock in PMC for  WDTC +//*---------------------------------------------------------------------------- +static inline void +AT91F_WDTC_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_SYS)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US1_CfgPMC +//* \brief Enable Peripheral clock in PMC for  US1 +//*---------------------------------------------------------------------------- +static inline void +AT91F_US1_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_US1)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US1_CfgPIO +//* \brief Configure PIO controllers to drive US1 signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_US1_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       ((unsigned int) AT91C_PA29_RI1) | ((unsigned int) AT91C_PA26_DCD1) | ((unsigned int) AT91C_PA28_DSR1) | ((unsigned int) AT91C_PA27_DTR1) | ((unsigned int) AT91C_PA23_SCK1) | ((unsigned int) AT91C_PA24_RTS1) | ((unsigned int) AT91C_PA22_TXD1) | ((unsigned int) AT91C_PA21_RXD1) | ((unsigned int) AT91C_PA25_CTS1),	// Peripheral A +		       0);	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US0_CfgPMC +//* \brief Enable Peripheral clock in PMC for  US0 +//*---------------------------------------------------------------------------- +static inline void +AT91F_US0_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_US0)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_US0_CfgPIO +//* \brief Configure PIO controllers to drive US0 signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_US0_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       ((unsigned int) AT91C_PA5_RXD0) | ((unsigned int) AT91C_PA8_CTS0) | ((unsigned int) AT91C_PA7_RTS0) | ((unsigned int) AT91C_PA6_TXD0),	// Peripheral A +		       ((unsigned int) AT91C_PA2_SCK0));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_CfgPMC +//* \brief Enable Peripheral clock in PMC for  SPI +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_SPI)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_SPI_CfgPIO +//* \brief Configure PIO controllers to drive SPI signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_SPI_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       ((unsigned int) AT91C_PA13_MOSI) | ((unsigned int) AT91C_PA31_NPCS1) | ((unsigned int) AT91C_PA14_SPCK) | ((unsigned int) AT91C_PA11_NPCS0) | ((unsigned int) AT91C_PA12_MISO),	// Peripheral A +		       ((unsigned int) AT91C_PA9_NPCS1) | ((unsigned int) AT91C_PA22_NPCS3) | ((unsigned int) AT91C_PA3_NPCS3) | ((unsigned int) AT91C_PA5_NPCS3) | ((unsigned int) AT91C_PA10_NPCS2) | ((unsigned int) AT91C_PA30_NPCS2));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PITC_CfgPMC +//* \brief Enable Peripheral clock in PMC for  PITC +//*---------------------------------------------------------------------------- +static inline void +AT91F_PITC_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_SYS)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_CfgPMC +//* \brief Enable Peripheral clock in PMC for  AIC +//*---------------------------------------------------------------------------- +static inline void +AT91F_AIC_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_FIQ) | +			       ((unsigned int) 1 << AT91C_ID_IRQ0) | +			       ((unsigned int) 1 << AT91C_ID_IRQ1)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_AIC_CfgPIO +//* \brief Configure PIO controllers to drive AIC signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_AIC_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       ((unsigned int) AT91C_PA30_IRQ1),	// Peripheral A +		       ((unsigned int) AT91C_PA20_IRQ0) | ((unsigned int) AT91C_PA19_FIQ));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TWI_CfgPMC +//* \brief Enable Peripheral clock in PMC for  TWI +//*---------------------------------------------------------------------------- +static inline void +AT91F_TWI_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_TWI)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TWI_CfgPIO +//* \brief Configure PIO controllers to drive TWI signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_TWI_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       ((unsigned int) AT91C_PA4_TWCK) | ((unsigned int) AT91C_PA3_TWD),	// Peripheral A +		       0);	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWMC_CH3_CfgPIO +//* \brief Configure PIO controllers to drive PWMC_CH3 signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_CH3_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       0,	// Peripheral A +		       ((unsigned int) AT91C_PA7_PWM3) | ((unsigned int) AT91C_PA14_PWM3));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWMC_CH2_CfgPIO +//* \brief Configure PIO controllers to drive PWMC_CH2 signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_CH2_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       ((unsigned int) AT91C_PA2_PWM2),	// Peripheral A +		       ((unsigned int) AT91C_PA13_PWM2) | ((unsigned int) AT91C_PA25_PWM2));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWMC_CH1_CfgPIO +//* \brief Configure PIO controllers to drive PWMC_CH1 signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_CH1_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       ((unsigned int) AT91C_PA1_PWM1),	// Peripheral A +		       ((unsigned int) AT91C_PA24_PWM1) | ((unsigned int) AT91C_PA12_PWM1));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWMC_CH0_CfgPIO +//* \brief Configure PIO controllers to drive PWMC_CH0 signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_CH0_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       ((unsigned int) AT91C_PA0_PWM0),	// Peripheral A +		       ((unsigned int) AT91C_PA23_PWM0) | ((unsigned int) AT91C_PA11_PWM0));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_CfgPMC +//* \brief Enable Peripheral clock in PMC for  ADC +//*---------------------------------------------------------------------------- +static inline void +AT91F_ADC_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_ADC)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_ADC_CfgPIO +//* \brief Configure PIO controllers to drive ADC signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_ADC_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       0,	// Peripheral A +		       ((unsigned int) AT91C_PA8_ADTRG));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_RTTC_CfgPMC +//* \brief Enable Peripheral clock in PMC for  RTTC +//*---------------------------------------------------------------------------- +static inline void +AT91F_RTTC_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_SYS)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_UDP_CfgPMC +//* \brief Enable Peripheral clock in PMC for  UDP +//*---------------------------------------------------------------------------- +static inline void +AT91F_UDP_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_UDP)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TC0_CfgPMC +//* \brief Enable Peripheral clock in PMC for  TC0 +//*---------------------------------------------------------------------------- +static inline void +AT91F_TC0_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_TC0)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TC0_CfgPIO +//* \brief Configure PIO controllers to drive TC0 signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_TC0_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       0,	// Peripheral A +		       ((unsigned int) AT91C_PA0_TIOA0) | ((unsigned int) AT91C_PA4_TCLK0) | ((unsigned int) AT91C_PA1_TIOB0));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TC1_CfgPMC +//* \brief Enable Peripheral clock in PMC for  TC1 +//*---------------------------------------------------------------------------- +static inline void +AT91F_TC1_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_TC1)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TC1_CfgPIO +//* \brief Configure PIO controllers to drive TC1 signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_TC1_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       0,	// Peripheral A +		       ((unsigned int) AT91C_PA15_TIOA1) | ((unsigned int) AT91C_PA28_TCLK1) | ((unsigned int) AT91C_PA16_TIOB1));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TC2_CfgPMC +//* \brief Enable Peripheral clock in PMC for  TC2 +//*---------------------------------------------------------------------------- +static inline void +AT91F_TC2_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_TC2)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_TC2_CfgPIO +//* \brief Configure PIO controllers to drive TC2 signals +//*---------------------------------------------------------------------------- +static inline void +AT91F_TC2_CfgPIO (void) +{ +  // Configure PIO controllers to periph mode +  AT91F_PIO_CfgPeriph (AT91C_BASE_PIOA,	// PIO controller base address +		       0,	// Peripheral A +		       ((unsigned int) AT91C_PA27_TIOB2) | ((unsigned int) AT91C_PA26_TIOA2) | ((unsigned int) AT91C_PA29_TCLK2));	// Peripheral B +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_MC_CfgPMC +//* \brief Enable Peripheral clock in PMC for  MC +//*---------------------------------------------------------------------------- +static inline void +AT91F_MC_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_SYS)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PIOA_CfgPMC +//* \brief Enable Peripheral clock in PMC for  PIOA +//*---------------------------------------------------------------------------- +static inline void +AT91F_PIOA_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_PIOA)); +} + +//*---------------------------------------------------------------------------- +//* \fn    AT91F_PWMC_CfgPMC +//* \brief Enable Peripheral clock in PMC for  PWMC +//*---------------------------------------------------------------------------- +static inline void +AT91F_PWMC_CfgPMC (void) +{ +  AT91F_PMC_EnablePeriphClock (AT91C_BASE_PMC,	// PIO controller base address +			       ((unsigned int) 1 << AT91C_ID_PWMC)); +} + +#define __ramfunc __attribute__ ((long_call, section (".fastrun"))) + +#endif // lib_AT91SAM7 diff --git a/openpicc/os/core/ARM7_AT91SAM7S/port.c b/openpicc/os/core/ARM7_AT91SAM7S/port.c new file mode 100644 index 0000000..75bb567 --- /dev/null +++ b/openpicc/os/core/ARM7_AT91SAM7S/port.c @@ -0,0 +1,237 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + + +/*----------------------------------------------------------- + * Implementation of functions defined in portable.h for the ARM7 port. + * + * Components that can be compiled to either ARM or THUMB mode are + * contained in this file.  The ISR routines, which can only be compiled + * to ARM mode are contained in portISR.c. + *----------------------------------------------------------*/ + +/* +	Changes from V2.5.2 +		 +	+ ulCriticalNesting is now saved as part of the task context, as is  +	  therefore added to the initial task stack during pxPortInitialiseStack. +*/ + + +/* Standard includes. */ +#include <stdlib.h> + +/* Scheduler includes. */ +#include "FreeRTOS.h" +#include "task.h" + +/* Processor constants. */ +#include "AT91SAM7.h" +#include "lib_AT91SAM7.h" + +/* Constants required to setup the task context. */ +#define portINITIAL_SPSR				( ( portSTACK_TYPE ) 0x1f )	/* System mode, ARM mode, interrupts enabled. */ +#define portTHUMB_MODE_BIT				( ( portSTACK_TYPE ) 0x20 ) +#define portINSTRUCTION_SIZE			( ( portSTACK_TYPE ) 4 ) +#define portNO_CRITICAL_SECTION_NESTING	( ( portSTACK_TYPE ) 0 ) + +/* Constants required to setup the tick ISR. */ +#define portENABLE_TIMER			( ( unsigned portCHAR ) 0x01 ) +#define portPRESCALE_VALUE			0x00 +#define portINTERRUPT_ON_MATCH		( ( unsigned portLONG ) 0x01 ) +#define portRESET_COUNT_ON_MATCH	( ( unsigned portLONG ) 0x02 ) + +/* Constants required to setup the PIT. */ +#define portPIT_CLOCK_DIVISOR			( ( unsigned portLONG ) 16 ) +#define portPIT_COUNTER_VALUE			( ( ( configCPU_CLOCK_HZ / portPIT_CLOCK_DIVISOR ) / 1000UL ) * portTICK_RATE_MS ) + +#define portINT_LEVEL_SENSITIVE  0 +#define portPIT_ENABLE      	( ( unsigned portSHORT ) 0x1 << 24 ) +#define portPIT_INT_ENABLE     	( ( unsigned portSHORT ) 0x1 << 25 ) +/*-----------------------------------------------------------*/ + +/* Setup the timer to generate the tick interrupts. */ +static void prvSetupTimerInterrupt (void); + +/*  + * The scheduler can only be started from ARM mode, so  + * vPortISRStartFirstSTask() is defined in portISR.c.  + */ +extern void vPortISRStartFirstTask (void); + +/*-----------------------------------------------------------*/ + +/*  + * Initialise the stack of a task to look exactly as if a call to  + * portSAVE_CONTEXT had been called. + * + * See header file for description.  + */ +portSTACK_TYPE * +pxPortInitialiseStack (portSTACK_TYPE * pxTopOfStack, pdTASK_CODE pxCode, +		       void *pvParameters) +{ +  portSTACK_TYPE *pxOriginalTOS; + +  pxOriginalTOS = pxTopOfStack; + +  /* Setup the initial stack of the task.  The stack is set exactly as  +     expected by the portRESTORE_CONTEXT() macro. */ + +  /* First on the stack is the return address - which in this case is the +     start of the task.  The offset is added to make the return address appear +     as it would within an IRQ ISR. */ +  *pxTopOfStack = (portSTACK_TYPE) pxCode + portINSTRUCTION_SIZE; +  pxTopOfStack--; + +  *pxTopOfStack = (portSTACK_TYPE) 0xaaaaaaaa;	/* R14 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) pxOriginalTOS;	/* Stack used when task starts goes in R13. */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x12121212;	/* R12 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x11111111;	/* R11 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x10101010;	/* R10 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x09090909;	/* R9 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x08080808;	/* R8 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x07070707;	/* R7 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x06060606;	/* R6 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x05050505;	/* R5 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x04040404;	/* R4 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x03030303;	/* R3 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x02020202;	/* R2 */ +  pxTopOfStack--; +  *pxTopOfStack = (portSTACK_TYPE) 0x01010101;	/* R1 */ +  pxTopOfStack--; + +  /* When the task starts is will expect to find the function parameter in +     R0. */ +  *pxTopOfStack = (portSTACK_TYPE) pvParameters;	/* R0 */ +  pxTopOfStack--; + +  /* The last thing onto the stack is the status register, which is set for +     system mode, with interrupts enabled. */ +  *pxTopOfStack = (portSTACK_TYPE) portINITIAL_SPSR; + +#ifdef THUMB_INTERWORK +  { +    /* We want the task to start in thumb mode. */ +    *pxTopOfStack |= portTHUMB_MODE_BIT; +  } +#endif + +  pxTopOfStack--; + +  /* Some optimisation levels use the stack differently to others.  This  +     means the interrupt flags cannot always be stored on the stack and will +     instead be stored in a variable, which is then saved as part of the +     tasks context. */ +  *pxTopOfStack = portNO_CRITICAL_SECTION_NESTING; + +  return pxTopOfStack; +} + +/*-----------------------------------------------------------*/ + +portBASE_TYPE +xPortStartScheduler (void) +{ +  /* Start the timer that generates the tick ISR.  Interrupts are disabled +     here already. */ +  prvSetupTimerInterrupt (); + +  /* Start the first task. */ +  vPortISRStartFirstTask (); + +  /* Should not get here! */ +  return 0; +} + +/*-----------------------------------------------------------*/ + +void +vPortEndScheduler (void) +{ +  /* It is unlikely that the ARM port will require this function as there +     is nothing to return to.  */ +} + +/*-----------------------------------------------------------*/ + +/* + * Setup the timer 0 to generate the tick interrupts at the required frequency. + */ +static void +prvSetupTimerInterrupt (void) +{ +  AT91PS_PITC pxPIT = AT91C_BASE_PITC; + +  /* Setup the AIC for PIT interrupts.  The interrupt routine chosen depends +     on whether the preemptive or cooperative scheduler is being used. */ +#if configUSE_PREEMPTION == 0 + +  extern void (vNonPreemptiveTick) (void); +  AT91F_AIC_ConfigureIt (AT91C_ID_SYS, AT91C_AIC_PRIOR_HIGHEST, +			 portINT_LEVEL_SENSITIVE, +			 (void (*)(void)) vNonPreemptiveTick); + +#else + +  extern void (vPreemptiveTick) (void); +  AT91F_AIC_ConfigureIt (AT91C_ID_SYS, AT91C_AIC_PRIOR_HIGHEST, +			 portINT_LEVEL_SENSITIVE, +			 (void (*)(void)) vPreemptiveTick); + +#endif + +  /* Configure the PIT period. */ +  pxPIT->PITC_PIMR = +    portPIT_ENABLE | portPIT_INT_ENABLE | portPIT_COUNTER_VALUE; + +  /* Enable the interrupt.  Global interrupts are disables at this point so  +     this is safe. */ +  AT91C_BASE_AIC->AIC_IECR = 0x1 << AT91C_ID_SYS; +} + +/*-----------------------------------------------------------*/ diff --git a/openpicc/os/core/ARM7_AT91SAM7S/portISR.c b/openpicc/os/core/ARM7_AT91SAM7S/portISR.c new file mode 100644 index 0000000..507712e --- /dev/null +++ b/openpicc/os/core/ARM7_AT91SAM7S/portISR.c @@ -0,0 +1,239 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + + +/*----------------------------------------------------------- + * Components that can be compiled to either ARM or THUMB mode are + * contained in port.c  The ISR routines, which can only be compiled + * to ARM mode, are contained in this file. + *----------------------------------------------------------*/ + +/* +	Changes from V3.2.4 + +	+ The assembler statements are now included in a single asm block rather +	  than each line having its own asm block. +*/ + +/* Scheduler includes. */ +#include "FreeRTOS.h" +#include "task.h" + +#include "AT91SAM7.h" + +/* Constants required to handle interrupts. */ +#define portTIMER_MATCH_ISR_BIT		( ( unsigned portCHAR ) 0x01 ) +#define portCLEAR_VIC_INTERRUPT		( ( unsigned portLONG ) 0 ) + +/* Constants required to handle critical sections. */ +#define portNO_CRITICAL_NESTING		( ( unsigned portLONG ) 0 ) +volatile unsigned portLONG ulCriticalNesting = 9999UL; + +/*-----------------------------------------------------------*/ + +/* ISR to handle manual context switches (from a call to taskYIELD()). */ +void vPortYieldProcessor (void) __attribute__ ((interrupt ("SWI"), naked)); + +/*  + * The scheduler can only be started from ARM mode, hence the inclusion of this + * function here. + */ +void vPortISRStartFirstTask (void); +/*-----------------------------------------------------------*/ + +void +vPortISRStartFirstTask (void) +{ +  /* Simply start the scheduler.  This is included here as it can only be +     called from ARM mode. */ +  portRESTORE_CONTEXT (); +} + +/*-----------------------------------------------------------*/ + +/* + * Called by portYIELD() or taskYIELD() to manually force a context switch. + * + * When a context switch is performed from the task level the saved task  + * context is made to look as if it occurred from within the tick ISR.  This + * way the same restore context function can be used when restoring the context + * saved from the ISR or that saved from a call to vPortYieldProcessor. + */ +void +vPortYieldProcessor (void) +{ +  /* Within an IRQ ISR the link register has an offset from the true return  +     address, but an SWI ISR does not.  Add the offset manually so the same  +     ISR return code can be used in both cases. */ +  asm volatile ("ADD		LR, LR, #4"); + +  /* Perform the context switch.  First save the context of the current task. */ +  portSAVE_CONTEXT (); + +  /* Find the highest priority task that is ready to run. */ +  vTaskSwitchContext (); + +  /* Restore the context of the new task. */ +  portRESTORE_CONTEXT (); +} + +/*-----------------------------------------------------------*/ + +/*  + * The ISR used for the scheduler tick depends on whether the cooperative or + * the preemptive scheduler is being used. + */ + +#if configUSE_PREEMPTION == 0 + +	/* The cooperative scheduler requires a normal IRQ service routine to  +	   simply increment the system tick. */ +void vNonPreemptiveTick (void) __attribute__ ((interrupt ("IRQ"))); +void +vNonPreemptiveTick (void) +{ +  unsigned portLONG ulDummy; + +  /* Increment the tick count - which may wake some tasks but as the +     preemptive scheduler is not being used any woken task is not given +     processor time no matter what its priority. */ +  vTaskIncrementTick (); + +  /* Clear the PIT interrupt. */ +  ulDummy = AT91C_BASE_PITC->PITC_PIVR; + +  /* End the interrupt in the AIC. */ +  AT91C_BASE_AIC->AIC_EOICR = ulDummy; +} + +#else + +	/* The preemptive scheduler is defined as "naked" as the full context is +	   saved on entry as part of the context switch. */ +void vPreemptiveTick (void) __attribute__ ((naked)); +void +vPreemptiveTick (void) +{ +  /* Save the context of the current task. */ +  portSAVE_CONTEXT (); + +  /* Increment the tick count - this may wake a task. */ +  vTaskIncrementTick (); + +  /* Find the highest priority task that is ready to run. */ +  vTaskSwitchContext (); + +  /* End the interrupt in the AIC. */ +  AT91C_BASE_AIC->AIC_EOICR = AT91C_BASE_PITC->PITC_PIVR;; + +  portRESTORE_CONTEXT (); +} + +#endif +/*-----------------------------------------------------------*/ + +/* + * The interrupt management utilities can only be called from ARM mode.  When + * THUMB_INTERWORK is defined the utilities are defined as functions here to + * ensure a switch to ARM mode.  When THUMB_INTERWORK is not defined then + * the utilities are defined as macros in portmacro.h - as per other ports. + */ +void vPortDisableInterruptsFromThumb (void) __attribute__ ((naked)); +void vPortEnableInterruptsFromThumb (void) __attribute__ ((naked)); + +void +vPortDisableInterruptsFromThumb (void) +{ +  asm volatile ("STMDB	SP!, {R0}		\n\t"	/* Push R0.                                                                     */ +		"MRS	R0, CPSR		\n\t"	/* Get CPSR.                                                            */ +		"ORR	R0, R0, #0xC0	\n\t"	/* Disable IRQ, FIQ.                                            */ +		"MSR	CPSR, R0		\n\t"	/* Write back modified value.                           */ +		"LDMIA	SP!, {R0}		\n\t"	/* Pop R0.                                                                      */ +		"BX		R14");	/* Return back to thumb.                                        */ +} + +void +vPortEnableInterruptsFromThumb (void) +{ +  asm volatile ("STMDB	SP!, {R0}		\n\t"	/* Push R0.                                                                     */ +		"MRS	R0, CPSR		\n\t"	/* Get CPSR.                                                            */ +		"BIC	R0, R0, #0xC0	\n\t"	/* Enable IRQ, FIQ.                                                     */ +		"MSR	CPSR, R0		\n\t"	/* Write back modified value.                           */ +		"LDMIA	SP!, {R0}		\n\t"	/* Pop R0.                                                                      */ +		"BX		R14");	/* Return back to thumb.                                        */ +} + + +/* The code generated by the GCC compiler uses the stack in different ways at +different optimisation levels.  The interrupt flags can therefore not always +be saved to the stack.  Instead the critical section nesting level is stored +in a variable, which is then saved as part of the stack context. */ +void +vPortEnterCritical (void) +{ +  /* Disable interrupts as per portDISABLE_INTERRUPTS();                                                  */ +  asm volatile ("STMDB	SP!, {R0}			\n\t"	/* Push R0.                                                             */ +		"MRS	R0, CPSR			\n\t"	/* Get CPSR.                                                    */ +		"ORR	R0, R0, #0xC0		\n\t"	/* Disable IRQ, FIQ.                                    */ +		"MSR	CPSR, R0			\n\t"	/* Write back modified value.                   */ +		"LDMIA	SP!, {R0}");	/* Pop R0.                                                              */ + +  /* Now interrupts are disabled ulCriticalNesting can be accessed  +     directly.  Increment ulCriticalNesting to keep a count of how many times +     portENTER_CRITICAL() has been called. */ +  ulCriticalNesting++; +} + +void +vPortExitCritical (void) +{ +  if (ulCriticalNesting > portNO_CRITICAL_NESTING) +    { +      /* Decrement the nesting count as we are leaving a critical section. */ +      ulCriticalNesting--; + +      /* If the nesting level has reached zero then interrupts should be +         re-enabled. */ +      if (ulCriticalNesting == portNO_CRITICAL_NESTING) +	{ +	  /* Enable interrupts as per portEXIT_CRITICAL().                                        */ +	  asm volatile ("STMDB	SP!, {R0}		\n\t"	/* Push R0.                                             */ +			"MRS	R0, CPSR		\n\t"	/* Get CPSR.                                    */ +			"BIC	R0, R0, #0xC0	\n\t"	/* Enable IRQ, FIQ.                             */ +			"MSR	CPSR, R0		\n\t"	/* Write back modified value.   */ +			"LDMIA	SP!, {R0}");	/* Pop R0.                                              */ +	} +    } +} diff --git a/openpicc/os/core/ARM7_AT91SAM7S/portmacro.h b/openpicc/os/core/ARM7_AT91SAM7S/portmacro.h new file mode 100644 index 0000000..6b25ec5 --- /dev/null +++ b/openpicc/os/core/ARM7_AT91SAM7S/portmacro.h @@ -0,0 +1,266 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +/* +	Changes from V3.2.3 +	 +	+ Modified portENTER_SWITCHING_ISR() to allow use with GCC V4.0.1. + +	Changes from V3.2.4 + +	+ Removed the use of the %0 parameter within the assembler macros and  +	  replaced them with hard coded registers.  This will ensure the +	  assembler does not select the link register as the temp register as +	  was occasionally happening previously. + +	+ The assembler statements are now included in a single asm block rather +	  than each line having its own asm block. +*/ + +#ifndef PORTMACRO_H +#define PORTMACRO_H + +/*----------------------------------------------------------- + * Port specific definitions.   + * + * The settings in this file configure FreeRTOS correctly for the + * given hardware and compiler. + * + * These settings should not be altered. + *----------------------------------------------------------- + */ + +/* Type definitions. */ +#define portCHAR		char +#define portFLOAT		float +#define portDOUBLE		double +#define portLONG		long +#define portSHORT		short +#define portSTACK_TYPE	unsigned portLONG +#define portBASE_TYPE	portLONG + +#if( configUSE_16_BIT_TICKS == 1 ) +typedef unsigned portSHORT portTickType; +#define portMAX_DELAY ( portTickType ) 0xffff +#else +typedef unsigned portLONG portTickType; +#define portMAX_DELAY ( portTickType ) 0xffffffff +#endif +/*-----------------------------------------------------------*/ + +/* Architecture specifics. */ +#define portSTACK_GROWTH			( -1 ) +#define portTICK_RATE_MS			( ( portTickType ) 1000 / configTICK_RATE_HZ ) +#define portBYTE_ALIGNMENT			4 +#define portNOP()					asm volatile ( "NOP" ); +/*-----------------------------------------------------------*/ + + +/* Scheduler utilities. */ + +/* + * portRESTORE_CONTEXT, portRESTORE_CONTEXT, portENTER_SWITCHING_ISR + * and portEXIT_SWITCHING_ISR can only be called from ARM mode, but + * are included here for efficiency.  An attempt to call one from + * THUMB mode code will result in a compile time error. + */ + +#define portRESTORE_CONTEXT()											\ +{																		\ +extern volatile void * volatile pxCurrentTCB;							\ +extern volatile unsigned portLONG ulCriticalNesting;					\ +																		\ +	/* Set the LR to the task stack. */									\ +	asm volatile (														\ +	"LDR		R0, =pxCurrentTCB								\n\t"	\ +	"LDR		R0, [R0]										\n\t"	\ +	"LDR		LR, [R0]										\n\t"	\ +																		\ +	/* The critical nesting depth is the first item on the stack. */	\ +	/* Load it into the ulCriticalNesting variable. */					\ +	"LDR		R0, =ulCriticalNesting							\n\t"	\ +	"LDMFD	LR!, {R1}											\n\t"	\ +	"STR		R1, [R0]										\n\t"	\ +																		\ +	/* Get the SPSR from the stack. */									\ +	"LDMFD	LR!, {R0}											\n\t"	\ +	"MSR		SPSR, R0										\n\t"	\ +																		\ +	/* Restore all system mode registers for the task. */				\ +	"LDMFD	LR, {R0-R14}^										\n\t"	\ +	"NOP														\n\t"	\ +																		\ +	/* Restore the return address. */									\ +	"LDR		LR, [LR, #+60]									\n\t"	\ +																		\ +	/* And return - correcting the offset in the LR to obtain the */	\ +	/* correct address. */												\ +	"SUBS	PC, LR, #4											\n\t"	\ +	);																	\ +	( void ) ulCriticalNesting;											\ +	( void ) pxCurrentTCB;												\ +} +/*-----------------------------------------------------------*/ + +#define portSAVE_CONTEXT()												\ +{																		\ +extern volatile void * volatile pxCurrentTCB;							\ +extern volatile unsigned portLONG ulCriticalNesting;					\ +																		\ +	/* Push R0 as we are going to use the register. */					\ +	asm volatile (														\ +	"STMDB	SP!, {R0}											\n\t"	\ +																		\ +	/* Set R0 to point to the task stack pointer. */					\ +	"STMDB	SP,{SP}^											\n\t"	\ +	"NOP														\n\t"	\ +	"SUB	SP, SP, #4											\n\t"	\ +	"LDMIA	SP!,{R0}											\n\t"	\ +																		\ +	/* Push the return address onto the stack. */						\ +	"STMDB	R0!, {LR}											\n\t"	\ +																		\ +	/* Now we have saved LR we can use it instead of R0. */				\ +	"MOV	LR, R0												\n\t"	\ +																		\ +	/* Pop R0 so we can save it onto the system mode stack. */			\ +	"LDMIA	SP!, {R0}											\n\t"	\ +																		\ +	/* Push all the system mode registers onto the task stack. */		\ +	"STMDB	LR,{R0-LR}^											\n\t"	\ +	"NOP														\n\t"	\ +	"SUB	LR, LR, #60											\n\t"	\ +																		\ +	/* Push the SPSR onto the task stack. */							\ +	"MRS	R0, SPSR											\n\t"	\ +	"STMDB	LR!, {R0}											\n\t"	\ +																		\ +	"LDR	R0, =ulCriticalNesting								\n\t"	\ +	"LDR	R0, [R0]											\n\t"	\ +	"STMDB	LR!, {R0}											\n\t"	\ +																		\ +	/* Store the new top of stack for the task. */						\ +	"LDR	R0, =pxCurrentTCB									\n\t"	\ +	"LDR	R0, [R0]											\n\t"	\ +	"STR	LR, [R0]											\n\t"	\ +	);																	\ +	( void ) ulCriticalNesting;											\ +	( void ) pxCurrentTCB;												\ +} + + +/*----------------------------------------------------------- + * ISR entry and exit macros.  These are only required if a task switch + * is required from the ISR. + *----------------------------------------------------------*/ + + +#define portENTER_SWITCHING_ISR()										\ +	/* Save the context of the interrupted task. */						\ +	portSAVE_CONTEXT();													\ +																		\ +	/* We don't know the stack requirements for the ISR, so the frame */\ +	/* pointer will be set to the top of the task stack, and the stack*/\ +	/* pointer left where it is.  The IRQ stack will get used for any */\ +	/* functions calls made by this ISR. */								\ +	asm volatile ( "SUB		R11, LR, #4" );							\ +	{ + +#define portEXIT_SWITCHING_ISR( SwitchRequired )						\ +		/* If a switch is required then we just need to call */			\ +		/* vTaskSwitchContext() as the context has already been */		\ +		/* saved. */													\ +		if( SwitchRequired )											\ +		{																\ +			vTaskSwitchContext();										\ +		}																\ +	}																	\ +	/* Restore the context of which ever task is now the highest */		\ +	/* priority that is ready to run. */								\ +	portRESTORE_CONTEXT(); + +#define portYIELD()					asm volatile ( "SWI" ); +/*-----------------------------------------------------------*/ + + +/* Critical section management. */ + +/* + * The interrupt management utilities can only be called from ARM mode.  When + * THUMB_INTERWORK is defined the utilities are defined as functions in  + * portISR.c to ensure a switch to ARM mode.  When THUMB_INTERWORK is not  + * defined then the utilities are defined as macros here - as per other ports. + */ + +#ifdef THUMB_INTERWORK + +extern void vPortDisableInterruptsFromThumb (void) __attribute__ ((naked)); +extern void vPortEnableInterruptsFromThumb (void) __attribute__ ((naked)); + +#define portDISABLE_INTERRUPTS()	vPortDisableInterruptsFromThumb() +#define portENABLE_INTERRUPTS()		vPortEnableInterruptsFromThumb() + +#else + +#define portDISABLE_INTERRUPTS()											\ +		asm volatile (															\ +			"STMDB	SP!, {R0}		\n\t"	/* Push R0.						*/	\ +			"MRS	R0, CPSR		\n\t"	/* Get CPSR.					*/	\ +			"ORR	R0, R0, #0xC0	\n\t"	/* Disable IRQ, FIQ.			*/	\ +			"MSR	CPSR, R0		\n\t"	/* Write back modified value.	*/	\ +			"LDMIA	SP!, {R0}			" )	/* Pop R0.                                              */ + +#define portENABLE_INTERRUPTS()												\ +		asm volatile (															\ +			"STMDB	SP!, {R0}		\n\t"	/* Push R0.						*/	\ +			"MRS	R0, CPSR		\n\t"	/* Get CPSR.					*/	\ +			"BIC	R0, R0, #0xC0	\n\t"	/* Enable IRQ, FIQ.				*/	\ +			"MSR	CPSR, R0		\n\t"	/* Write back modified value.	*/	\ +			"LDMIA	SP!, {R0}			" )	/* Pop R0.                                              */ + +#endif /* THUMB_INTERWORK */ + +extern void vPortEnterCritical (void); +extern void vPortExitCritical (void); + +#define portENTER_CRITICAL()		vPortEnterCritical(); +#define portEXIT_CRITICAL()			vPortExitCritical(); +/*-----------------------------------------------------------*/ + +/* Task function macros as described on the FreeRTOS.org WEB site. */ +#define portTASK_FUNCTION_PROTO( vFunction, pvParameters ) void vFunction( void *pvParameters ) +#define portTASK_FUNCTION( vFunction, pvParameters ) void vFunction( void *pvParameters ) + +#endif /* PORTMACRO_H */ diff --git a/openpicc/os/core/MemMang/heap_1.c b/openpicc/os/core/MemMang/heap_1.c new file mode 100644 index 0000000..8370479 --- /dev/null +++ b/openpicc/os/core/MemMang/heap_1.c @@ -0,0 +1,143 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +/*  + +Changes between V2.5.1 and V2.5.1 + +	+ The memory pool has been defined within a struct to ensure correct memory +	  alignment on 32bit systems. + +Changes between V2.6.1 and V3.0.0 + +	+ An overflow check has been added to ensure the next free byte variable  +	  does not wrap around. +*/ + + +/* + * The simplest possible implementation of pvPortMalloc().  Note that this + * implementation does NOT allow allocated memory to be freed again. + * + * See heap_2.c and heap_3.c for alternative implementations, and the memory + * management pages of http://www.FreeRTOS.org for more information. + */ +#include <stdlib.h> +#include "FreeRTOS.h" +#include "task.h" + +/* Setup the correct byte alignment mask for the defined byte alignment. */ + +#if portBYTE_ALIGNMENT == 8 +#define heapBYTE_ALIGNMENT_MASK ( ( size_t ) 0x0007 ) +#endif + +#if portBYTE_ALIGNMENT == 4 +#define heapBYTE_ALIGNMENT_MASK	( ( size_t ) 0x0003 ) +#endif + +#if portBYTE_ALIGNMENT == 2 +#define heapBYTE_ALIGNMENT_MASK	( ( size_t ) 0x0001 ) +#endif + +#if portBYTE_ALIGNMENT == 1 +#define heapBYTE_ALIGNMENT_MASK	( ( size_t ) 0x0000 ) +#endif + +#ifndef heapBYTE_ALIGNMENT_MASK +#error "Invalid portBYTE_ALIGNMENT definition" +#endif + +/* Allocate the memory for the heap.  The struct is used to force byte +alignment without using any non-portable code. */ +static struct xRTOS_HEAP +{ +  unsigned portLONG ulDummy; +  unsigned portCHAR ucHeap[configTOTAL_HEAP_SIZE]; +} xHeap; + +static size_t xNextFreeByte = (size_t) 0; +/*-----------------------------------------------------------*/ + +void * +pvPortMalloc (size_t xWantedSize) +{ +  void *pvReturn = NULL; + +  /* Ensure that blocks are always aligned to the required number of bytes. */ +#if portBYTE_ALIGNMENT != 1 +  if (xWantedSize & heapBYTE_ALIGNMENT_MASK) +    { +      /* Byte alignment required. */ +      xWantedSize += +	(portBYTE_ALIGNMENT - (xWantedSize & heapBYTE_ALIGNMENT_MASK)); +    } +#endif + +  vTaskSuspendAll (); +  { +    /* Check there is enough room left for the allocation. */ +    if (((xNextFreeByte + xWantedSize) < configTOTAL_HEAP_SIZE) && ((xNextFreeByte + xWantedSize) > xNextFreeByte))	/* Check for overflow. */ +      { +	/* Return the next free byte then increment the index past this +	   block. */ +	pvReturn = &(xHeap.ucHeap[xNextFreeByte]); +	xNextFreeByte += xWantedSize; +      } +  } +  xTaskResumeAll (); + +  return pvReturn; +} + +/*-----------------------------------------------------------*/ + +void +vPortFree (void *pv) +{ +  /* Memory cannot be freed using this scheme.  See heap_2.c and heap_3.c  +     for alternative implementations, and the memory management pages of  +     http://www.FreeRTOS.org for more information. */ +  (void) pv; +} + +/*-----------------------------------------------------------*/ + +void +vPortInitialiseBlocks (void) +{ +  /* Only required when static memory is not cleared. */ +  xNextFreeByte = (size_t) 0; +} diff --git a/openpicc/os/core/MemMang/heap_2.c b/openpicc/os/core/MemMang/heap_2.c new file mode 100644 index 0000000..0b74d44 --- /dev/null +++ b/openpicc/os/core/MemMang/heap_2.c @@ -0,0 +1,255 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license +	and contact details.  Please ensure to read the configuration and relevant +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +/* + * A sample implementation of pvPortMalloc() and vPortFree() that permits + * allocated blocks to be freed, but does not combine adjacent free blocks + * into a single larger block. + * + * See heap_1.c and heap_3.c for alternative implementations, and the memory + * management pages of http://www.FreeRTOS.org for more information. + */ +#include <stdlib.h> + +#include "FreeRTOS.h" +#include "task.h" + +/* Setup the correct byte alignment mask for the defined byte alignment. */ + +#if portBYTE_ALIGNMENT == 8 +#define heapBYTE_ALIGNMENT_MASK ( ( size_t ) 0x0007 ) +#endif + +#if portBYTE_ALIGNMENT == 4 +#define heapBYTE_ALIGNMENT_MASK	( ( size_t ) 0x0003 ) +#endif + +#if portBYTE_ALIGNMENT == 2 +#define heapBYTE_ALIGNMENT_MASK	( ( size_t ) 0x0001 ) +#endif + +#if portBYTE_ALIGNMENT == 1 +#define heapBYTE_ALIGNMENT_MASK	( ( size_t ) 0x0000 ) +#endif + +#ifndef heapBYTE_ALIGNMENT_MASK +#error "Invalid portBYTE_ALIGNMENT definition" +#endif + +/* Allocate the memory for the heap.  The struct is used to force byte +alignment without using any non-portable code. */ +static struct xRTOS_HEAP +{ +  unsigned portLONG ulDummy; +  unsigned portCHAR ucHeap[configTOTAL_HEAP_SIZE]; +} xHeap; + +/* Define the linked list structure.  This is used to link free blocks in order +of their size. */ +typedef struct A_BLOCK_LINK +{ +  struct A_BLOCK_LINK *pxNextFreeBlock;	/*<< The next free block in the list. */ +  size_t xBlockSize;		/*<< The size of the free block. */ +} xBlockLink; + + +static const unsigned portSHORT heapSTRUCT_SIZE = +  (sizeof (xBlockLink) + (sizeof (xBlockLink) % portBYTE_ALIGNMENT)); +#define heapMINIMUM_BLOCK_SIZE	( ( size_t ) ( heapSTRUCT_SIZE * 2 ) ) + +/* Create a couple of list links to mark the start and end of the list. */ +static xBlockLink xStart, xEnd; + +/* STATIC FUNCTIONS ARE DEFINED AS MACROS TO MINIMIZE THE FUNCTION CALL DEPTH. */ + +/* + * Insert a block into the list of free blocks - which is ordered by size of + * the block.  Small blocks at the start of the list and large blocks at the end + * of the list. + */ +#define prvInsertBlockIntoFreeList( pxBlockToInsert )								\ +{																					\ +xBlockLink *pxIterator;																\ +size_t xBlockSize;																	\ +																					\ +	xBlockSize = pxBlockToInsert->xBlockSize;										\ +																					\ +	/* Iterate through the list until a block is found that has a larger size */	\ +	/* than the block we are inserting. */											\ +	for( pxIterator = &xStart; pxIterator->pxNextFreeBlock->xBlockSize < xBlockSize; pxIterator = pxIterator->pxNextFreeBlock )	\ +	{																				\ +		/* There is nothing to do here - just iterate to the correct position. */	\ +	}																				\ +																					\ +	/* Update the list to include the block being inserted in the correct */		\ +	/* position. */																	\ +	pxBlockToInsert->pxNextFreeBlock = pxIterator->pxNextFreeBlock;					\ +	pxIterator->pxNextFreeBlock = pxBlockToInsert;									\ +} +/*-----------------------------------------------------------*/ + +#define prvHeapInit()																\ +{																					\ +xBlockLink *pxFirstFreeBlock;														\ +																					\ +	/* xStart is used to hold a pointer to the first item in the list of free */	\ +	/* blocks.  The void cast is used to prevent compiler warnings. */				\ +	xStart.pxNextFreeBlock = ( void * ) xHeap.ucHeap;								\ +	xStart.xBlockSize = ( size_t ) 0;												\ +																					\ +	/* xEnd is used to mark the end of the list of free blocks. */					\ +	xEnd.xBlockSize = configTOTAL_HEAP_SIZE;										\ +	xEnd.pxNextFreeBlock = NULL;													\ +																					\ +	/* To start with there is a single free block that is sized to take up the		\ +	entire heap space. */															\ +	pxFirstFreeBlock = ( void * ) xHeap.ucHeap;										\ +	pxFirstFreeBlock->xBlockSize = configTOTAL_HEAP_SIZE;							\ +	pxFirstFreeBlock->pxNextFreeBlock = &xEnd;										\ +} +/*-----------------------------------------------------------*/ + +void * +pvPortMalloc (size_t xWantedSize) +{ +  xBlockLink *pxBlock, *pxPreviousBlock, *pxNewBlockLink; +  static portBASE_TYPE xHeapHasBeenInitialised = pdFALSE; +  void *pvReturn = NULL; + +  vTaskSuspendAll (); +  { +    /* If this is the first call to malloc then the heap will require +       initialisation to setup the list of free blocks. */ +    if (xHeapHasBeenInitialised == pdFALSE) +      { +	prvHeapInit (); +	xHeapHasBeenInitialised = pdTRUE; +      } + +    /* The wanted size is increased so it can contain a xBlockLink +       structure in addition to the requested amount of bytes. */ +    if (xWantedSize > 0) +      { +	xWantedSize += heapSTRUCT_SIZE; + +	/* Ensure that blocks are always aligned to the required number of bytes. */ +	if (xWantedSize & heapBYTE_ALIGNMENT_MASK) +	  { +	    /* Byte alignment required. */ +	    xWantedSize += +	      (portBYTE_ALIGNMENT - (xWantedSize & heapBYTE_ALIGNMENT_MASK)); +	  } +      } + +    if ((xWantedSize > 0) && (xWantedSize < configTOTAL_HEAP_SIZE)) +      { +	/* Blocks are stored in byte order - traverse the list from the start +	   (smallest) block until one of adequate size is found. */ +	pxPreviousBlock = &xStart; +	pxBlock = xStart.pxNextFreeBlock; +	while ((pxBlock->xBlockSize < xWantedSize) +	       && (pxBlock->pxNextFreeBlock)) +	  { +	    pxPreviousBlock = pxBlock; +	    pxBlock = pxBlock->pxNextFreeBlock; +	  } + +	/* If we found the end marker then a block of adequate size was not found. */ +	if (pxBlock != &xEnd) +	  { +	    /* Return the memory space - jumping over the xBlockLink structure +	       at its start. */ +	    pvReturn = +	      (void +	       *) (((unsigned portCHAR *) pxPreviousBlock->pxNextFreeBlock) + +		   heapSTRUCT_SIZE); + +	    /* This block is being returned for use so must be taken our of the +	       list of free blocks. */ +	    pxPreviousBlock->pxNextFreeBlock = pxBlock->pxNextFreeBlock; + +	    /* If the block is larger than required it can be split into two. */ +	    if ((pxBlock->xBlockSize - xWantedSize) > heapMINIMUM_BLOCK_SIZE) +	      { +		/* This block is to be split into two.  Create a new block +		   following the number of bytes requested. The void cast is +		   used to prevent byte alignment warnings from the compiler. */ +		pxNewBlockLink = +		  (void *) (((unsigned portCHAR *) pxBlock) + xWantedSize); + +		/* Calculate the sizes of two blocks split from the single +		   block. */ +		pxNewBlockLink->xBlockSize = +		  pxBlock->xBlockSize - xWantedSize; +		pxBlock->xBlockSize = xWantedSize; + +		/* Insert the new block into the list of free blocks. */ +		prvInsertBlockIntoFreeList ((pxNewBlockLink)); +	      } +	  } +      } +  } +  xTaskResumeAll (); + +  return pvReturn; +} + +/*-----------------------------------------------------------*/ + +void +vPortFree (void *pv) +{ +  unsigned portCHAR *puc = (unsigned portCHAR *) pv; +  xBlockLink *pxLink; + +  if (pv) +    { +      /* The memory being freed will have an xBlockLink structure immediately +         before it. */ +      puc -= heapSTRUCT_SIZE; + +      /* This casting is to keep the compiler from issuing warnings. */ +      pxLink = (void *) puc; + +      vTaskSuspendAll (); +      { +	/* Add this block to the list of free blocks. */ +	prvInsertBlockIntoFreeList (((xBlockLink *) pxLink)); +      } +      xTaskResumeAll (); +    } +} + +/*-----------------------------------------------------------*/ diff --git a/openpicc/os/core/MemMang/heap_3.c b/openpicc/os/core/MemMang/heap_3.c new file mode 100644 index 0000000..ca1311e --- /dev/null +++ b/openpicc/os/core/MemMang/heap_3.c @@ -0,0 +1,82 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + + +/* + * Implementation of pvPortMalloc() and vPortFree() that relies on the + * compilers own malloc() and free() implementations. + * + * This file can only be used if the linker is configured to to generate + * a heap memory area. + * + * See heap_2.c and heap_1.c for alternative implementations, and the memory + * management pages of http://www.FreeRTOS.org for more information. + */ + +#include <stdlib.h> + +#include "FreeRTOS.h" +#include "task.h" + +/*-----------------------------------------------------------*/ + +void * +pvPortMalloc (size_t xWantedSize) +{ +  void *pvReturn; + +  vTaskSuspendAll (); +  { +    pvReturn = malloc (xWantedSize); +  } +  xTaskResumeAll (); + +  return pvReturn; +} + +/*-----------------------------------------------------------*/ + +void +vPortFree (void *pv) +{ +  if (pv) +    { +      vTaskSuspendAll (); +      { +	free (pv); +      } +      xTaskResumeAll (); +    } +} diff --git a/openpicc/os/core/include/FreeRTOS.h b/openpicc/os/core/include/FreeRTOS.h new file mode 100644 index 0000000..7afc084 --- /dev/null +++ b/openpicc/os/core/include/FreeRTOS.h @@ -0,0 +1,114 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef INC_FREERTOS_H +#define INC_FREERTOS_H + + +/*  + * Include the generic headers required for the FreeRTOS port being used.  + */ +#include <stddef.h> + +/* Basic FreeRTOS definitions. */ +#include "projdefs.h" + +/* Application specific configuration options. */ +#include "FreeRTOSConfig.h" + +/* Definitions specific to the port being used. */ +#include "portable.h" + + + + + + + +/* + * Check all the required application specific macros have been defined.  + * These macros are application specific and (as downloaded) are defined + * within FreeRTOSConfig.h. + */ + +#ifndef configUSE_PREEMPTION +#error Missing definition:  configUSE_PREEMPTION should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef configUSE_IDLE_HOOK +#error Missing definition:  configUSE_IDLE_HOOK should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef configUSE_TICK_HOOK +#error Missing definition:  configUSE_TICK_HOOK should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef configUSE_CO_ROUTINES +#error  Missing definition:  configUSE_CO_ROUTINES should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef INCLUDE_vTaskPrioritySet +#error Missing definition:  INCLUDE_vTaskPrioritySet should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef INCLUDE_uxTaskPriorityGet +#error Missing definition:  INCLUDE_uxTaskPriorityGet should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef INCLUDE_vTaskDelete +#error Missing definition:  INCLUDE_vTaskDelete		 should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef INCLUDE_vTaskCleanUpResources +#error Missing definition:  INCLUDE_vTaskCleanUpResources should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef INCLUDE_vTaskSuspend +#error Missing definition:  INCLUDE_vTaskSuspend	 should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef INCLUDE_vTaskDelayUntil +#error Missing definition:  INCLUDE_vTaskDelayUntil should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef INCLUDE_vTaskDelay +#error Missing definition:  INCLUDE_vTaskDelay should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#ifndef configUSE_16_BIT_TICKS +#error Missing definition:  configUSE_16_BIT_TICKS should be defined in FreeRTOSConfig.h as either 1 or 0.  See the Configuration section of the FreeRTOS API documentation for details. +#endif + +#endif diff --git a/openpicc/os/core/include/blocktim.h b/openpicc/os/core/include/blocktim.h new file mode 100644 index 0000000..a60605a --- /dev/null +++ b/openpicc/os/core/include/blocktim.h @@ -0,0 +1,42 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef BLOCK_TIME_TEST_H +#define BLOCK_TIME_TEST_H + +void vCreateBlockTimeTasks (void); +portBASE_TYPE xAreBlockTimeTestTasksStillRunning (void); + +#endif diff --git a/openpicc/os/core/include/comtest.h b/openpicc/os/core/include/comtest.h new file mode 100644 index 0000000..472e138 --- /dev/null +++ b/openpicc/os/core/include/comtest.h @@ -0,0 +1,46 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef COMTEST_H +#define COMTEST_H + +void vAltStartComTestTasks (unsigned portBASE_TYPE uxPriority, +			    unsigned portLONG ulBaudRate, +			    unsigned portBASE_TYPE uxLED); +void vStartComTestTasks (unsigned portBASE_TYPE uxPriority, eCOMPort ePort, +			 eBaud eBaudRate); +portBASE_TYPE xAreComTestTasksStillRunning (void); + +#endif diff --git a/openpicc/os/core/include/comtest2.h b/openpicc/os/core/include/comtest2.h new file mode 100644 index 0000000..1dd155d --- /dev/null +++ b/openpicc/os/core/include/comtest2.h @@ -0,0 +1,44 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef COMTEST_H +#define COMTEST_H + +void vAltStartComTestTasks (unsigned portBASE_TYPE uxPriority, +			    unsigned portLONG ulBaudRate, +			    unsigned portBASE_TYPE uxLED); +portBASE_TYPE xAreComTestTasksStillRunning (void); + +#endif diff --git a/openpicc/os/core/include/crhook.h b/openpicc/os/core/include/crhook.h new file mode 100644 index 0000000..de16883 --- /dev/null +++ b/openpicc/os/core/include/crhook.h @@ -0,0 +1,50 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef CRHOOK_H +#define CRHOOK_H + +/* + * Create the co-routines used to communicate wit the tick hook. + */ +void vStartHookCoRoutines (void); + +/* + * Return pdPASS or pdFAIL depending on whether an error has been detected + * or not. + */ +portBASE_TYPE xAreHookCoRoutinesStillRunning (void); + +#endif diff --git a/openpicc/os/core/include/croutine.h b/openpicc/os/core/include/croutine.h new file mode 100644 index 0000000..0394240 --- /dev/null +++ b/openpicc/os/core/include/croutine.h @@ -0,0 +1,720 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license +	and contact details.  Please ensure to read the configuration and relevant +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ +#ifndef CO_ROUTINE_H +#define CO_ROUTINE_H + +#include "list.h" + +/* Used to hide the implementation of the co-routine control block.  The +control block structure however has to be included in the header due to +the macro implementation of the co-routine functionality. */ +typedef void *xCoRoutineHandle; + +/* Defines the prototype to which co-routine functions must conform. */ +typedef void (*crCOROUTINE_CODE) (xCoRoutineHandle, unsigned portBASE_TYPE); + +typedef struct corCoRoutineControlBlock +{ +  crCOROUTINE_CODE pxCoRoutineFunction; +  xListItem xGenericListItem;	/*< List item used to place the CRCB in ready and blocked queues. */ +  xListItem xEventListItem;	/*< List item used to place the CRCB in event lists. */ +  unsigned portBASE_TYPE uxPriority;	/*< The priority of the co-routine in relation to other co-routines. */ +  unsigned portBASE_TYPE uxIndex;	/*< Used to distinguish between co-routines when multiple co-routines use the same co-routine function. */ +  unsigned portSHORT uxState;	/*< Used internally by the co-routine implementation. */ +} corCRCB;			/* Co-routine control block.  Note must be identical in size down to uxPriority with tskTCB. */ + +/** + * croutine. h + *<pre> + portBASE_TYPE xCoRoutineCreate( +                                 crCOROUTINE_CODE pxCoRoutineCode, +                                 unsigned portBASE_TYPE uxPriority, +                                 unsigned portBASE_TYPE uxIndex +                               );</pre> + * + * Create a new co-routine and add it to the list of co-routines that are + * ready to run. + * + * @param pxCoRoutineCode Pointer to the co-routine function.  Co-routine + * functions require special syntax - see the co-routine section of the WEB + * documentation for more information. + * + * @param uxPriority The priority with respect to other co-routines at which + *  the co-routine will run. + * + * @param uxIndex Used to distinguish between different co-routines that + * execute the same function.  See the example below and the co-routine section + * of the WEB documentation for further information. + * + * @return pdPASS if the co-routine was successfully created and added to a ready + * list, otherwise an error code defined with ProjDefs.h. + * + * Example usage: +   <pre> + // Co-routine to be created. + void vFlashCoRoutine( xCoRoutineHandle xHandle, unsigned portBASE_TYPE uxIndex ) + { + // Variables in co-routines must be declared static if they must maintain value across a blocking call. + // This may not be necessary for const variables. + static const char cLedToFlash[ 2 ] = { 5, 6 }; + static const portTickType xTimeToDelay[ 2 ] = { 200, 400 }; + +     // Must start every co-routine with a call to crSTART(); +     crSTART( xHandle ); + +     for( ;; ) +     { +         // This co-routine just delays for a fixed period, then toggles +         // an LED.  Two co-routines are created using this function, so +         // the uxIndex parameter is used to tell the co-routine which +         // LED to flash and how long to delay.  This assumes xQueue has +         // already been created. +         vParTestToggleLED( cLedToFlash[ uxIndex ] ); +         crDELAY( xHandle, uxFlashRates[ uxIndex ] ); +     } + +     // Must end every co-routine with a call to crEND(); +     crEND(); + } + + // Function that creates two co-routines. + void vOtherFunction( void ) + { + unsigned char ucParameterToPass; + xTaskHandle xHandle; +		 +     // Create two co-routines at priority 0.  The first is given index 0 +     // so (from the code above) toggles LED 5 every 200 ticks.  The second +     // is given index 1 so toggles LED 6 every 400 ticks. +     for( uxIndex = 0; uxIndex < 2; uxIndex++ ) +     { +         xCoRoutineCreate( vFlashCoRoutine, 0, uxIndex ); +     } + } +   </pre> + * \defgroup xCoRoutineCreate xCoRoutineCreate + * \ingroup Tasks + */ +signed portBASE_TYPE xCoRoutineCreate (crCOROUTINE_CODE pxCoRoutineCode, +				       unsigned portBASE_TYPE uxPriority, +				       unsigned portBASE_TYPE uxIndex); + + +/** + * croutine. h + *<pre> + void vCoRoutineSchedule( void );</pre> + * + * Run a co-routine. + * + * vCoRoutineSchedule() executes the highest priority co-routine that is able + * to run.  The co-routine will execute until it either blocks, yields or is + * preempted by a task.  Co-routines execute cooperatively so one + * co-routine cannot be preempted by another, but can be preempted by a task. + * + * If an application comprises of both tasks and co-routines then + * vCoRoutineSchedule should be called from the idle task (in an idle task + * hook). + * + * Example usage: +   <pre> + // This idle task hook will schedule a co-routine each time it is called. + // The rest of the idle task will execute between co-routine calls. + void vApplicationIdleHook( void ) + { +	vCoRoutineSchedule(); + } + + // Alternatively, if you do not require any other part of the idle task to + // execute, the idle task hook can call vCoRoutineScheduler() within an + // infinite loop. + void vApplicationIdleHook( void ) + { +    for( ;; ) +    { +        vCoRoutineSchedule(); +    } + } + </pre> + * \defgroup vCoRoutineSchedule vCoRoutineSchedule + * \ingroup Tasks + */ +void vCoRoutineSchedule (void); + +/** + * croutine. h + * <pre> + crSTART( xCoRoutineHandle xHandle );</pre> + * + * This macro MUST always be called at the start of a co-routine function. + * + * Example usage: +   <pre> + // Co-routine to be created. + void vACoRoutine( xCoRoutineHandle xHandle, unsigned portBASE_TYPE uxIndex ) + { + // Variables in co-routines must be declared static if they must maintain value across a blocking call. + static portLONG ulAVariable; + +     // Must start every co-routine with a call to crSTART(); +     crSTART( xHandle ); + +     for( ;; ) +     { +          // Co-routine functionality goes here. +     } + +     // Must end every co-routine with a call to crEND(); +     crEND(); + }</pre> + * \defgroup crSTART crSTART + * \ingroup Tasks + */ +#define crSTART( pxCRCB ) switch( ( ( corCRCB * )pxCRCB )->uxState ) { case 0: + +/** + * croutine. h + * <pre> + crEND();</pre> + * + * This macro MUST always be called at the end of a co-routine function. + * + * Example usage: +   <pre> + // Co-routine to be created. + void vACoRoutine( xCoRoutineHandle xHandle, unsigned portBASE_TYPE uxIndex ) + { + // Variables in co-routines must be declared static if they must maintain value across a blocking call. + static portLONG ulAVariable; + +     // Must start every co-routine with a call to crSTART(); +     crSTART( xHandle ); + +     for( ;; ) +     { +          // Co-routine functionality goes here. +     } + +     // Must end every co-routine with a call to crEND(); +     crEND(); + }</pre> + * \defgroup crSTART crSTART + * \ingroup Tasks + */ +#define crEND() } + +/* + * These macros are intended for internal use by the co-routine implementation + * only.  The macros should not be used directly by application writers. + */ +#define crSET_STATE0( xHandle ) ( ( corCRCB * )xHandle)->uxState = (__LINE__ * 2); return; case (__LINE__ * 2): +#define crSET_STATE1( xHandle ) ( ( corCRCB * )xHandle)->uxState = ((__LINE__ * 2)+1); return; case ((__LINE__ * 2)+1): + +/** + * croutine. h + *<pre> + crDELAY( xCoRoutineHandle xHandle, portTickType xTicksToDelay );</pre> + * + * Delay a co-routine for a fixed period of time. + * + * crDELAY can only be called from the co-routine function itself - not + * from within a function called by the co-routine function.  This is because + * co-routines do not maintain their own stack. + * + * @param xHandle The handle of the co-routine to delay.  This is the xHandle + * parameter of the co-routine function. + * + * @param xTickToDelay The number of ticks that the co-routine should delay + * for.  The actual amount of time this equates to is defined by + * configTICK_RATE_HZ (set in FreeRTOSConfig.h).  The constant portTICK_RATE_MS + * can be used to convert ticks to milliseconds. + * + * Example usage: +   <pre> + // Co-routine to be created. + void vACoRoutine( xCoRoutineHandle xHandle, unsigned portBASE_TYPE uxIndex ) + { + // Variables in co-routines must be declared static if they must maintain value across a blocking call. + // This may not be necessary for const variables. + // We are to delay for 200ms. + static const xTickType xDelayTime = 200 / portTICK_RATE_MS; + +     // Must start every co-routine with a call to crSTART(); +     crSTART( xHandle ); + +     for( ;; ) +     { +        // Delay for 200ms. +        crDELAY( xHandle, xDelayTime ); + +        // Do something here. +     } + +     // Must end every co-routine with a call to crEND(); +     crEND(); + }</pre> + * \defgroup crDELAY crDELAY + * \ingroup Tasks + */ +#define crDELAY( xHandle, xTicksToDelay )												\ +	if( xTicksToDelay > 0 )																\ +	{																					\ +		vCoRoutineAddToDelayedList( xTicksToDelay, NULL );								\ +	}																					\ +	crSET_STATE0( xHandle ); + +/** + * <pre> + crQUEUE_SEND( +                  xCoRoutineHandle xHandle, +                  xQueueHandle pxQueue, +                  void *pvItemToQueue, +                  portTickType xTicksToWait, +                  portBASE_TYPE *pxResult +             )</pre> + * + * The macro's crQUEUE_SEND() and crQUEUE_RECEIVE() are the co-routine + * equivalent to the xQueueSend() and xQueueReceive() functions used by tasks. + * + * crQUEUE_SEND and crQUEUE_RECEIVE can only be used from a co-routine whereas + * xQueueSend() and xQueueReceive() can only be used from tasks. + * + * crQUEUE_SEND can only be called from the co-routine function itself - not + * from within a function called by the co-routine function.  This is because + * co-routines do not maintain their own stack. + * + * See the co-routine section of the WEB documentation for information on + * passing data between tasks and co-routines and between ISR's and + * co-routines. + * + * @param xHandle The handle of the calling co-routine.  This is the xHandle + * parameter of the co-routine function. + * + * @param pxQueue The handle of the queue on which the data will be posted. + * The handle is obtained as the return value when the queue is created using + * the xQueueCreate() API function. + * + * @param pvItemToQueue A pointer to the data being posted onto the queue. + * The number of bytes of each queued item is specified when the queue is + * created.  This number of bytes is copied from pvItemToQueue into the queue + * itself. + * + * @param xTickToDelay The number of ticks that the co-routine should block + * to wait for space to become available on the queue, should space not be + * available immediately. The actual amount of time this equates to is defined + * by configTICK_RATE_HZ (set in FreeRTOSConfig.h).  The constant + * portTICK_RATE_MS can be used to convert ticks to milliseconds (see example + * below). + * + * @param pxResult The variable pointed to by pxResult will be set to pdPASS if + * data was successfully posted onto the queue, otherwise it will be set to an + * error defined within ProjDefs.h. + * + * Example usage: +   <pre> + // Co-routine function that blocks for a fixed period then posts a number onto + // a queue. + static void prvCoRoutineFlashTask( xCoRoutineHandle xHandle, unsigned portBASE_TYPE uxIndex ) + { + // Variables in co-routines must be declared static if they must maintain value across a blocking call. + static portBASE_TYPE xNumberToPost = 0; + static portBASE_TYPE xResult; + +    // Co-routines must begin with a call to crSTART(). +    crSTART( xHandle ); + +    for( ;; ) +    { +        // This assumes the queue has already been created. +        crQUEUE_SEND( xHandle, xCoRoutineQueue, &xNumberToPost, NO_DELAY, &xResult ); + +        if( xResult != pdPASS ) +        { +            // The message was not posted! +        } + +        // Increment the number to be posted onto the queue. +        xNumberToPost++; + +        // Delay for 100 ticks. +        crDELAY( xHandle, 100 ); +    } + +    // Co-routines must end with a call to crEND(). +    crEND(); + }</pre> + * \defgroup crQUEUE_SEND crQUEUE_SEND + * \ingroup Tasks + */ +#define crQUEUE_SEND( xHandle, pxQueue, pvItemToQueue, xTicksToWait, pxResult )			\ +{																						\ +	*pxResult = xQueueCRSend( pxQueue, pvItemToQueue, xTicksToWait );					\ +	if( *pxResult == errQUEUE_BLOCKED )													\ +	{																					\ +		crSET_STATE0( xHandle );														\ +		*pxResult = xQueueCRSend( pxQueue, pvItemToQueue, 0 );							\ +	}																					\ +	if( *pxResult == errQUEUE_YIELD )													\ +	{																					\ +		crSET_STATE1( xHandle );														\ +		*pxResult = pdPASS;																\ +	}																					\ +} + +/** + * croutine. h + * <pre> +  crQUEUE_RECEIVE( +                     xCoRoutineHandle xHandle, +                     xQueueHandle pxQueue, +                     void *pvBuffer, +                     portTickType xTicksToWait, +                     portBASE_TYPE *pxResult +                 )</pre> + * + * The macro's crQUEUE_SEND() and crQUEUE_RECEIVE() are the co-routine + * equivalent to the xQueueSend() and xQueueReceive() functions used by tasks. + * + * crQUEUE_SEND and crQUEUE_RECEIVE can only be used from a co-routine whereas + * xQueueSend() and xQueueReceive() can only be used from tasks. + * + * crQUEUE_RECEIVE can only be called from the co-routine function itself - not + * from within a function called by the co-routine function.  This is because + * co-routines do not maintain their own stack. + * + * See the co-routine section of the WEB documentation for information on + * passing data between tasks and co-routines and between ISR's and + * co-routines. + * + * @param xHandle The handle of the calling co-routine.  This is the xHandle + * parameter of the co-routine function. + * + * @param pxQueue The handle of the queue from which the data will be received. + * The handle is obtained as the return value when the queue is created using + * the xQueueCreate() API function. + * + * @param pvBuffer The buffer into which the received item is to be copied. + * The number of bytes of each queued item is specified when the queue is + * created.  This number of bytes is copied into pvBuffer. + * + * @param xTickToDelay The number of ticks that the co-routine should block + * to wait for data to become available from the queue, should data not be + * available immediately. The actual amount of time this equates to is defined + * by configTICK_RATE_HZ (set in FreeRTOSConfig.h).  The constant + * portTICK_RATE_MS can be used to convert ticks to milliseconds (see the + * crQUEUE_SEND example). + * + * @param pxResult The variable pointed to by pxResult will be set to pdPASS if + * data was successfully retrieved from the queue, otherwise it will be set to + * an error code as defined within ProjDefs.h. + * + * Example usage: + <pre> + // A co-routine receives the number of an LED to flash from a queue.  It + // blocks on the queue until the number is received. + static void prvCoRoutineFlashWorkTask( xCoRoutineHandle xHandle, unsigned portBASE_TYPE uxIndex ) + { + // Variables in co-routines must be declared static if they must maintain value across a blocking call. + static portBASE_TYPE xResult; + static unsigned portBASE_TYPE uxLEDToFlash; + +    // All co-routines must start with a call to crSTART(). +    crSTART( xHandle ); + +    for( ;; ) +    { +        // Wait for data to become available on the queue. +        crQUEUE_RECEIVE( xHandle, xCoRoutineQueue, &uxLEDToFlash, portMAX_DELAY, &xResult ); + +        if( xResult == pdPASS ) +        { +            // We received the LED to flash - flash it! +            vParTestToggleLED( uxLEDToFlash ); +        } +    } + +    crEND(); + }</pre> + * \defgroup crQUEUE_RECEIVE crQUEUE_RECEIVE + * \ingroup Tasks + */ +#define crQUEUE_RECEIVE( xHandle, pxQueue, pvBuffer, xTicksToWait, pxResult )			\ +{																						\ +	*pxResult = xQueueCRReceive( pxQueue, pvBuffer, xTicksToWait );						\ +	if( *pxResult == errQUEUE_BLOCKED ) 												\ +	{																					\ +		crSET_STATE0( xHandle );														\ +		*pxResult = xQueueCRReceive( pxQueue, pvBuffer, 0 );							\ +	}																					\ +	if( *pxResult == errQUEUE_YIELD )													\ +	{																					\ +		crSET_STATE1( xHandle );														\ +		*pxResult = pdPASS;																\ +	}																					\ +} + +/** + * croutine. h + * <pre> +  crQUEUE_SEND_FROM_ISR( +                            xQueueHandle pxQueue, +                            void *pvItemToQueue, +                            portBASE_TYPE xCoRoutinePreviouslyWoken +                       )</pre> + * + * The macro's crQUEUE_SEND_FROM_ISR() and crQUEUE_RECEIVE_FROM_ISR() are the + * co-routine equivalent to the xQueueSendFromISR() and xQueueReceiveFromISR() + * functions used by tasks. + * + * crQUEUE_SEND_FROM_ISR() and crQUEUE_RECEIVE_FROM_ISR() can only be used to + * pass data between a co-routine and and ISR, whereas xQueueSendFromISR() and + * xQueueReceiveFromISR() can only be used to pass data between a task and and + * ISR. + * + * crQUEUE_SEND_FROM_ISR can only be called from an ISR to send data to a queue + * that is being used from within a co-routine. + * + * See the co-routine section of the WEB documentation for information on + * passing data between tasks and co-routines and between ISR's and + * co-routines. + * + * @param xQueue The handle to the queue on which the item is to be posted. + * + * @param pvItemToQueue A pointer to the item that is to be placed on the + * queue.  The size of the items the queue will hold was defined when the + * queue was created, so this many bytes will be copied from pvItemToQueue + * into the queue storage area. + * + * @param xCoRoutinePreviouslyWoken This is included so an ISR can post onto + * the same queue multiple times from a single interrupt.  The first call + * should always pass in pdFALSE.  Subsequent calls should pass in + * the value returned from the previous call. + * + * @return pdTRUE if a co-routine was woken by posting onto the queue.  This is + * used by the ISR to determine if a context switch may be required following + * the ISR. + * + * Example usage: + <pre> + // A co-routine that blocks on a queue waiting for characters to be received. + static void vReceivingCoRoutine( xCoRoutineHandle xHandle, unsigned portBASE_TYPE uxIndex ) + { + portCHAR cRxedChar; + portBASE_TYPE xResult; + +     // All co-routines must start with a call to crSTART(). +     crSTART( xHandle ); + +     for( ;; ) +     { +         // Wait for data to become available on the queue.  This assumes the +         // queue xCommsRxQueue has already been created! +         crQUEUE_RECEIVE( xHandle, xCommsRxQueue, &uxLEDToFlash, portMAX_DELAY, &xResult ); + +         // Was a character received? +         if( xResult == pdPASS ) +         { +             // Process the character here. +         } +     } + +     // All co-routines must end with a call to crEND(). +     crEND(); + } + + // An ISR that uses a queue to send characters received on a serial port to + // a co-routine. + void vUART_ISR( void ) + { + portCHAR cRxedChar; + portBASE_TYPE xCRWokenByPost = pdFALSE; + +     // We loop around reading characters until there are none left in the UART. +     while( UART_RX_REG_NOT_EMPTY() ) +     { +         // Obtain the character from the UART. +         cRxedChar = UART_RX_REG; + +         // Post the character onto a queue.  xCRWokenByPost will be pdFALSE +         // the first time around the loop.  If the post causes a co-routine +         // to be woken (unblocked) then xCRWokenByPost will be set to pdTRUE. +         // In this manner we can ensure that if more than one co-routine is +         // blocked on the queue only one is woken by this ISR no matter how +         // many characters are posted to the queue. +         xCRWokenByPost = crQUEUE_SEND_FROM_ISR( xCommsRxQueue, &cRxedChar, xCRWokenByPost ); +     } + }</pre> + * \defgroup crQUEUE_SEND_FROM_ISR crQUEUE_SEND_FROM_ISR + * \ingroup Tasks + */ +#define crQUEUE_SEND_FROM_ISR( pxQueue, pvItemToQueue, xCoRoutinePreviouslyWoken ) xQueueCRSendFromISR( pxQueue, pvItemToQueue, xCoRoutinePreviouslyWoken ) + + +/** + * croutine. h + * <pre> +  crQUEUE_SEND_FROM_ISR( +                            xQueueHandle pxQueue, +                            void *pvBuffer, +                            portBASE_TYPE * pxCoRoutineWoken +                       )</pre> + * + * The macro's crQUEUE_SEND_FROM_ISR() and crQUEUE_RECEIVE_FROM_ISR() are the + * co-routine equivalent to the xQueueSendFromISR() and xQueueReceiveFromISR() + * functions used by tasks. + * + * crQUEUE_SEND_FROM_ISR() and crQUEUE_RECEIVE_FROM_ISR() can only be used to + * pass data between a co-routine and and ISR, whereas xQueueSendFromISR() and + * xQueueReceiveFromISR() can only be used to pass data between a task and and + * ISR. + * + * crQUEUE_RECEIVE_FROM_ISR can only be called from an ISR to receive data + * from a queue that is being used from within a co-routine (a co-routine + * posted to the queue). + * + * See the co-routine section of the WEB documentation for information on + * passing data between tasks and co-routines and between ISR's and + * co-routines. + * + * @param xQueue The handle to the queue on which the item is to be posted. + * + * @param pvBuffer A pointer to a buffer into which the received item will be + * placed.  The size of the items the queue will hold was defined when the + * queue was created, so this many bytes will be copied from the queue into + * pvBuffer. + * + * @param pxCoRoutineWoken A co-routine may be blocked waiting for space to become + * available on the queue.  If crQUEUE_RECEIVE_FROM_ISR causes such a + * co-routine to unblock *pxCoRoutineWoken will get set to pdTRUE, otherwise + * *pxCoRoutineWoken will remain unchanged. + * + * @return pdTRUE an item was successfully received from the queue, otherwise + * pdFALSE. + * + * Example usage: + <pre> + // A co-routine that posts a character to a queue then blocks for a fixed + // period.  The character is incremented each time. + static void vSendingCoRoutine( xCoRoutineHandle xHandle, unsigned portBASE_TYPE uxIndex ) + { + // cChar holds its value while this co-routine is blocked and must therefore + // be declared static. + static portCHAR cCharToTx = 'a'; + portBASE_TYPE xResult; + +     // All co-routines must start with a call to crSTART(). +     crSTART( xHandle ); + +     for( ;; ) +     { +         // Send the next character to the queue. +         crQUEUE_SEND( xHandle, xCoRoutineQueue, &cCharToTx, NO_DELAY, &xResult ); + +         if( xResult == pdPASS ) +         { +             // The character was successfully posted to the queue. +         } +		 else +		 { +			// Could not post the character to the queue. +		 } + +         // Enable the UART Tx interrupt to cause an interrupt in this +		 // hypothetical UART.  The interrupt will obtain the character +		 // from the queue and send it. +		 ENABLE_RX_INTERRUPT(); + +		 // Increment to the next character then block for a fixed period. +		 // cCharToTx will maintain its value across the delay as it is +		 // declared static. +		 cCharToTx++; +		 if( cCharToTx > 'x' ) +		 { +			cCharToTx = 'a'; +		 } +		 crDELAY( 100 ); +     } + +     // All co-routines must end with a call to crEND(). +     crEND(); + } + + // An ISR that uses a queue to receive characters to send on a UART. + void vUART_ISR( void ) + { + portCHAR cCharToTx; + portBASE_TYPE xCRWokenByPost = pdFALSE; + +     while( UART_TX_REG_EMPTY() ) +     { +         // Are there any characters in the queue waiting to be sent? +		 // xCRWokenByPost will automatically be set to pdTRUE if a co-routine +		 // is woken by the post - ensuring that only a single co-routine is +		 // woken no matter how many times we go around this loop. +         if( crQUEUE_RECEIVE_FROM_ISR( pxQueue, &cCharToTx, &xCRWokenByPost ) ) +		 { +			 SEND_CHARACTER( cCharToTx ); +		 } +     } + }</pre> + * \defgroup crQUEUE_RECEIVE_FROM_ISR crQUEUE_RECEIVE_FROM_ISR + * \ingroup Tasks + */ +#define crQUEUE_RECEIVE_FROM_ISR( pxQueue, pvBuffer, pxCoRoutineWoken ) xQueueCRReceiveFromISR( pxQueue, pvBuffer, pxCoRoutineWoken ) + +/* + * This function is intended for internal use by the co-routine macros only. + * The macro nature of the co-routine implementation requires that the + * prototype appears here.  The function should not be used by application + * writers. + * + * Removes the current co-routine from its ready list and places it in the + * appropriate delayed list. + */ +void vCoRoutineAddToDelayedList (portTickType xTicksToDelay, +				 xList * pxEventList); + +/* + * This function is intended for internal use by the queue implementation only. + * The function should not be used by application writers. + * + * Removes the highest priority co-routine from the event list and places it in + * the pending ready list. + */ +signed portBASE_TYPE xCoRoutineRemoveFromEventList (const xList * +						    pxEventList); + + +#endif /* CO_ROUTINE_H */ diff --git a/openpicc/os/core/include/death.h b/openpicc/os/core/include/death.h new file mode 100644 index 0000000..d5f20e0 --- /dev/null +++ b/openpicc/os/core/include/death.h @@ -0,0 +1,42 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef SUICIDE_TASK_H +#define SUICIDE_TASK_H + +void vCreateSuicidalTasks (unsigned portBASE_TYPE uxPriority); +portBASE_TYPE xIsCreateTaskStillRunning (void); + +#endif diff --git a/openpicc/os/core/include/dynamic.h b/openpicc/os/core/include/dynamic.h new file mode 100644 index 0000000..5a77c07 --- /dev/null +++ b/openpicc/os/core/include/dynamic.h @@ -0,0 +1,42 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef DYNAMIC_MANIPULATION_H +#define DYNAMIC_MANIPULATION_H + +void vStartDynamicPriorityTasks (void); +portBASE_TYPE xAreDynamicPriorityTasksStillRunning (void); + +#endif diff --git a/openpicc/os/core/include/fileIO.h b/openpicc/os/core/include/fileIO.h new file mode 100644 index 0000000..d1b336b --- /dev/null +++ b/openpicc/os/core/include/fileIO.h @@ -0,0 +1,44 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef FILE_IO_H +#define FILE_OI_H + +void vDisplayMessage (const portCHAR * const pcMessageToPrint); +void vWriteMessageToDisk (const portCHAR * const pcMessage); +void vWriteBufferToDisk (const portCHAR * const pcBuffer, +			 unsigned portLONG ulBufferLength); + +#endif diff --git a/openpicc/os/core/include/list.h b/openpicc/os/core/include/list.h new file mode 100644 index 0000000..cdd6a75 --- /dev/null +++ b/openpicc/os/core/include/list.h @@ -0,0 +1,272 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license +	and contact details.  Please ensure to read the configuration and relevant +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +/* + * This is the list implementation used by the scheduler.  While it is tailored + * heavily for the schedulers needs, it is also available for use by + * application code. + * + * xLists can only store pointers to xListItems.  Each xListItem contains a + * numeric value (xItemValue).  Most of the time the lists are sorted in + * descending item value order. + * + * Lists are created already containing one list item.  The value of this + * item is the maximum possible that can be stored, it is therefore always at + * the end of the list and acts as a marker.  The list member pxHead always + * points to this marker - even though it is at the tail of the list.  This + * is because the tail contains a wrap back pointer to the true head of + * the list. + * + * In addition to it's value, each list item contains a pointer to the next + * item in the list (pxNext), a pointer to the list it is in (pxContainer) + * and a pointer to back to the object that contains it.  These later two + * pointers are included for efficiency of list manipulation.  There is + * effectively a two way link between the object containing the list item and + * the list item itself. + * + * + * \page ListIntroduction List Implementation + * \ingroup FreeRTOSIntro + */ + + +#ifndef LIST_H +#define LIST_H + +/* + * Definition of the only type of object that a list can contain. + */ +struct xLIST_ITEM +{ +  portTickType xItemValue;	/*< The value being listed.  In most cases this is used to sort the list in descending order. */ +  volatile struct xLIST_ITEM *pxNext;	/*< Pointer to the next xListItem in the list. */ +  volatile struct xLIST_ITEM *pxPrevious;	/*< Pointer to the previous xListItem in the list. */ +  void *pvOwner;		/*< Pointer to the object (normally a TCB) that contains the list item.  There is therefore a two way link between the object containing the list item and the list item itself. */ +  void *pvContainer;		/*< Pointer to the list in which this list item is placed (if any). */ +}; +typedef struct xLIST_ITEM xListItem;	/* For some reason lint wants this as two separate definitions. */ + +struct xMINI_LIST_ITEM +{ +  portTickType xItemValue; +  volatile struct xLIST_ITEM *pxNext; +  volatile struct xLIST_ITEM *pxPrevious; +}; +typedef struct xMINI_LIST_ITEM xMiniListItem; + +/* + * Definition of the type of queue used by the scheduler. + */ +typedef struct xLIST +{ +  volatile unsigned portBASE_TYPE uxNumberOfItems; +  volatile xListItem *pxIndex;	/*< Used to walk through the list.  Points to the last item returned by a call to pvListGetOwnerOfNextEntry (). */ +  volatile xMiniListItem xListEnd;	/*< List item that contains the maximum possible item value meaning it is always at the end of the list and is therefore used as a marker. */ +} xList; + +/* + * Access macro to set the owner of a list item.  The owner of a list item + * is the object (usually a TCB) that contains the list item. + * + * \page listSET_LIST_ITEM_OWNER listSET_LIST_ITEM_OWNER + * \ingroup LinkedList + */ +#define listSET_LIST_ITEM_OWNER( pxListItem, pxOwner )		( pxListItem )->pvOwner = ( void * ) pxOwner + +/* + * Access macro to set the value of the list item.  In most cases the value is + * used to sort the list in descending order. + * + * \page listSET_LIST_ITEM_VALUE listSET_LIST_ITEM_VALUE + * \ingroup LinkedList + */ +#define listSET_LIST_ITEM_VALUE( pxListItem, xValue )		( pxListItem )->xItemValue = xValue + +/* + * Access macro the retrieve the value of the list item.  The value can + * represent anything - for example a the priority of a task, or the time at + * which a task should be unblocked. + * + * \page listGET_LIST_ITEM_VALUE listGET_LIST_ITEM_VALUE + * \ingroup LinkedList + */ +#define listGET_LIST_ITEM_VALUE( pxListItem )				( ( pxListItem )->xItemValue ) + +/* + * Access macro to determine if a list contains any items.  The macro will + * only have the value true if the list is empty. + * + * \page listLIST_IS_EMPTY listLIST_IS_EMPTY + * \ingroup LinkedList + */ +#define listLIST_IS_EMPTY( pxList )				( ( pxList )->uxNumberOfItems == ( unsigned portBASE_TYPE ) 0 ) + +/* + * Access macro to return the number of items in the list. + */ +#define listCURRENT_LIST_LENGTH( pxList )		( ( pxList )->uxNumberOfItems ) + +/* + * Access function to obtain the owner of the next entry in a list. + * + * The list member pxIndex is used to walk through a list.  Calling + * listGET_OWNER_OF_NEXT_ENTRY increments pxIndex to the next item in the list + * and returns that entries pxOwner parameter.  Using multiple calls to this + * function it is therefore possible to move through every item contained in + * a list. + * + * The pxOwner parameter of a list item is a pointer to the object that owns + * the list item.  In the scheduler this is normally a task control block. + * The pxOwner parameter effectively creates a two way link between the list + * item and its owner. + * + * @param pxList The list from which the next item owner is to be returned. + * + * \page listGET_OWNER_OF_NEXT_ENTRY listGET_OWNER_OF_NEXT_ENTRY + * \ingroup LinkedList + */ +#define listGET_OWNER_OF_NEXT_ENTRY( pxTCB, pxList )									\ +	/* Increment the index to the next item and return the item, ensuring */			\ +	/* we don't return the marker used at the end of the list.  */						\ +	( pxList )->pxIndex = ( pxList )->pxIndex->pxNext;									\ +	if( ( pxList )->pxIndex == ( xListItem * ) &( ( pxList )->xListEnd ) )				\ +	{																					\ +		( pxList )->pxIndex = ( pxList )->pxIndex->pxNext;								\ +	}																					\ +	pxTCB = ( pxList )->pxIndex->pvOwner + + +/* + * Access function to obtain the owner of the first entry in a list.  Lists + * are normally sorted in ascending item value order. + * + * This function returns the pxOwner member of the first item in the list. + * The pxOwner parameter of a list item is a pointer to the object that owns + * the list item.  In the scheduler this is normally a task control block. + * The pxOwner parameter effectively creates a two way link between the list + * item and its owner. + * + * @param pxList The list from which the owner of the head item is to be + * returned. + * + * \page listGET_OWNER_OF_HEAD_ENTRY listGET_OWNER_OF_HEAD_ENTRY + * \ingroup LinkedList + */ +#define listGET_OWNER_OF_HEAD_ENTRY( pxList )  ( ( pxList->uxNumberOfItems != ( unsigned portBASE_TYPE ) 0 ) ? ( (&( pxList->xListEnd ))->pxNext->pvOwner ) : ( NULL ) ) + +/* + * Check to see if a list item is within a list.  The list item maintains a + * "container" pointer that points to the list it is in.  All this macro does + * is check to see if the container and the list match. + * + * @param pxList The list we want to know if the list item is within. + * @param pxListItem The list item we want to know if is in the list. + * @return pdTRUE is the list item is in the list, otherwise pdFALSE. + * pointer against + */ +#define listIS_CONTAINED_WITHIN( pxList, pxListItem ) ( ( pxListItem )->pvContainer == ( void * ) pxList ) + +/* + * Must be called before a list is used!  This initialises all the members + * of the list structure and inserts the xListEnd item into the list as a + * marker to the back of the list. + * + * @param pxList Pointer to the list being initialised. + * + * \page vListInitialise vListInitialise + * \ingroup LinkedList + */ +void vListInitialise (xList * pxList); + +/* + * Must be called before a list item is used.  This sets the list container to + * null so the item does not think that it is already contained in a list. + * + * @param pxItem Pointer to the list item being initialised. + * + * \page vListInitialiseItem vListInitialiseItem + * \ingroup LinkedList + */ +void vListInitialiseItem (xListItem * pxItem); + +/* + * Insert a list item into a list.  The item will be inserted into the list in + * a position determined by its item value (descending item value order). + * + * @param pxList The list into which the item is to be inserted. + * + * @param pxNewListItem The item to that is to be placed in the list. + * + * \page vListInsert vListInsert + * \ingroup LinkedList + */ +void vListInsert (xList * pxList, xListItem * pxNewListItem); + +/* + * Insert a list item into a list.  The item will be inserted in a position + * such that it will be the last item within the list returned by multiple + * calls to listGET_OWNER_OF_NEXT_ENTRY. + * + * The list member pvIndex is used to walk through a list.  Calling + * listGET_OWNER_OF_NEXT_ENTRY increments pvIndex to the next item in the list. + * Placing an item in a list using vListInsertEnd effectively places the item + * in the list position pointed to by pvIndex.  This means that every other + * item within the list will be returned by listGET_OWNER_OF_NEXT_ENTRY before + * the pvIndex parameter again points to the item being inserted. + * + * @param pxList The list into which the item is to be inserted. + * + * @param pxNewListItem The list item to be inserted into the list. + * + * \page vListInsertEnd vListInsertEnd + * \ingroup LinkedList + */ +void vListInsertEnd (xList * pxList, xListItem * pxNewListItem); + +/* + * Remove an item from a list.  The list item has a pointer to the list that + * it is in, so only the list item need be passed into the function. + * + * @param vListRemove The item to be removed.  The item will remove itself from + * the list pointed to by it's pxContainer parameter. + * + * \page vListRemove vListRemove + * \ingroup LinkedList + */ +void vListRemove (xListItem * pxItemToRemove); + + + +#endif diff --git a/openpicc/os/core/include/mevents.h b/openpicc/os/core/include/mevents.h new file mode 100644 index 0000000..a4580a8 --- /dev/null +++ b/openpicc/os/core/include/mevents.h @@ -0,0 +1,42 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef EVENTS_TEST_H +#define EVENTS_TEST_H + +void vStartMultiEventTasks (void); +portBASE_TYPE xAreMultiEventTasksStillRunning (void); + +#endif diff --git a/openpicc/os/core/include/portable.h b/openpicc/os/core/include/portable.h new file mode 100644 index 0000000..49d11b0 --- /dev/null +++ b/openpicc/os/core/include/portable.h @@ -0,0 +1,233 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section +	of http:www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http:www.FreeRTOS.org for documentation, latest information, license +	and contact details.  Please ensure to read the configuration and relevant +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +/*----------------------------------------------------------- + * Portable layer API.  Each function must be defined for each port. + *----------------------------------------------------------*/ + +#ifndef PORTABLE_H +#define PORTABLE_H + +/* Include the macro file relevant to the port being used. */ + +#ifdef OPEN_WATCOM_INDUSTRIAL_PC_PORT +#include "..\..\source\portable\owatcom\16bitdos\pc\portmacro.h" +typedef void (__interrupt __far * pxISR) (); +#endif + +#ifdef OPEN_WATCOM_FLASH_LITE_186_PORT +#include "..\..\source\portable\owatcom\16bitdos\flsh186\portmacro.h" +typedef void (__interrupt __far * pxISR) (); +#endif + +#ifdef GCC_MEGA_AVR +#include "../portable/GCC/ATMega323/portmacro.h" +#endif + +#ifdef IAR_MEGA_AVR +#include "../portable/IAR/ATMega323/portmacro.h" +#endif + +#ifdef MPLAB_PIC24_PORT +#include "..\..\Source\portable\MPLAB\PIC24_dsPIC\portmacro.h" +#endif + +#ifdef MPLAB_DSPIC_PORT +#include "..\..\Source\portable\MPLAB\PIC24_dsPIC\portmacro.h" +#endif + +#ifdef MPLAB_PIC18F_PORT +#include "..\..\source\portable\MPLAB\PIC18F\portmacro.h" +#endif + +#ifdef _FEDPICC +#include "libFreeRTOS/Include/portmacro.h" +#endif + +#ifdef SDCC_CYGNAL +#include "../../Source/portable/SDCC/Cygnal/portmacro.h" +#endif + +#ifdef GCC_ARM7 +#include "../../Source/portable/GCC/ARM7_LPC2000/portmacro.h" +#endif + +#ifdef ROWLEY_LPC23xx +#include "../../Source/portable/GCC/ARM7_LPC23xx/portmacro.h" +#endif + +#ifdef GCC_MSP430 +#include "../../Source/portable/GCC/MSP430F449/portmacro.h" +#endif + +#ifdef ROWLEY_MSP430 +#include "../../Source/portable/Rowley/MSP430F449/portmacro.h" +#endif + +#ifdef KEIL_ARM7 +#include "..\..\Source\portable\Keil\ARM7\portmacro.h" +#endif + +#ifdef SAM7_GCC +#include "../ARM7_AT91SAM7S/portmacro.h" +#endif + +#ifdef SAM7_IAR +#include "..\..\Source\portable\IAR\AtmelSAM7S64\portmacro.h" +#endif + +#ifdef LPC2000_IAR +#include "..\..\Source\portable\IAR\LPC2000\portmacro.h" +#endif + +#ifdef STR71X_IAR +#include "..\..\Source\portable\IAR\STR71x\portmacro.h" +#endif + +#ifdef STR75X_IAR +#include "..\..\Source\portable\IAR\STR75x\portmacro.h" +#endif + +#ifdef STR75X_GCC +#include "..\..\Source\portable\GCC\STR75x\portmacro.h" +#endif + +#ifdef STR91X_IAR +#include "..\..\Source\portable\IAR\STR91x\portmacro.h" +#endif + +#ifdef GCC_H8S +#include "../../Source/portable/GCC/H8S2329/portmacro.h" +#endif + +#ifdef GCC_AT91FR40008 +#include "../../Source/portable/GCC/ARM7_AT91FR40008/portmacro.h" +#endif + +#ifdef RVDS_ARMCM3_LM3S102 +#include "../../Source/portable/RVDS/ARM_CM3/portmacro.h" +#endif + +#ifdef GCC_ARMCM3_LM3S102 +#include "../../Source/portable/GCC/ARM_CM3/portmacro.h" +#endif + +#ifdef IAR_ARMCM3_LM +#include "../../Source/portable/IAR/ARM_CM3/portmacro.h" +#endif + +#ifdef HCS12_CODE_WARRIOR +#include "../../Source/portable/CodeWarrior/HCS12/portmacro.h" +#endif + +#ifdef MICROBLAZE_GCC +#include "../../Source/portable/GCC/MicroBlaze/portmacro.h" +#endif + +#ifdef TERN_EE +#include "..\..\Source\portable\Paradigm\Tern_EE\small\portmacro.h" +#endif + +#ifdef GCC_HCS12 +#include "../../Source/portable/GCC/HCS12/portmacro.h" +#endif + +#ifdef GCC_MCF5235 +#include "../../Source/portable/GCC/MCF5235/portmacro.h" +#endif + +#ifdef BCC_INDUSTRIAL_PC_PORT +	/* A short file name has to be used in place of the normal +	   FreeRTOSConfig.h when using the Borland compiler. */ +#include "frconfig.h" +#include "..\portable\BCC\16BitDOS\PC\prtmacro.h" +typedef void (__interrupt __far * pxISR) (); +#endif + +#ifdef BCC_FLASH_LITE_186_PORT +	/* A short file name has to be used in place of the normal +	   FreeRTOSConfig.h when using the Borland compiler. */ +#include "frconfig.h" +#include "..\portable\BCC\16BitDOS\flsh186\prtmacro.h" +typedef void (__interrupt __far * pxISR) (); +#endif + +#if __GNUC__ && (__AVR32_UC3A0256__ || \ +                 __AVR32_UC3A0512__ || \ +                 __AVR32_UC3A1128__ || \ +                 __AVR32_UC3A1256__ || \ +                 __AVR32_UC3A1512__) +#include "portmacro.h" +#endif + +#if __ICCAVR32__ && (__AT32UC3A0256__ || \ +                     __AT32UC3A0512__ || \ +                     __AT32UC3A1128__ || \ +                     __AT32UC3A1256__ || \ +                     __AT32UC3A1512__) +#include "portmacro.h" +#endif + +/* + * Setup the stack of a new task so it is ready to be placed under the + * scheduler control.  The registers have to be placed on the stack in + * the order that the port expects to find them. + */ +portSTACK_TYPE *pxPortInitialiseStack (portSTACK_TYPE * pxTopOfStack, +				       pdTASK_CODE pxCode, +				       void *pvParameters); + +/* + * Map to the memory management routines required for the port. + */ +void *pvPortMalloc (size_t xSize); +void vPortFree (void *pv); +void vPortInitialiseBlocks (void); + +/* + * Setup the hardware ready for the scheduler to take control.  This generally + * sets up a tick interrupt and sets timers for the correct tick frequency. + */ +portBASE_TYPE xPortStartScheduler (void); + +/* + * Undo any hardware/ISR setup that was performed by xPortStartScheduler() so + * the hardware is left in its original condition after the scheduler stops + * executing. + */ +void vPortEndScheduler (void); + + +#endif /* PORTABLE_H */ diff --git a/openpicc/os/core/include/print.h b/openpicc/os/core/include/print.h new file mode 100644 index 0000000..d219bc4 --- /dev/null +++ b/openpicc/os/core/include/print.h @@ -0,0 +1,43 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef PRINT_H +#define PRINT_H + +void vPrintInitialise (void); +void vPrintDisplayMessage (const portCHAR * const *pcMessageToSend); +const portCHAR *pcPrintGetNextMessage (portTickType xPrintRate); + +#endif diff --git a/openpicc/os/core/include/projdefs.h b/openpicc/os/core/include/projdefs.h new file mode 100644 index 0000000..3b2f1b7 --- /dev/null +++ b/openpicc/os/core/include/projdefs.h @@ -0,0 +1,56 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef PROJDEFS_H +#define PROJDEFS_H + +/* Defines to prototype to which task functions must conform. */ +typedef void (*pdTASK_CODE) (void *); + +#define pdTRUE		( 1 ) +#define pdFALSE		( 0 ) + +#define pdPASS									( 1 ) +#define pdFAIL									( 0 ) +#define errQUEUE_EMPTY							( 0 ) +#define errQUEUE_FULL							( 0 ) + +/* Error definitions. */ +#define errCOULD_NOT_ALLOCATE_REQUIRED_MEMORY	( -1 ) +#define errNO_TASK_TO_RUN						( -2 ) +#define errQUEUE_BLOCKED						( -4 ) +#define errQUEUE_YIELD							( -5 ) + +#endif /* PROJDEFS_H */ diff --git a/openpicc/os/core/include/queue.h b/openpicc/os/core/include/queue.h new file mode 100644 index 0000000..e95d7b0 --- /dev/null +++ b/openpicc/os/core/include/queue.h @@ -0,0 +1,492 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef QUEUE_H +#define QUEUE_H + +typedef void *xQueueHandle; + +/** + * queue. h + * <pre> + xQueueHandle xQueueCreate(  +                              unsigned portBASE_TYPE uxQueueLength,  +                              unsigned portBASE_TYPE uxItemSize  +                          ); + * </pre> + * + * Creates a new queue instance.  This allocates the storage required by the + * new queue and returns a handle for the queue. + * + * @param uxQueueLength The maximum number of items that the queue can contain. + * + * @param uxItemSize The number of bytes each item in the queue will require.   + * Items are queued by copy, not by reference, so this is the number of bytes + * that will be copied for each posted item.  Each item on the queue must be + * the same size. + * + * @return If the queue is successfully create then a handle to the newly  + * created queue is returned.  If the queue cannot be created then 0 is + * returned. + *  + * Example usage: +   <pre> + struct AMessage + { +    portCHAR ucMessageID; +    portCHAR ucData[ 20 ]; + }; + + void vATask( void *pvParameters ) + { + xQueueHandle xQueue1, xQueue2; + +    // Create a queue capable of containing 10 unsigned long values. +    xQueue1 = xQueueCreate( 10, sizeof( unsigned portLONG ) ); +    if( xQueue1 == 0 ) +    { +        // Queue was not created and must not be used. +    } + +    // Create a queue capable of containing 10 pointers to AMessage structures. +    // These should be passed by pointer as they contain a lot of data. +    xQueue2 = xQueueCreate( 10, sizeof( struct AMessage * ) ); +    if( xQueue2 == 0 ) +    { +        // Queue was not created and must not be used. +    } + +    // ... Rest of task code. + } + </pre> + * \defgroup xQueueCreate xQueueCreate + * \ingroup QueueManagement + */ +xQueueHandle xQueueCreate (unsigned portBASE_TYPE uxQueueLength, +			   unsigned portBASE_TYPE uxItemSize); + +/** + * queue. h + * <pre> + portBASE_TYPE xQueueSend(  +                             xQueueHandle xQueue,  +                             const void * pvItemToQueue,  +                             portTickType xTicksToWait  +                         ); + * </pre> + * + * Post an item on a queue.  The item is queued by copy, not by reference. + * This function must not be called from an interrupt service routine. + * See xQueueSendFromISR () for an alternative which may be used in an ISR. + * + * @param xQueue The handle to the queue on which the item is to be posted. + *  + * @param pvItemToQueue A pointer to the item that is to be placed on the  + * queue.  The size of the items the queue will hold was defined when the + * queue was created, so this many bytes will be copied from pvItemToQueue + * into the queue storage area. + * + * @param xTicksToWait The maximum amount of time the task should block + * waiting for space to become available on the queue, should it already + * be full.  The call will return immediately if this is set to 0.  The + * time is defined in tick periods so the constant portTICK_RATE_MS  + * should be used to convert to real time if this is required. + * + * @return pdTRUE if the item was successfully posted, otherwise errQUEUE_FULL. + * + * Example usage: +   <pre> + struct AMessage + { +    portCHAR ucMessageID; +    portCHAR ucData[ 20 ]; + } xMessage; + + unsigned portLONG ulVar = 10UL; + + void vATask( void *pvParameters ) + { + xQueueHandle xQueue1, xQueue2; + struct AMessage *pxMessage; + +    // Create a queue capable of containing 10 unsigned long values. +    xQueue1 = xQueueCreate( 10, sizeof( unsigned portLONG ) ); + +    // Create a queue capable of containing 10 pointers to AMessage structures. +    // These should be passed by pointer as they contain a lot of data. +    xQueue2 = xQueueCreate( 10, sizeof( struct AMessage * ) ); + +    // ... + +    if( xQueue1 != 0 ) +    { +        // Send an unsigned long.  Wait for 10 ticks for space to become  +        // available if necessary. +        if( xQueueSend( xQueue1, ( void * ) &ulVar, ( portTickType ) 10 ) != pdPASS ) +        { +            // Failed to post the message, even after 10 ticks. +        } +    } + +    if( xQueue2 != 0 ) +    { +        // Send a pointer to a struct AMessage object.  Don't block if the +        // queue is already full. +        pxMessage = & xMessage; +        xQueueSend( xQueue2, ( void * ) &pxMessage, ( portTickType ) 0 ); +    } + +	// ... Rest of task code. + } + </pre> + * \defgroup xQueueSend xQueueSend + * \ingroup QueueManagement + */ +signed portBASE_TYPE xQueueSend (xQueueHandle xQueue, +				 const void *pvItemToQueue, +				 portTickType xTicksToWait); + +/** + * queue. h + * <pre> + portBASE_TYPE xQueueReceive(  +                                xQueueHandle xQueue,  +                                void *pvBuffer,  +                                portTickType xTicksToWait  +                            );</pre> + * + * Receive an item from a queue.  The item is received by copy so a buffer of  + * adequate size must be provided.  The number of bytes copied into the buffer + * was defined when the queue was created. + * + * This function must not be used in an interrupt service routine.  See + * xQueueReceiveFromISR for an alternative that can. + * + * @param pxQueue The handle to the queue from which the item is to be + * received. + * + * @param pvBuffer Pointer to the buffer into which the received item will + * be copied. + *  + * @param xTicksToWait The maximum amount of time the task should block + * waiting for an item to receive should the queue be empty at the time + * of the call.    The time is defined in tick periods so the constant  + * portTICK_RATE_MS should be used to convert to real time if this is required. + * + * @return pdTRUE if an item was successfully received from the queue, + * otherwise pdFALSE. + * + * Example usage: +   <pre> + struct AMessage + { +    portCHAR ucMessageID; +    portCHAR ucData[ 20 ]; + } xMessage; + + xQueueHandle xQueue; +  + // Task to create a queue and post a value. + void vATask( void *pvParameters ) + { + struct AMessage *pxMessage; + +    // Create a queue capable of containing 10 pointers to AMessage structures. +    // These should be passed by pointer as they contain a lot of data. +    xQueue = xQueueCreate( 10, sizeof( struct AMessage * ) ); +    if( xQueue == 0 ) +    { +        // Failed to create the queue. +    } + +    // ... + +    // Send a pointer to a struct AMessage object.  Don't block if the +    // queue is already full. +    pxMessage = & xMessage; +    xQueueSend( xQueue, ( void * ) &pxMessage, ( portTickType ) 0 ); + +	// ... Rest of task code. + } + + // Task to receive from the queue. + void vADifferentTask( void *pvParameters ) + { + struct AMessage *pxRxedMessage; + +    if( xQueue != 0 ) +    { +        // Receive a message on the created queue.  Block for 10 ticks if a +        // message is not immediately available. +        if( xQueueReceive( xQueue, &( pxRxedMessage ), ( portTickType ) 10 ) ) +        { +            // pcRxedMessage now points to the struct AMessage variable posted +            // by vATask. +        } +    } + +	// ... Rest of task code. + } + </pre> + * \defgroup xQueueReceive xQueueReceive + * \ingroup QueueManagement + */ +signed portBASE_TYPE xQueueReceive (xQueueHandle xQueue, void *pvBuffer, +				    portTickType xTicksToWait); + +/** + * queue. h + * <pre>unsigned portBASE_TYPE uxQueueMessagesWaiting( xQueueHandle xQueue );</pre> + * + * Return the number of messages stored in a queue. + * + * @param xQueue A handle to the queue being queried. + *  + * @return The number of messages available in the queue. + * + * \page uxQueueMessagesWaiting uxQueueMessagesWaiting + * \ingroup QueueManagement + */ +unsigned portBASE_TYPE uxQueueMessagesWaiting (xQueueHandle xQueue); + +/** + * queue. h + * <pre>void vQueueDelete( xQueueHandle xQueue );</pre> + * + * Delete a queue - freeing all the memory allocated for storing of items + * placed on the queue. + *  + * @param xQueue A handle to the queue to be deleted. + * + * \page vQueueDelete vQueueDelete + * \ingroup QueueManagement + */ +void vQueueDelete (xQueueHandle xQueue); + +/** + * queue. h + * <pre> + portBASE_TYPE xQueueSendFromISR(  +                                    xQueueHandle pxQueue,  +                                    const void *pvItemToQueue,  +                                    portBASE_TYPE xTaskPreviouslyWoken  +                                ); + </pre> + * + * Post an item on a queue.  It is safe to use this function from within an + * interrupt service routine. + * + * Items are queued by copy not reference so it is preferable to only + * queue small items, especially when called from an ISR.  In most cases + * it would be preferable to store a pointer to the item being queued. + * + * @param xQueue The handle to the queue on which the item is to be posted. + *  + * @param pvItemToQueue A pointer to the item that is to be placed on the  + * queue.  The size of the items the queue will hold was defined when the + * queue was created, so this many bytes will be copied from pvItemToQueue + * into the queue storage area. + * + * @param cTaskPreviouslyWoken This is included so an ISR can post onto + * the same queue multiple times from a single interrupt.  The first call + * should always pass in pdFALSE.  Subsequent calls should pass in + * the value returned from the previous call.  See the file serial .c in the + * PC port for a good example of this mechanism. + * + * @return pdTRUE if a task was woken by posting onto the queue.  This is  + * used by the ISR to determine if a context switch may be required following + * the ISR. + * + * Example usage for buffered IO (where the ISR can obtain more than one value + * per call): +   <pre> + void vBufferISR( void ) + { + portCHAR cIn; + portBASE_TYPE xTaskWokenByPost; + +    // We have not woken a task at the start of the ISR. +    cTaskWokenByPost = pdFALSE; + +    // Loop until the buffer is empty. +    do +    { +        // Obtain a byte from the buffer. +        cIn = portINPUT_BYTE( RX_REGISTER_ADDRESS );						 + +        // Post the byte.  The first time round the loop cTaskWokenByPost +        // will be pdFALSE.  If the queue send causes a task to wake we do +        // not want the task to run until we have finished the ISR, so +        // xQueueSendFromISR does not cause a context switch.  Also we  +        // don't want subsequent posts to wake any other tasks, so we store +        // the return value back into cTaskWokenByPost so xQueueSendFromISR +        // knows not to wake any task the next iteration of the loop. +        xTaskWokenByPost = xQueueSendFromISR( xRxQueue, &cIn, cTaskWokenByPost ); + +    } while( portINPUT_BYTE( BUFFER_COUNT ) ); + +    // Now the buffer is empty we can switch context if necessary. +    if( cTaskWokenByPost ) +    { +        taskYIELD (); +    } + } + </pre> + * + * \defgroup xQueueSendFromISR xQueueSendFromISR + * \ingroup QueueManagement + */ +signed portBASE_TYPE xQueueSendFromISR (xQueueHandle pxQueue, +					const void *pvItemToQueue, +					signed portBASE_TYPE +					xTaskPreviouslyWoken); + +/** + * queue. h + * <pre> + portBASE_TYPE xQueueReceiveFromISR(  +                                       xQueueHandle pxQueue,  +                                       void *pvBuffer,  +                                       portBASE_TYPE *pxTaskWoken  +                                   );  + * </pre> + * + * Receive an item from a queue.  It is safe to use this function from within an + * interrupt service routine. + * + * @param pxQueue The handle to the queue from which the item is to be + * received. + * + * @param pvBuffer Pointer to the buffer into which the received item will + * be copied. + *  + * @param pxTaskWoken A task may be blocked waiting for space to become + * available on the queue.  If xQueueReceiveFromISR causes such a task to + * unblock *pxTaskWoken will get set to pdTRUE, otherwise *pxTaskWoken will + * remain unchanged. + * + * @return pdTRUE if an item was successfully received from the queue, + * otherwise pdFALSE. + * + * Example usage: +   <pre> +  + xQueueHandle xQueue; +  + // Function to create a queue and post some values. + void vAFunction( void *pvParameters ) + { + portCHAR cValueToPost; + const portTickType xBlockTime = ( portTickType )0xff; + +    // Create a queue capable of containing 10 characters. +    xQueue = xQueueCreate( 10, sizeof( portCHAR ) ); +    if( xQueue == 0 ) +    { +        // Failed to create the queue. +    } + +    // ... + +    // Post some characters that will be used within an ISR.  If the queue +    // is full then this task will block for xBlockTime ticks. +    cValueToPost = 'a'; +    xQueueSend( xQueue, ( void * ) &cValueToPost, xBlockTime ); +    cValueToPost = 'b'; +    xQueueSend( xQueue, ( void * ) &cValueToPost, xBlockTime ); + +    // ... keep posting characters ... this task may block when the queue +    // becomes full. + +    cValueToPost = 'c'; +    xQueueSend( xQueue, ( void * ) &cValueToPost, xBlockTime ); + } + + // ISR that outputs all the characters received on the queue.  + void vISR_Routine( void ) + { + portBASE_TYPE xTaskWokenByReceive = pdFALSE; + portCHAR cRxedChar; + +    while( xQueueReceiveFromISR( xQueue, ( void * ) &cRxedChar, &xTaskWokenByReceive) ) +    { +        // A character was received.  Output the character now. +        vOutputCharacter( cRxedChar ); + +        // If removing the character from the queue woke the task that was  +        // posting onto the queue cTaskWokenByReceive will have been set to +        // pdTRUE.  No matter how many times this loop iterates only one +        // task will be woken. +    } + +    if( cTaskWokenByPost != ( portCHAR ) pdFALSE; +    { +        taskYIELD (); +    } + } + </pre> + * \defgroup xQueueReceiveFromISR xQueueReceiveFromISR + * \ingroup QueueManagement + */ +signed portBASE_TYPE xQueueReceiveFromISR (xQueueHandle pxQueue, +					   void *pvBuffer, +					   signed portBASE_TYPE * +					   pxTaskWoken); + + +/*  + * The functions defined above are for passing data to and from tasks.  The  + * functions below are the equivalents for passing data to and from  + * co-rtoutines. + * + * These functions are called from the co-routine macro implementation and + * should not be called directly from application code.  Instead use the macro + * wrappers defined within croutine.h. + */ +signed portBASE_TYPE xQueueCRSendFromISR (xQueueHandle pxQueue, +					  const void *pvItemToQueue, +					  signed portBASE_TYPE +					  xCoRoutinePreviouslyWoken); +signed portBASE_TYPE xQueueCRReceiveFromISR (xQueueHandle pxQueue, +					     void *pvBuffer, +					     signed portBASE_TYPE * +					     pxTaskWoken); +signed portBASE_TYPE xQueueCRSend (xQueueHandle pxQueue, +				   const void *pvItemToQueue, +				   portTickType xTicksToWait); +signed portBASE_TYPE xQueueCRReceive (xQueueHandle pxQueue, void *pvBuffer, +				      portTickType xTicksToWait); + +#endif diff --git a/openpicc/os/core/include/semphr.h b/openpicc/os/core/include/semphr.h new file mode 100644 index 0000000..acdd022 --- /dev/null +++ b/openpicc/os/core/include/semphr.h @@ -0,0 +1,291 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#include "queue.h" + +#ifndef SEMAPHORE_H +#define SEMAPHORE_H + +typedef xQueueHandle xSemaphoreHandle; + +#define semBINARY_SEMAPHORE_QUEUE_LENGTH	( ( unsigned portCHAR ) 1 ) +#define semSEMAPHORE_QUEUE_ITEM_LENGTH		( ( unsigned portCHAR ) 0 ) +#define semGIVE_BLOCK_TIME					( ( portTickType ) 0 ) + + +/** + * semphr. h + * <pre>vSemaphoreCreateBinary( xSemaphoreHandle xSemaphore )</pre> + * + * <i>Macro</i> that implements a semaphore by using the existing queue mechanism. + * The queue length is 1 as this is a binary semaphore.  The data size is 0 + * as we don't want to actually store any data - we just want to know if the + * queue is empty or full. + * + * @param xSemaphore Handle to the created semaphore.  Should be of type xSemaphoreHandle. + * + * Example usage: + <pre> + xSemaphoreHandle xSemaphore; + + void vATask( void * pvParameters ) + { +    // Semaphore cannot be used before a call to vSemaphoreCreateBinary (). +    // This is a macro so pass the variable in directly. +    vSemaphoreCreateBinary( xSemaphore ); + +    if( xSemaphore != NULL ) +    { +        // The semaphore was created successfully. +        // The semaphore can now be used.   +    } + } + </pre> + * \defgroup vSemaphoreCreateBinary vSemaphoreCreateBinary + * \ingroup Semaphores + */ +#define vSemaphoreCreateBinary( xSemaphore )		{																							\ +														xSemaphore = xQueueCreate( ( unsigned portCHAR ) 1, semSEMAPHORE_QUEUE_ITEM_LENGTH );	\ +														if( xSemaphore != NULL )																\ +														{																						\ +															xSemaphoreGive( xSemaphore );														\ +														}																						\ +													} + +/** + * semphr. h + * xSemaphoreTake(  + *                   xSemaphoreHandle xSemaphore,  + *                   portTickType xBlockTime  + *               )</pre> + * + * <i>Macro</i> to obtain a semaphore.  The semaphore must of been created using  + * vSemaphoreCreateBinary (). + * + * @param xSemaphore A handle to the semaphore being obtained.  This is the + * handle returned by vSemaphoreCreateBinary (); + * + * @param xBlockTime The time in ticks to wait for the semaphore to become + * available.  The macro portTICK_RATE_MS can be used to convert this to a + * real time.  A block time of zero can be used to poll the semaphore. + * + * @return pdTRUE if the semaphore was obtained.  pdFALSE if xBlockTime + * expired without the semaphore becoming available. + * + * Example usage: + <pre> + xSemaphoreHandle xSemaphore = NULL; + + // A task that creates a semaphore. + void vATask( void * pvParameters ) + { +    // Create the semaphore to guard a shared resource. +    vSemaphoreCreateBinary( xSemaphore ); + } + + // A task that uses the semaphore. + void vAnotherTask( void * pvParameters ) + { +    // ... Do other things. + +    if( xSemaphore != NULL ) +    { +        // See if we can obtain the semaphore.  If the semaphore is not available +        // wait 10 ticks to see if it becomes free.	 +        if( xSemaphoreTake( xSemaphore, ( portTickType ) 10 ) == pdTRUE ) +        { +            // We were able to obtain the semaphore and can now access the +            // shared resource. + +            // ... + +            // We have finished accessing the shared resource.  Release the  +            // semaphore. +            xSemaphoreGive( xSemaphore ); +        } +        else +        { +            // We could not obtain the semaphore and can therefore not access +            // the shared resource safely. +        } +    } + } + </pre> + * \defgroup xSemaphoreTake xSemaphoreTake + * \ingroup Semaphores + */ +#define xSemaphoreTake( xSemaphore, xBlockTime )	xQueueReceive( ( xQueueHandle ) xSemaphore, NULL, xBlockTime ) + +/** + * semphr. h + * <pre>xSemaphoreGive( xSemaphoreHandle xSemaphore )</pre> + * + * <i>Macro</i> to release a semaphore.  The semaphore must of been created using  + * vSemaphoreCreateBinary (), and obtained using sSemaphoreTake (). + * + * This must not be used from an ISR.  See xSemaphoreGiveFromISR () for + * an alternative which can be used from an ISR. + * + * @param xSemaphore A handle to the semaphore being released.  This is the + * handle returned by vSemaphoreCreateBinary (); + * + * @return pdTRUE if the semaphore was released.  pdFALSE if an error occurred. + * Semaphores are implemented using queues.  An error can occur if there is + * no space on the queue to post a message - indicating that the  + * semaphore was not first obtained correctly. + * + * Example usage: + <pre> + xSemaphoreHandle xSemaphore = NULL; + + void vATask( void * pvParameters ) + { +    // Create the semaphore to guard a shared resource. +    vSemaphoreCreateBinary( xSemaphore ); + +    if( xSemaphore != NULL ) +    { +        if( xSemaphoreGive( xSemaphore ) != pdTRUE ) +        { +            // We would expect this call to fail because we cannot give +            // a semaphore without first "taking" it! +        } + +        // Obtain the semaphore - don't block if the semaphore is not +        // immediately available. +        if( xSemaphoreTake( xSemaphore, ( portTickType ) 0 ) ) +        { +            // We now have the semaphore and can access the shared resource. + +            // ... + +            // We have finished accessing the shared resource so can free the +            // semaphore. +            if( xSemaphoreGive( xSemaphore ) != pdTRUE ) +            { +                // We would not expect this call to fail because we must have +                // obtained the semaphore to get here. +            } +        } +    } + } + </pre> + * \defgroup xSemaphoreGive xSemaphoreGive + * \ingroup Semaphores + */ +#define xSemaphoreGive( xSemaphore )				xQueueSend( ( xQueueHandle ) xSemaphore, NULL, semGIVE_BLOCK_TIME ) + +/** + * semphr. h + * <pre> + xSemaphoreGiveFromISR(  +                          xSemaphoreHandle xSemaphore,  +                          portSHORT sTaskPreviouslyWoken  +                      )</pre> + * + * <i>Macro</i> to  release a semaphore.  The semaphore must of been created using  + * vSemaphoreCreateBinary (), and obtained using xSemaphoreTake (). + * + * This macro can be used from an ISR. + * + * @param xSemaphore A handle to the semaphore being released.  This is the + * handle returned by vSemaphoreCreateBinary (); + * + * @param sTaskPreviouslyWoken This is included so an ISR can make multiple calls + * to xSemaphoreGiveFromISR () from a single interrupt.  The first call + * should always pass in pdFALSE.  Subsequent calls should pass in + * the value returned from the previous call.  See the file serial .c in the + * PC port for a good example of using xSemaphoreGiveFromISR (). + * + * @return pdTRUE if a task was woken by releasing the semaphore.  This is  + * used by the ISR to determine if a context switch may be required following + * the ISR. + * + * Example usage: + <pre> + #define LONG_TIME 0xffff + #define TICKS_TO_WAIT	10 + xSemaphoreHandle xSemaphore = NULL; + + // Repetitive task. + void vATask( void * pvParameters ) + { +    for( ;; ) +    { +        // We want this task to run every 10 ticks or a timer.  The semaphore  +        // was created before this task was started + +        // Block waiting for the semaphore to become available. +        if( xSemaphoreTake( xSemaphore, LONG_TIME ) == pdTRUE ) +        { +            // It is time to execute. + +            // ... + +            // We have finished our task.  Return to the top of the loop where +            // we will block on the semaphore until it is time to execute  +            // again. +        } +    } + } + + // Timer ISR + void vTimerISR( void * pvParameters ) + { + static unsigned portCHAR ucLocalTickCount = 0; + +    // A timer tick has occurred. + +    // ... Do other time functions. + +    // Is it time for vATask () to run? +    ucLocalTickCount++; +    if( ucLocalTickCount >= TICKS_TO_WAIT ) +    { +        // Unblock the task by releasing the semaphore. +        xSemaphoreGive( xSemaphore ); + +        // Reset the count so we release the semaphore again in 10 ticks time. +        ucLocalTickCount = 0; +    } + } + </pre> + * \defgroup xSemaphoreGiveFromISR xSemaphoreGiveFromISR + * \ingroup Semaphores + */ +#define xSemaphoreGiveFromISR( xSemaphore, xTaskPreviouslyWoken )			xQueueSendFromISR( ( xQueueHandle ) xSemaphore, NULL, xTaskPreviouslyWoken ) + + +#endif diff --git a/openpicc/os/core/include/serial.h b/openpicc/os/core/include/serial.h new file mode 100644 index 0000000..58c7a5f --- /dev/null +++ b/openpicc/os/core/include/serial.h @@ -0,0 +1,116 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section  +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license  +	and contact details.  Please ensure to read the configuration and relevant  +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef SERIAL_COMMS_H +#define SERIAL_COMMS_H + +typedef void *xComPortHandle; + +typedef enum +{ +  serCOM1, +  serCOM2, +  serCOM3, +  serCOM4, +  serCOM5, +  serCOM6, +  serCOM7, +  serCOM8 +} eCOMPort; + +typedef enum +{ +  serNO_PARITY, +  serODD_PARITY, +  serEVEN_PARITY, +  serMARK_PARITY, +  serSPACE_PARITY +} eParity; + +typedef enum +{ +  serSTOP_1, +  serSTOP_2 +} eStopBits; + +typedef enum +{ +  serBITS_5, +  serBITS_6, +  serBITS_7, +  serBITS_8 +} eDataBits; + +typedef enum +{ +  ser50, +  ser75, +  ser110, +  ser134, +  ser150, +  ser200, +  ser300, +  ser600, +  ser1200, +  ser1800, +  ser2400, +  ser4800, +  ser9600, +  ser19200, +  ser38400, +  ser57600, +  ser115200 +} eBaud; + +xComPortHandle xSerialPortInitMinimal (unsigned portLONG ulWantedBaud, +				       unsigned portBASE_TYPE uxQueueLength); +xComPortHandle xSerialPortInit (eCOMPort ePort, eBaud eWantedBaud, +				eParity eWantedParity, +				eDataBits eWantedDataBits, +				eStopBits eWantedStopBits, +				unsigned portBASE_TYPE uxBufferLength); +void vSerialPutString (xComPortHandle pxPort, +		       const signed portCHAR * const pcString, +		       unsigned portSHORT usStringLength); +signed portBASE_TYPE xSerialGetChar (xComPortHandle pxPort, +				     signed portCHAR * pcRxedChar, +				     portTickType xBlockTime); +signed portBASE_TYPE xSerialPutChar (xComPortHandle pxPort, +				     signed portCHAR cOutChar, +				     portTickType xBlockTime); +portBASE_TYPE xSerialWaitForSemaphore (xComPortHandle xPort); +void vSerialClose (xComPortHandle xPort); + +#endif diff --git a/openpicc/os/core/include/task.h b/openpicc/os/core/include/task.h new file mode 100644 index 0000000..3d01c53 --- /dev/null +++ b/openpicc/os/core/include/task.h @@ -0,0 +1,960 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license +	and contact details.  Please ensure to read the configuration and relevant +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +#ifndef TASK_H +#define TASK_H + +#include "portable.h" +#include "list.h" + +/*----------------------------------------------------------- + * MACROS AND DEFINITIONS + *----------------------------------------------------------*/ + +#define tskKERNEL_VERSION_NUMBER "V4.2.1" + +/** + * task. h + * + * Type by which tasks are referenced.  For example, a call to xTaskCreate + * returns (via a pointer parameter) an xTaskHandle variable that can then + * be used as a parameter to vTaskDelete to delete the task. + * + * \page xTaskHandle xTaskHandle + * \ingroup Tasks + */ +typedef void *xTaskHandle; + +/* + * Used internally only. + */ +typedef struct xTIME_OUT +{ +  portBASE_TYPE xOverflowCount; +  portTickType xTimeOnEntering; +} xTimeOutType; + +/* + * Defines the priority used by the idle task.  This must not be modified. + * + * \ingroup TaskUtils + */ +#define tskIDLE_PRIORITY			( ( unsigned portBASE_TYPE ) 0 ) + +/** + * task. h + * + * Macro for forcing a context switch. + * + * \page taskYIELD taskYIELD + * \ingroup SchedulerControl + */ +#define taskYIELD()					portYIELD() + +/** + * task. h + * + * Macro to mark the start of a critical code region.  Preemptive context + * switches cannot occur when in a critical region. + * + * NOTE: This may alter the stack (depending on the portable implementation) + * so must be used with care! + * + * \page taskENTER_CRITICAL taskENTER_CRITICAL + * \ingroup SchedulerControl + */ +#define taskENTER_CRITICAL()		portENTER_CRITICAL() + +/** + * task. h + * + * Macro to mark the end of a critical code region.  Preemptive context + * switches cannot occur when in a critical region. + * + * NOTE: This may alter the stack (depending on the portable implementation) + * so must be used with care! + * + * \page taskEXIT_CRITICAL taskEXIT_CRITICAL + * \ingroup SchedulerControl + */ +#define taskEXIT_CRITICAL()			portEXIT_CRITICAL() + +/** + * task. h + * + * Macro to disable all maskable interrupts. + * + * \page taskDISABLE_INTERRUPTS taskDISABLE_INTERRUPTS + * \ingroup SchedulerControl + */ +#define taskDISABLE_INTERRUPTS()	portDISABLE_INTERRUPTS() + +/** + * task. h + * + * Macro to enable microcontroller interrupts. + * + * \page taskENABLE_INTERRUPTS taskENABLE_INTERRUPTS + * \ingroup SchedulerControl + */ +#define taskENABLE_INTERRUPTS()		portENABLE_INTERRUPTS() + + +/*----------------------------------------------------------- + * TASK CREATION API + *----------------------------------------------------------*/ + +/** + * task. h + *<pre> + portBASE_TYPE xTaskCreate( +                              pdTASK_CODE pvTaskCode, +                              const portCHAR * const pcName, +                              unsigned portSHORT usStackDepth, +                              void *pvParameters, +                              unsigned portBASE_TYPE uxPriority, +                              xTaskHandle *pvCreatedTask +                          );</pre> + * + * Create a new task and add it to the list of tasks that are ready to run. + * + * @param pvTaskCode Pointer to the task entry function.  Tasks + * must be implemented to never return (i.e. continuous loop). + * + * @param pcName A descriptive name for the task.  This is mainly used to + * facilitate debugging.  Max length defined by tskMAX_TASK_NAME_LEN - default + * is 16. + * + * @param usStackDepth The size of the task stack specified as the number of + * variables the stack can hold - not the number of bytes.  For example, if + * the stack is 16 bits wide and usStackDepth is defined as 100, 200 bytes + * will be allocated for stack storage. + * + * @param pvParameters Pointer that will be used as the parameter for the task + * being created. + * + * @param uxPriority The priority at which the task should run. + * + * @param pvCreatedTask Used to pass back a handle by which the created task + * can be referenced. + * + * @return pdPASS if the task was successfully created and added to a ready + * list, otherwise an error code defined in the file errors. h + * + * Example usage: +   <pre> + // Task to be created. + void vTaskCode( void * pvParameters ) + { +     for( ;; ) +     { +         // Task code goes here. +     } + } + + // Function that creates a task. + void vOtherFunction( void ) + { + unsigned char ucParameterToPass; + xTaskHandle xHandle; +		 +     // Create the task, storing the handle. +     xTaskCreate( vTaskCode, "NAME", STACK_SIZE, &ucParameterToPass, tskIDLE_PRIORITY, &xHandle ); +		 +     // Use the handle to delete the task. +     vTaskDelete( xHandle ); + } +   </pre> + * \defgroup xTaskCreate xTaskCreate + * \ingroup Tasks + */ +signed portBASE_TYPE xTaskCreate (pdTASK_CODE pvTaskCode, +				  const signed portCHAR * const pcName, +				  unsigned portSHORT usStackDepth, +				  void *pvParameters, +				  unsigned portBASE_TYPE uxPriority, +				  xTaskHandle * pvCreatedTask); + +/** + * task. h + * <pre>void vTaskDelete( xTaskHandle pxTask );</pre> + * + * INCLUDE_vTaskDelete must be defined as 1 for this function to be available. + * See the configuration section for more information. + * + * Remove a task from the RTOS real time kernels management.  The task being + * deleted will be removed from all ready, blocked, suspended and event lists. + * + * NOTE:  The idle task is responsible for freeing the kernel allocated + * memory from tasks that have been deleted.  It is therefore important that + * the idle task is not starved of microcontroller processing time if your + * application makes any calls to vTaskDelete ().  Memory allocated by the + * task code is not automatically freed, and should be freed before the task + * is deleted. + * + * See the demo application file death.c for sample code that utilises + * vTaskDelete (). + * + * @param pxTask The handle of the task to be deleted.  Passing NULL will + * cause the calling task to be deleted. + * + * Example usage: +   <pre> + void vOtherFunction( void ) + { + xTaskHandle xHandle; +		 +     // Create the task, storing the handle. +     xTaskCreate( vTaskCode, "NAME", STACK_SIZE, NULL, tskIDLE_PRIORITY, &xHandle ); +		 +     // Use the handle to delete the task. +     vTaskDelete( xHandle ); + } +   </pre> + * \defgroup vTaskDelete vTaskDelete + * \ingroup Tasks + */ +void vTaskDelete (xTaskHandle pxTask); + + +/*----------------------------------------------------------- + * TASK CONTROL API + *----------------------------------------------------------*/ + +/** + * task. h + * <pre>void vTaskDelay( portTickType xTicksToDelay );</pre> + * + * Delay a task for a given number of ticks.  The actual time that the + * task remains blocked depends on the tick rate.  The constant + * portTICK_RATE_MS can be used to calculate real time from the tick + * rate - with the resolution of one tick period. + * + * INCLUDE_vTaskDelay must be defined as 1 for this function to be available. + * See the configuration section for more information. + * + * @param xTicksToDelay The amount of time, in tick periods, that + * the calling task should block. + * + * Example usage: +   <pre> + // Wait 10 ticks before performing an action. + // NOTE: + // This is for demonstration only and would be better achieved + // using vTaskDelayUntil (). + void vTaskFunction( void * pvParameters ) + { + portTickType xDelay, xNextTime; + +     // Calc the time at which we want to perform the action +     // next. +     xNextTime = xTaskGetTickCount () + ( portTickType ) 10; + +     for( ;; ) +     { +         xDelay = xNextTime - xTaskGetTickCount (); +         xNextTime += ( portTickType ) 10; + +         // Guard against overflow +         if( xDelay <= ( portTickType ) 10 ) +         { +             vTaskDelay( xDelay ); +         } + +         // Perform action here. +     } + } +   </pre> + * \defgroup vTaskDelay vTaskDelay + * \ingroup TaskCtrl + */ +void vTaskDelay (portTickType xTicksToDelay); + +/** + * task. h + * <pre>void vTaskDelayUntil( portTickType *pxPreviousWakeTime, portTickType xTimeIncrement );</pre> + * + * INCLUDE_vTaskDelayUntil must be defined as 1 for this function to be available. + * See the configuration section for more information. + * + * Delay a task until a specified time.  This function can be used by cyclical + * tasks to ensure a constant execution frequency. + * + * This function differs from vTaskDelay () in one important aspect:  vTaskDelay () will + * cause a task to block for the specified number of ticks from the time vTaskDelay () is + * called.  It is therefore difficult to use vTaskDelay () by itself to generate a fixed + * execution frequency as the time between a task starting to execute and that task + * calling vTaskDelay () may not be fixed [the task may take a different path though the + * code between calls, or may get interrupted or preempted a different number of times + * each time it executes]. + * + * Whereas vTaskDelay () specifies a wake time relative to the time at which the function + * is called, vTaskDelayUntil () specifies the absolute (exact) time at which it wishes to + * unblock. + * + * The constant portTICK_RATE_MS can be used to calculate real time from the tick + * rate - with the resolution of one tick period. + * + * @param pxPreviousWakeTime Pointer to a variable that holds the time at which the + * task was last unblocked.  The variable must be initialised with the current time + * prior to its first use (see the example below).  Following this the variable is + * automatically updated within vTaskDelayUntil (). + * + * @param xTimeIncrement The cycle time period.  The task will be unblocked at + * time *pxPreviousWakeTime + xTimeIncrement.  Calling vTaskDelayUntil with the + * same xTimeIncrement parameter value will cause the task to execute with + * a fixed interface period. + * + * Example usage: +   <pre> + // Perform an action every 10 ticks. + void vTaskFunction( void * pvParameters ) + { + portTickType xLastWakeTime; + const portTickType xFrequency = 10; + +     // Initialise the xLastWakeTime variable with the current time. +     xLastWakeTime = xTaskGetTickCount (); +     for( ;; ) +     { +         // Wait for the next cycle. +         vTaskDelayUntil( &xLastWakeTime, xFrequency ); + +         // Perform action here. +     } + } +   </pre> + * \defgroup vTaskDelayUntil vTaskDelayUntil + * \ingroup TaskCtrl + */ +void vTaskDelayUntil (portTickType * pxPreviousWakeTime, +		      portTickType xTimeIncrement); + +/** + * task. h + * <pre>unsigned portBASE_TYPE uxTaskPriorityGet( xTaskHandle pxTask );</pre> + * + * INCLUDE_xTaskPriorityGet must be defined as 1 for this function to be available. + * See the configuration section for more information. + * + * Obtain the priority of any task. + * + * @param pxTask Handle of the task to be queried.  Passing a NULL + * handle results in the priority of the calling task being returned. + * + * @return The priority of pxTask. + * + * Example usage: +   <pre> + void vAFunction( void ) + { + xTaskHandle xHandle; +		 +     // Create a task, storing the handle. +     xTaskCreate( vTaskCode, "NAME", STACK_SIZE, NULL, tskIDLE_PRIORITY, &xHandle ); +		 +     // ... + +     // Use the handle to obtain the priority of the created task. +     // It was created with tskIDLE_PRIORITY, but may have changed +     // it itself. +     if( uxTaskPriorityGet( xHandle ) != tskIDLE_PRIORITY ) +     { +         // The task has changed it's priority. +     } + +     // ... + +     // Is our priority higher than the created task? +     if( uxTaskPriorityGet( xHandle ) < uxTaskPriorityGet( NULL ) ) +     { +         // Our priority (obtained using NULL handle) is higher. +     } + } +   </pre> + * \defgroup uxTaskPriorityGet uxTaskPriorityGet + * \ingroup TaskCtrl + */ +unsigned portBASE_TYPE uxTaskPriorityGet (xTaskHandle pxTask); + +/** + * task. h + * <pre>void vTaskPrioritySet( xTaskHandle pxTask, unsigned portBASE_TYPE uxNewPriority );</pre> + * + * INCLUDE_vTaskPrioritySet must be defined as 1 for this function to be available. + * See the configuration section for more information. + * + * Set the priority of any task. + * + * A context switch will occur before the function returns if the priority + * being set is higher than the currently executing task. + * + * @param pxTask Handle to the task for which the priority is being set. + * Passing a NULL handle results in the priority of the calling task being set. + * + * @param uxNewPriority The priority to which the task will be set. + * + * Example usage: +   <pre> + void vAFunction( void ) + { + xTaskHandle xHandle; +		 +     // Create a task, storing the handle. +     xTaskCreate( vTaskCode, "NAME", STACK_SIZE, NULL, tskIDLE_PRIORITY, &xHandle ); + +     // ... + +     // Use the handle to raise the priority of the created task. +     vTaskPrioritySet( xHandle, tskIDLE_PRIORITY + 1 ); + +     // ... + +     // Use a NULL handle to raise our priority to the same value. +     vTaskPrioritySet( NULL, tskIDLE_PRIORITY + 1 ); + } +   </pre> + * \defgroup vTaskPrioritySet vTaskPrioritySet + * \ingroup TaskCtrl + */ +void vTaskPrioritySet (xTaskHandle pxTask, +		       unsigned portBASE_TYPE uxNewPriority); + +/** + * task. h + * <pre>void vTaskSuspend( xTaskHandle pxTaskToSuspend );</pre> + * + * INCLUDE_vTaskSuspend must be defined as 1 for this function to be available. + * See the configuration section for more information. + * + * Suspend any task.  When suspended a task will never get any microcontroller + * processing time, no matter what its priority. + * + * Calls to vTaskSuspend are not accumulative - + * i.e. calling vTaskSuspend () twice on the same task still only requires one + * call to vTaskResume () to ready the suspended task. + * + * @param pxTaskToSuspend Handle to the task being suspended.  Passing a NULL + * handle will cause the calling task to be suspended. + * + * Example usage: +   <pre> + void vAFunction( void ) + { + xTaskHandle xHandle; +		 +     // Create a task, storing the handle. +     xTaskCreate( vTaskCode, "NAME", STACK_SIZE, NULL, tskIDLE_PRIORITY, &xHandle ); +		 +     // ... + +     // Use the handle to suspend the created task. +     vTaskSuspend( xHandle ); + +     // ... +		 +     // The created task will not run during this period, unless +     // another task calls vTaskResume( xHandle ). +		 +     //... +		 + +     // Suspend ourselves. +     vTaskSuspend( NULL ); + +     // We cannot get here unless another task calls vTaskResume +     // with our handle as the parameter. + } +   </pre> + * \defgroup vTaskSuspend vTaskSuspend + * \ingroup TaskCtrl + */ +void vTaskSuspend (xTaskHandle pxTaskToSuspend); + +/** + * task. h + * <pre>void vTaskResume( xTaskHandle pxTaskToResume );</pre> + * + * INCLUDE_vTaskSuspend must be defined as 1 for this function to be available. + * See the configuration section for more information. + * + * Resumes a suspended task. + * + * A task that has been suspended by one of more calls to vTaskSuspend () + * will be made available for running again by a single call to + * vTaskResume (). + * + * @param pxTaskToResume Handle to the task being readied. + * + * Example usage: +   <pre> + void vAFunction( void ) + { + xTaskHandle xHandle; +		 +     // Create a task, storing the handle. +     xTaskCreate( vTaskCode, "NAME", STACK_SIZE, NULL, tskIDLE_PRIORITY, &xHandle ); +		 +     // ... + +     // Use the handle to suspend the created task. +     vTaskSuspend( xHandle ); + +     // ... +	 +     // The created task will not run during this period, unless +     // another task calls vTaskResume( xHandle ). +		 +     //... +		 + +     // Resume the suspended task ourselves. +     vTaskResume( xHandle ); + +     // The created task will once again get microcontroller processing +     // time in accordance with it priority within the system. + } +   </pre> + * \defgroup vTaskResume vTaskResume + * \ingroup TaskCtrl + */ +void vTaskResume (xTaskHandle pxTaskToResume); + +/** + * task. h + * <pre>void xTaskResumeFromISR( xTaskHandle pxTaskToResume );</pre> + * + * INCLUDE_xTaskResumeFromISR must be defined as 1 for this function to be  + * available.  See the configuration section for more information. + * + * An implementation of vTaskResume() that can be called from within an ISR. + * + * A task that has been suspended by one of more calls to vTaskSuspend () + * will be made available for running again by a single call to + * xTaskResumeFromISR (). + * + * @param pxTaskToResume Handle to the task being readied. + * + * \defgroup vTaskResumeFromISR vTaskResumeFromISR + * \ingroup TaskCtrl + */ +portBASE_TYPE xTaskResumeFromISR (xTaskHandle pxTaskToResume); + +/*----------------------------------------------------------- + * SCHEDULER CONTROL + *----------------------------------------------------------*/ + +/** + * task. h + * <pre>void vTaskStartScheduler( void );</pre> + * + * Starts the real time kernel tick processing.  After calling the kernel + * has control over which tasks are executed and when.  This function + * does not return until an executing task calls vTaskEndScheduler (). + * + * At least one task should be created via a call to xTaskCreate () + * before calling vTaskStartScheduler ().  The idle task is created + * automatically when the first application task is created. + * + * See the demo application file main.c for an example of creating + * tasks and starting the kernel. + * + * Example usage: +   <pre> + void vAFunction( void ) + { +     // Create at least one task before starting the kernel. +     xTaskCreate( vTaskCode, "NAME", STACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); + +     // Start the real time kernel with preemption. +     vTaskStartScheduler (); + +     // Will not get here unless a task calls vTaskEndScheduler () + } +   </pre> + * + * \defgroup vTaskStartScheduler vTaskStartScheduler + * \ingroup SchedulerControl + */ +void vTaskStartScheduler (void); + +/** + * task. h + * <pre>void vTaskEndScheduler( void );</pre> + * + * Stops the real time kernel tick.  All created tasks will be automatically + * deleted and multitasking (either preemptive or cooperative) will + * stop.  Execution then resumes from the point where vTaskStartScheduler () + * was called, as if vTaskStartScheduler () had just returned. + * + * See the demo application file main. c in the demo/PC directory for an + * example that uses vTaskEndScheduler (). + * + * vTaskEndScheduler () requires an exit function to be defined within the + * portable layer (see vPortEndScheduler () in port. c for the PC port).  This + * performs hardware specific operations such as stopping the kernel tick. + * + * vTaskEndScheduler () will cause all of the resources allocated by the + * kernel to be freed - but will not free resources allocated by application + * tasks. + * + * Example usage: +   <pre> + void vTaskCode( void * pvParameters ) + { +     for( ;; ) +     { +         // Task code goes here. + +         // At some point we want to end the real time kernel processing +         // so call ... +         vTaskEndScheduler (); +     } + } + + void vAFunction( void ) + { +     // Create at least one task before starting the kernel. +     xTaskCreate( vTaskCode, "NAME", STACK_SIZE, NULL, tskIDLE_PRIORITY, NULL ); + +     // Start the real time kernel with preemption. +     vTaskStartScheduler (); + +     // Will only get here when the vTaskCode () task has called +     // vTaskEndScheduler ().  When we get here we are back to single task +     // execution. + } +   </pre> + * + * \defgroup vTaskEndScheduler vTaskEndScheduler + * \ingroup SchedulerControl + */ +void vTaskEndScheduler (void); + +/** + * task. h + * <pre>void vTaskSuspendAll( void );</pre> + * + * Suspends all real time kernel activity while keeping interrupts (including the + * kernel tick) enabled. + * + * After calling vTaskSuspendAll () the calling task will continue to execute + * without risk of being swapped out until a call to xTaskResumeAll () has been + * made. + * + * Example usage: +   <pre> + void vTask1( void * pvParameters ) + { +     for( ;; ) +     { +         // Task code goes here. + +         // ... + +         // At some point the task wants to perform a long operation during +         // which it does not want to get swapped out.  It cannot use +         // taskENTER_CRITICAL ()/taskEXIT_CRITICAL () as the length of the +         // operation may cause interrupts to be missed - including the +         // ticks. + +         // Prevent the real time kernel swapping out the task. +         vTaskSuspendAll (); + +         // Perform the operation here.  There is no need to use critical +         // sections as we have all the microcontroller processing time. +         // During this time interrupts will still operate and the kernel +         // tick count will be maintained. + +         // ... + +         // The operation is complete.  Restart the kernel. +         xTaskResumeAll (); +     } + } +   </pre> + * \defgroup vTaskSuspendAll vTaskSuspendAll + * \ingroup SchedulerControl + */ +void vTaskSuspendAll (void); + +/** + * task. h + * <pre>portCHAR xTaskResumeAll( void );</pre> + * + * Resumes real time kernel activity following a call to vTaskSuspendAll (). + * After a call to vTaskSuspendAll () the kernel will take control of which + * task is executing at any time. + * + * @return If resuming the scheduler caused a context switch then pdTRUE is + *         returned, otherwise pdFALSE is returned. + * + * Example usage: +   <pre> + void vTask1( void * pvParameters ) + { +     for( ;; ) +     { +         // Task code goes here. + +         // ... + +         // At some point the task wants to perform a long operation during +         // which it does not want to get swapped out.  It cannot use +         // taskENTER_CRITICAL ()/taskEXIT_CRITICAL () as the length of the +         // operation may cause interrupts to be missed - including the +         // ticks. + +         // Prevent the real time kernel swapping out the task. +         vTaskSuspendAll (); + +         // Perform the operation here.  There is no need to use critical +         // sections as we have all the microcontroller processing time. +         // During this time interrupts will still operate and the real +         // time kernel tick count will be maintained. + +         // ... + +         // The operation is complete.  Restart the kernel.  We want to force +         // a context switch - but there is no point if resuming the scheduler +         // caused a context switch already. +         if( !xTaskResumeAll () ) +         { +              taskYIELD (); +         } +     } + } +   </pre> + * \defgroup xTaskResumeAll xTaskResumeAll + * \ingroup SchedulerControl + */ +signed portBASE_TYPE xTaskResumeAll (void); + + +/*----------------------------------------------------------- + * TASK UTILITIES + *----------------------------------------------------------*/ + +/** + * task. h + * <PRE>volatile portTickType xTaskGetTickCount( void );</PRE> + * + * @return The count of ticks since vTaskStartScheduler was called. + * + * \page xTaskGetTickCount xTaskGetTickCount + * \ingroup TaskUtils + */ +portTickType xTaskGetTickCount (void); + +/** + * task. h + * <PRE>unsigned portSHORT uxTaskGetNumberOfTasks( void );</PRE> + * + * @return The number of tasks that the real time kernel is currently managing. + * This includes all ready, blocked and suspended tasks.  A task that + * has been deleted but not yet freed by the idle task will also be + * included in the count. + * + * \page uxTaskGetNumberOfTasks uxTaskGetNumberOfTasks + * \ingroup TaskUtils + */ +unsigned portBASE_TYPE uxTaskGetNumberOfTasks (void); + +/** + * task. h + * <PRE>void vTaskList( portCHAR *pcWriteBuffer );</PRE> + * + * configUSE_TRACE_FACILITY, INCLUDE_vTaskDelete and INCLUDE_vTaskSuspend + * must all be defined as 1 for this function to be available. + * See the configuration section for more information. + * + * NOTE: This function will disable interrupts for its duration.  It is + * not intended for normal application runtime use but as a debug aid. + * + * Lists all the current tasks, along with their current state and stack + * usage high water mark. + * + * Tasks are reported as blocked ('B'), ready ('R'), deleted ('D') or + * suspended ('S'). + * + * @param pcWriteBuffer A buffer into which the above mentioned details + * will be written, in ascii form.  This buffer is assumed to be large + * enough to contain the generated report.  Approximately 40 bytes per + * task should be sufficient. + * + * \page vTaskList vTaskList + * \ingroup TaskUtils + */ +void vTaskList (signed portCHAR * pcWriteBuffer); + +/** + * task. h + * <PRE>void vTaskStartTrace( portCHAR * pcBuffer, unsigned portBASE_TYPE uxBufferSize );</PRE> + * + * Starts a real time kernel activity trace.  The trace logs the identity of + * which task is running when. + * + * The trace file is stored in binary format.  A separate DOS utility called + * convtrce.exe is used to convert this into a tab delimited text file which + * can be viewed and plotted in a spread sheet. + * + * @param pcBuffer The buffer into which the trace will be written. + * + * @param ulBufferSize The size of pcBuffer in bytes.  The trace will continue + * until either the buffer in full, or ulTaskEndTrace () is called. + * + * \page vTaskStartTrace vTaskStartTrace + * \ingroup TaskUtils + */ +void vTaskStartTrace (signed portCHAR * pcBuffer, +		      unsigned portLONG ulBufferSize); + +/** + * task. h + * <PRE>unsigned portLONG ulTaskEndTrace( void );</PRE> + * + * Stops a kernel activity trace.  See vTaskStartTrace (). + * + * @return The number of bytes that have been written into the trace buffer. + * + * \page usTaskEndTrace usTaskEndTrace + * \ingroup TaskUtils + */ +unsigned portLONG ulTaskEndTrace (void); + + +/*----------------------------------------------------------- + * SCHEDULER INTERNALS AVAILABLE FOR PORTING PURPOSES + *----------------------------------------------------------*/ + +/* + * THIS FUNCTION MUST NOT BE USED FROM APPLICATION CODE.  IT IS ONLY + * INTENDED FOR USE WHEN IMPLEMENTING A PORT OF THE SCHEDULER AND IS + * AN INTERFACE WHICH IS FOR THE EXCLUSIVE USE OF THE SCHEDULER. + * + * Called from the real time kernel tick (either preemptive or cooperative), + * this increments the tick count and checks if any tasks that are blocked + * for a finite period required removing from a blocked list and placing on + * a ready list. + */ +inline void vTaskIncrementTick (void); + +/* + * THIS FUNCTION MUST NOT BE USED FROM APPLICATION CODE.  IT IS AN + * INTERFACE WHICH IS FOR THE EXCLUSIVE USE OF THE SCHEDULER. + * + * THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED. + * + * Removes the calling task from the ready list and places it both + * on the list of tasks waiting for a particular event, and the + * list of delayed tasks.  The task will be removed from both lists + * and replaced on the ready list should either the event occur (and + * there be no higher priority tasks waiting on the same event) or + * the delay period expires. + * + * @param pxEventList The list containing tasks that are blocked waiting + * for the event to occur. + * + * @param xTicksToWait The maximum amount of time that the task should wait + * for the event to occur.  This is specified in kernel ticks,the constant + * portTICK_RATE_MS can be used to convert kernel ticks into a real time + * period. + */ +void vTaskPlaceOnEventList (xList * pxEventList, portTickType xTicksToWait); + +/* + * THIS FUNCTION MUST NOT BE USED FROM APPLICATION CODE.  IT IS AN + * INTERFACE WHICH IS FOR THE EXCLUSIVE USE OF THE SCHEDULER. + * + * THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED. + * + * Removes a task from both the specified event list and the list of blocked + * tasks, and places it on a ready queue. + * + * xTaskRemoveFromEventList () will be called if either an event occurs to + * unblock a task, or the block timeout period expires. + * + * @return pdTRUE if the task being removed has a higher priority than the task + * making the call, otherwise pdFALSE. + */ +signed portBASE_TYPE xTaskRemoveFromEventList (const xList * pxEventList); + +/* + * THIS FUNCTION MUST NOT BE USED FROM APPLICATION CODE.  IT IS AN + * INTERFACE WHICH IS FOR THE EXCLUSIVE USE OF THE SCHEDULER. + * + * INCLUDE_vTaskCleanUpResources and INCLUDE_vTaskSuspend must be defined as 1 + * for this function to be available. + * See the configuration section for more information. + * + * Empties the ready and delayed queues of task control blocks, freeing the + * memory allocated for the task control block and task stacks as it goes. + */ +void vTaskCleanUpResources (void); + +/* + * THIS FUNCTION MUST NOT BE USED FROM APPLICATION CODE.  IT IS ONLY + * INTENDED FOR USE WHEN IMPLEMENTING A PORT OF THE SCHEDULER AND IS + * AN INTERFACE WHICH IS FOR THE EXCLUSIVE USE OF THE SCHEDULER. + * + * Sets the pointer to the current TCB to the TCB of the highest priority task + * that is ready to run. + */ +inline void vTaskSwitchContext (void); + +/* + * Return the handle of the calling task. + */ +xTaskHandle xTaskGetCurrentTaskHandle (void); + +/* + * Capture the current time status for future reference. + */ +void vTaskSetTimeOutState (xTimeOutType * pxTimeOut); + +/* + * Compare the time status now with that previously captured to see if the + * timeout has expired. + */ +portBASE_TYPE xTaskCheckForTimeOut (xTimeOutType * pxTimeOut, +				    portTickType * pxTicksToWait); + +/* + * Shortcut used by the queue implementation to prevent unnecessary call to + * taskYIELD(); + */ +void vTaskMissedYield (void); + +#endif /* TASK_H */ diff --git a/openpicc/os/core/list.c b/openpicc/os/core/list.c new file mode 100644 index 0000000..e6db76a --- /dev/null +++ b/openpicc/os/core/list.c @@ -0,0 +1,215 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license +	and contact details.  Please ensure to read the configuration and relevant +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +/* +Changes from V1.2.0 + +	+ Removed the volatile modifier from the function parameters.  This was +	  only ever included to prevent compiler warnings.  Now warnings are +	  removed by casting parameters where the calls are made. + +	+ prvListGetOwnerOfNextEntry() and prvListGetOwnerOfHeadEntry() have been +	  removed from the c file and added as macros to the h file. + +	+ uxNumberOfItems has been added to the list structure.  This removes the +	  need for a pointer comparison when checking if a list is empty, and so +	  is slightly faster. + +	+ Removed the NULL check in vListRemove().  This makes the call faster but +	  necessitates any application code utilising the list implementation to +	  ensure NULL pointers are not passed. + +Changes from V2.0.0 + +	+ Double linked the lists to allow faster removal item removal. + +Changes from V2.6.1 + +	+ Make use of the new portBASE_TYPE definition where ever appropriate. + +Changes from V3.0.0 + +	+ API changes as described on the FreeRTOS.org WEB site. + +Changes from V3.2.4 + +	+ Removed the pxHead member of the xList structure.  This always pointed +	  to the same place so has been removed to free a few bytes of RAM. + +	+ Introduced the xMiniListItem structure that does not include the  +	  xListItem members that are not required by the xListEnd member of a list. +	  Again this was done to reduce RAM usage. + +	+ Changed the volatile definitions of some structure members to clean up +	  the code where the list structures are used. + +Changes from V4.0.4 + +	+ Optimised vListInsert() in the case when the wake time is the maximum  +	  tick count value. +*/ + +#include <stdlib.h> +#include "FreeRTOS.h" +#include "list.h" + +/*----------------------------------------------------------- + * PUBLIC LIST API documented in list.h + *----------------------------------------------------------*/ + +void +vListInitialise (xList * pxList) +{ +  /* The list structure contains a list item which is used to mark the +     end of the list.  To initialise the list the list end is inserted +     as the only list entry. */ +  pxList->pxIndex = (xListItem *) & (pxList->xListEnd); + +  /* The list end value is the highest possible value in the list to +     ensure it remains at the end of the list. */ +  pxList->xListEnd.xItemValue = portMAX_DELAY; + +  /* The list end next and previous pointers point to itself so we know +     when the list is empty. */ +  pxList->xListEnd.pxNext = (xListItem *) & (pxList->xListEnd); +  pxList->xListEnd.pxPrevious = (xListItem *) & (pxList->xListEnd); + +  pxList->uxNumberOfItems = 0; +} + +/*-----------------------------------------------------------*/ + +void +vListInitialiseItem (xListItem * pxItem) +{ +  /* Make sure the list item is not recorded as being on a list. */ +  pxItem->pvContainer = NULL; +} + +/*-----------------------------------------------------------*/ + +void +vListInsertEnd (xList * pxList, xListItem * pxNewListItem) +{ +  volatile xListItem *pxIndex; + +  /* Insert a new list item into pxList, but rather than sort the list, +     makes the new list item the last item to be removed by a call to +     pvListGetOwnerOfNextEntry.  This means it has to be the item pointed to by +     the pxIndex member. */ +  pxIndex = pxList->pxIndex; + +  pxNewListItem->pxNext = pxIndex->pxNext; +  pxNewListItem->pxPrevious = pxList->pxIndex; +  pxIndex->pxNext->pxPrevious = (volatile xListItem *) pxNewListItem; +  pxIndex->pxNext = (volatile xListItem *) pxNewListItem; +  pxList->pxIndex = (volatile xListItem *) pxNewListItem; + +  /* Remember which list the item is in. */ +  pxNewListItem->pvContainer = (void *) pxList; + +  (pxList->uxNumberOfItems)++; +} + +/*-----------------------------------------------------------*/ + +void +vListInsert (xList * pxList, xListItem * pxNewListItem) +{ +  volatile xListItem *pxIterator; +  portTickType xValueOfInsertion; + +  /* Insert the new list item into the list, sorted in ulListItem order. */ +  xValueOfInsertion = pxNewListItem->xItemValue; + +  /* If the list already contains a list item with the same item value then +     the new list item should be placed after it.  This ensures that TCB's which +     are stored in ready lists (all of which have the same ulListItem value) +     get an equal share of the CPU.  However, if the xItemValue is the same as  +     the back marker the iteration loop below will not end.  This means we need +     to guard against this by checking the value first and modifying the  +     algorithm slightly if necessary. */ +  if (xValueOfInsertion == portMAX_DELAY) +    { +      pxIterator = pxList->xListEnd.pxPrevious; +    } +  else +    { +      for (pxIterator = (xListItem *) & (pxList->xListEnd); +	   pxIterator->pxNext->xItemValue <= xValueOfInsertion; +	   pxIterator = pxIterator->pxNext) +	{ +	  /* There is nothing to do here, we are just iterating to the +	     wanted insertion position. */ +	} +    } + +  pxNewListItem->pxNext = pxIterator->pxNext; +  pxNewListItem->pxNext->pxPrevious = (volatile xListItem *) pxNewListItem; +  pxNewListItem->pxPrevious = pxIterator; +  pxIterator->pxNext = (volatile xListItem *) pxNewListItem; + +  /* Remember which list the item is in.  This allows fast removal of the +     item later. */ +  pxNewListItem->pvContainer = (void *) pxList; + +  (pxList->uxNumberOfItems)++; +} + +/*-----------------------------------------------------------*/ + +void +vListRemove (xListItem * pxItemToRemove) +{ +  xList *pxList; + +  pxItemToRemove->pxNext->pxPrevious = pxItemToRemove->pxPrevious; +  pxItemToRemove->pxPrevious->pxNext = pxItemToRemove->pxNext; + +  /* The list item knows which list it is in.  Obtain the list from the list +     item. */ +  pxList = (xList *) pxItemToRemove->pvContainer; + +  /* Make sure the index is left pointing to a valid item. */ +  if (pxList->pxIndex == pxItemToRemove) +    { +      pxList->pxIndex = pxItemToRemove->pxPrevious; +    } + +  pxItemToRemove->pvContainer = NULL; +  (pxList->uxNumberOfItems)--; +} + +/*-----------------------------------------------------------*/ diff --git a/openpicc/os/core/queue.c b/openpicc/os/core/queue.c new file mode 100644 index 0000000..c2f08cb --- /dev/null +++ b/openpicc/os/core/queue.c @@ -0,0 +1,1002 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license +	and contact details.  Please ensure to read the configuration and relevant +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version along +	with commercial development and support options. +	*************************************************************************** +*/ + +/* +Changes from V1.01 + +	+ More use of 8bit data types. +	+ Function name prefixes changed where the data type returned has changed. + +Changed from V2.0.0 + +	+ Added the queue locking mechanism and make more use of the scheduler +	  suspension feature to minimise the time interrupts have to be disabled +	  when accessing a queue. + +Changed from V2.2.0 + +	+ Explicit use of 'signed' qualifier on portCHAR types added. + +Changes from V3.0.0 + +	+ API changes as described on the FreeRTOS.org WEB site. + +Changes from V3.2.3 + +	+ Added the queue functions that can be used from co-routines. + +Changes from V4.0.5 + +	+ Added a loop within xQueueSend() and xQueueReceive() to prevent the +	  functions exiting when a block time remains and the function has +	  not completed. + +Changes from V4.1.2: + +	+ BUG FIX:  Removed the call to prvIsQueueEmpty from within xQueueCRReceive +	  as it exited with interrupts enabled.  Thanks Paul Katz. + +Changes from V4.1.3: + +	+ Modified xQueueSend() and xQueueReceive() to handle the (very unlikely)  +	case whereby a task unblocking due to a temporal event can remove/send an  +	item from/to a queue when a higher priority task is	still blocked on the  +	queue.  This modification is a result of the SafeRTOS testing. +*/ + +#include <stdlib.h> +#include <string.h> +#include "FreeRTOS.h" +#include "task.h" +#include "croutine.h" + +/*----------------------------------------------------------- + * PUBLIC LIST API documented in list.h + *----------------------------------------------------------*/ + +/* Constants used with the cRxLock and cTxLock structure members. */ +#define queueUNLOCKED	( ( signed portBASE_TYPE ) -1 ) +#define queueERRONEOUS_UNBLOCK					( -1 ) + +/* + * Definition of the queue used by the scheduler. + * Items are queued by copy, not reference. + */ +typedef struct QueueDefinition +{ +  signed portCHAR *pcHead;	/*< Points to the beginning of the queue storage area. */ +  signed portCHAR *pcTail;	/*< Points to the byte at the end of the queue storage area.  Once more byte is allocated than necessary to store the queue items, this is used as a marker. */ + +  signed portCHAR *pcWriteTo;	/*< Points to the free next place in the storage area. */ +  signed portCHAR *pcReadFrom;	/*< Points to the last place that a queued item was read from. */ + +  xList xTasksWaitingToSend;	/*< List of tasks that are blocked waiting to post onto this queue.  Stored in priority order. */ +  xList xTasksWaitingToReceive;	/*< List of tasks that are blocked waiting to read from this queue.  Stored in priority order. */ + +  unsigned portBASE_TYPE uxMessagesWaiting;	/*< The number of items currently in the queue. */ +  unsigned portBASE_TYPE uxLength;	/*< The length of the queue defined as the number of items it will hold, not the number of bytes. */ +  unsigned portBASE_TYPE uxItemSize;	/*< The size of each items that the queue will hold. */ + +  signed portBASE_TYPE 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. */ +  signed portBASE_TYPE 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. */ +} xQUEUE; +/*-----------------------------------------------------------*/ + +/* + * Inside this file xQueueHandle is a pointer to a xQUEUE structure. + * To keep the definition private the API header file defines it as a + * pointer to void. + */ +typedef xQUEUE *xQueueHandle; + +/* + * Prototypes for public functions are included here so we don't have to + * include the API header file (as it defines xQueueHandle differently).  These + * functions are documented in the API header file. + */ +xQueueHandle xQueueCreate (unsigned portBASE_TYPE uxQueueLength, +			   unsigned portBASE_TYPE uxItemSize); +signed portBASE_TYPE xQueueSend (xQueueHandle xQueue, +				 const void *pvItemToQueue, +				 portTickType xTicksToWait); +unsigned portBASE_TYPE uxQueueMessagesWaiting (xQueueHandle pxQueue); +void vQueueDelete (xQueueHandle xQueue); +signed portBASE_TYPE xQueueSendFromISR (xQueueHandle pxQueue, +					const void *pvItemToQueue, +					signed portBASE_TYPE +					xTaskPreviouslyWoken); +signed portBASE_TYPE xQueueReceive (xQueueHandle pxQueue, void *pvBuffer, +				    portTickType xTicksToWait); +signed portBASE_TYPE xQueueReceiveFromISR (xQueueHandle pxQueue, +					   void *pvBuffer, +					   signed portBASE_TYPE * +					   pxTaskWoken); + +#if configUSE_CO_ROUTINES == 1 +signed portBASE_TYPE xQueueCRSendFromISR (xQueueHandle pxQueue, +					  const void *pvItemToQueue, +					  signed portBASE_TYPE +					  xCoRoutinePreviouslyWoken); +signed portBASE_TYPE xQueueCRReceiveFromISR (xQueueHandle pxQueue, +					     void *pvBuffer, +					     signed portBASE_TYPE * +					     pxTaskWoken); +signed portBASE_TYPE xQueueCRSend (xQueueHandle pxQueue, +				   const void *pvItemToQueue, +				   portTickType xTicksToWait); +signed portBASE_TYPE xQueueCRReceive (xQueueHandle pxQueue, void *pvBuffer, +				      portTickType xTicksToWait); +#endif + +/* + * Unlocks a queue locked by a call to prvLockQueue.  Locking a queue does not + * prevent an ISR from adding or removing items to the queue, but does prevent + * an ISR from removing tasks from the queue event lists.  If an ISR finds a + * queue is locked it will instead increment the appropriate queue lock count + * to indicate that a task may require unblocking.  When the queue in unlocked + * these lock counts are inspected, and the appropriate action taken. + */ +static void prvUnlockQueue (xQueueHandle pxQueue); + +/* + * Uses a critical section to determine if there is any data in a queue. + * + * @return pdTRUE if the queue contains no items, otherwise pdFALSE. + */ +static signed portBASE_TYPE prvIsQueueEmpty (const xQueueHandle pxQueue); + +/* + * Uses a critical section to determine if there is any space in a queue. + * + * @return pdTRUE if there is no space, otherwise pdFALSE; + */ +static signed portBASE_TYPE prvIsQueueFull (const xQueueHandle pxQueue); + +/* + * Macro that copies an item into the queue.  This is done by copying the item + * byte for byte, not by reference.  Updates the queue state to ensure it's + * integrity after the copy. + */ +#define prvCopyQueueData( pxQueue, pvItemToQueue )												\ +{																								\ +	memcpy( ( void * ) pxQueue->pcWriteTo, pvItemToQueue, ( unsigned ) pxQueue->uxItemSize );	\ +	++( pxQueue->uxMessagesWaiting );															\ +	pxQueue->pcWriteTo += pxQueue->uxItemSize;													\ +	if( pxQueue->pcWriteTo >= pxQueue->pcTail )													\ +	{																							\ +		pxQueue->pcWriteTo = pxQueue->pcHead;													\ +	}																							\ +} +/*-----------------------------------------------------------*/ + +/* + * Macro to mark a queue as locked.  Locking a queue prevents an ISR from + * accessing the queue event lists. + */ +#define prvLockQueue( pxQueue )			\ +{										\ +	taskENTER_CRITICAL();				\ +		++( pxQueue->xRxLock );			\ +		++( pxQueue->xTxLock );			\ +	taskEXIT_CRITICAL();				\ +} +/*-----------------------------------------------------------*/ + + +/*----------------------------------------------------------- + * PUBLIC QUEUE MANAGEMENT API documented in queue.h + *----------------------------------------------------------*/ + +xQueueHandle +xQueueCreate (unsigned portBASE_TYPE uxQueueLength, +	      unsigned portBASE_TYPE uxItemSize) +{ +  xQUEUE *pxNewQueue; +  size_t xQueueSizeInBytes; + +  /* Allocate the new queue structure. */ +  if (uxQueueLength > (unsigned portBASE_TYPE) 0) +    { +      pxNewQueue = (xQUEUE *) pvPortMalloc (sizeof (xQUEUE)); +      if (pxNewQueue != NULL) +	{ +	  /* Create the list of pointers to queue items.  The queue is one byte +	     longer than asked for to make wrap checking easier/faster. */ +	  xQueueSizeInBytes = +	    (size_t) (uxQueueLength * uxItemSize) + (size_t) 1; + +	  pxNewQueue->pcHead = +	    (signed portCHAR *) pvPortMalloc (xQueueSizeInBytes); +	  if (pxNewQueue->pcHead != NULL) +	    { +	      /* Initialise the queue members as described above where the +	         queue type is defined. */ +	      pxNewQueue->pcTail = +		pxNewQueue->pcHead + (uxQueueLength * uxItemSize); +	      pxNewQueue->uxMessagesWaiting = 0; +	      pxNewQueue->pcWriteTo = pxNewQueue->pcHead; +	      pxNewQueue->pcReadFrom = +		pxNewQueue->pcHead + ((uxQueueLength - 1) * uxItemSize); +	      pxNewQueue->uxLength = uxQueueLength; +	      pxNewQueue->uxItemSize = uxItemSize; +	      pxNewQueue->xRxLock = queueUNLOCKED; +	      pxNewQueue->xTxLock = queueUNLOCKED; + +	      /* Likewise ensure the event queues start with the correct state. */ +	      vListInitialise (&(pxNewQueue->xTasksWaitingToSend)); +	      vListInitialise (&(pxNewQueue->xTasksWaitingToReceive)); + +	      return pxNewQueue; +	    } +	  else +	    { +	      vPortFree (pxNewQueue); +	    } +	} +    } + +  /* Will only reach here if we could not allocate enough memory or no memory +     was required. */ +  return NULL; +} + +/*-----------------------------------------------------------*/ + +signed portBASE_TYPE +xQueueSend (xQueueHandle pxQueue, const void *pvItemToQueue, +	    portTickType xTicksToWait) +{ +  signed portBASE_TYPE xReturn = pdPASS; +  xTimeOutType xTimeOut; + +  /* Make sure other tasks do not access the queue. */ +  vTaskSuspendAll (); + +  /* Capture the current time status for future reference. */ +  vTaskSetTimeOutState (&xTimeOut); + +  /* It is important that this is the only thread/ISR that modifies the +     ready or delayed lists until xTaskResumeAll() is called.  Places where +     the ready/delayed lists are modified include: + +     + vTaskDelay() -  Nothing can call vTaskDelay as the scheduler is +     suspended, vTaskDelay() cannot be called from an ISR. +     + vTaskPrioritySet() - Has a critical section around the access. +     + vTaskSwitchContext() - This will not get executed while the scheduler +     is suspended. +     + prvCheckDelayedTasks() - This will not get executed while the +     scheduler is suspended. +     + xTaskCreate() - Has a critical section around the access. +     + vTaskResume() - Has a critical section around the access. +     + xTaskResumeAll() - Has a critical section around the access. +     + xTaskRemoveFromEventList - Checks to see if the scheduler is +     suspended.  If so then the TCB being removed from the event is +     removed from the event and added to the xPendingReadyList. +   */ + +  /* Make sure interrupts do not access the queue event list. */ +  prvLockQueue (pxQueue); + +  /* It is important that interrupts to not access the event list of the +     queue being modified here.  Places where the event list is modified +     include: + +     + xQueueSendFromISR().  This checks the lock on the queue to see if +     it has access.  If the queue is locked then the Tx lock count is +     incremented to signify that a task waiting for data can be made ready +     once the queue lock is removed.  If the queue is not locked then +     a task can be moved from the event list, but will not be removed +     from the delayed list or placed in the ready list until the scheduler +     is unlocked. + +     + xQueueReceiveFromISR().  As per xQueueSendFromISR(). +   */ + +  /* If the queue is already full we may have to block. */ +  do +    { +      if (prvIsQueueFull (pxQueue)) +	{ +	  /* The queue is full - do we want to block or just leave without +	     posting? */ +	  if (xTicksToWait > (portTickType) 0) +	    { +	      /* We are going to place ourselves on the xTasksWaitingToSend event +	         list, and will get woken should the delay expire, or space become +	         available on the queue. + +	         As detailed above we do not require mutual exclusion on the event +	         list as nothing else can modify it or the ready lists while we +	         have the scheduler suspended and queue locked. + +	         It is possible that an ISR has removed data from the queue since we +	         checked if any was available.  If this is the case then the data +	         will have been copied from the queue, and the queue variables +	         updated, but the event list will not yet have been checked to see if +	         anything is waiting as the queue is locked. */ +	      vTaskPlaceOnEventList (&(pxQueue->xTasksWaitingToSend), +				     xTicksToWait); + +	      /* Force a context switch now as we are blocked.  We can do +	         this from within a critical section as the task we are +	         switching to has its own context.  When we return here (i.e. we +	         unblock) we will leave the critical section as normal. + +	         It is possible that an ISR has caused an event on an unrelated and +	         unlocked queue.  If this was the case then the event list for that +	         queue will have been updated but the ready lists left unchanged - +	         instead the readied task will have been added to the pending ready +	         list. */ +	      taskENTER_CRITICAL (); +	      { +		/* We can safely unlock the queue and scheduler here as +		   interrupts are disabled.  We must not yield with anything +		   locked, but we can yield from within a critical section. + +		   Tasks that have been placed on the pending ready list cannot +		   be tasks that are waiting for events on this queue.  See +		   in comment xTaskRemoveFromEventList(). */ +		prvUnlockQueue (pxQueue); + +		/* Resuming the scheduler may cause a yield.  If so then there +		   is no point yielding again here. */ +		if (!xTaskResumeAll ()) +		  { +		    taskYIELD (); +		  } + +		/* We want to check to see if the queue is still full +		   before leaving the critical section.  This is to prevent +		   this task placing an item into the queue due to an +		   interrupt making space on the queue between critical +		   sections (when there might be a higher priority task +		   blocked on the queue that cannot run yet because the +		   scheduler gets suspended). */ +		if (pxQueue->uxMessagesWaiting == pxQueue->uxLength) +		  { +		    /* We unblocked but there is no space in the queue, +		       we probably timed out. */ +		    xReturn = errQUEUE_FULL; +		  } + +		/* Before leaving the critical section we have to ensure +		   exclusive access again. */ +		vTaskSuspendAll (); +		prvLockQueue (pxQueue); +	      } +	      taskEXIT_CRITICAL (); +	    } +	} + +      /* If xReturn is errQUEUE_FULL then we unblocked when the queue +         was still full.  Don't check it again now as it is possible that +         an interrupt has removed an item from the queue since we left the +         critical section and we don't want to write to the queue in case +         there is a task of higher priority blocked waiting for space to +         be available on the queue.  If this is the case the higher priority +         task will execute when the scheduler is unsupended. */ +      if (xReturn != errQUEUE_FULL) +	{ +	  /* When we are here it is possible that we unblocked as space became +	     available on the queue.  It is also possible that an ISR posted to the +	     queue since we left the critical section, so it may be that again there +	     is no space.  This would only happen if a task and ISR post onto the +	     same queue. */ +	  taskENTER_CRITICAL (); +	  { +	    if (pxQueue->uxMessagesWaiting < pxQueue->uxLength) +	      { +		/* There is room in the queue, copy the data into the queue. */ +		prvCopyQueueData (pxQueue, pvItemToQueue); +		xReturn = pdPASS; + +		/* Update the TxLock count so prvUnlockQueue knows to check for +		   tasks waiting for data to become available in the queue. */ +		++(pxQueue->xTxLock); +	      } +	    else +	      { +		xReturn = errQUEUE_FULL; +	      } +	  } +	  taskEXIT_CRITICAL (); +	} + +      if (xReturn == errQUEUE_FULL) +	{ +	  if (xTicksToWait > 0) +	    { +	      if (xTaskCheckForTimeOut (&xTimeOut, &xTicksToWait) == pdFALSE) +		{ +		  xReturn = queueERRONEOUS_UNBLOCK; +		} +	    } +	} +    } +  while (xReturn == queueERRONEOUS_UNBLOCK); + +  prvUnlockQueue (pxQueue); +  xTaskResumeAll (); + +  return xReturn; +} + +/*-----------------------------------------------------------*/ + +signed portBASE_TYPE +xQueueSendFromISR (xQueueHandle pxQueue, const void *pvItemToQueue, +		   signed portBASE_TYPE xTaskPreviouslyWoken) +{ +  /* Similar to xQueueSend, except we don't block if there is no room in the +     queue.  Also we don't directly wake a task that was blocked on a queue +     read, instead we return a flag to say whether a context switch is required +     or not (i.e. has a task with a higher priority than us been woken by this +     post). */ +  if (pxQueue->uxMessagesWaiting < pxQueue->uxLength) +    { +      prvCopyQueueData (pxQueue, pvItemToQueue); + +      /* If the queue is locked we do not alter the event list.  This will +         be done when the queue is unlocked later. */ +      if (pxQueue->xTxLock == queueUNLOCKED) +	{ +	  /* We only want to wake one task per ISR, so check that a task has +	     not already been woken. */ +	  if (!xTaskPreviouslyWoken) +	    { +	      if (!listLIST_IS_EMPTY (&(pxQueue->xTasksWaitingToReceive))) +		{ +		  if (xTaskRemoveFromEventList +		      (&(pxQueue->xTasksWaitingToReceive)) != pdFALSE) +		    { +		      /* The task waiting has a higher priority so record that a +		         context      switch is required. */ +		      return pdTRUE; +		    } +		} +	    } +	} +      else +	{ +	  /* Increment the lock count so the task that unlocks the queue +	     knows that data was posted while it was locked. */ +	  ++(pxQueue->xTxLock); +	} +    } + +  return xTaskPreviouslyWoken; +} + +/*-----------------------------------------------------------*/ + +signed portBASE_TYPE +xQueueReceive (xQueueHandle pxQueue, void *pvBuffer, +	       portTickType xTicksToWait) +{ +  signed portBASE_TYPE xReturn = pdTRUE; +  xTimeOutType xTimeOut; + +  /* This function is very similar to xQueueSend().  See comments within +     xQueueSend() for a more detailed explanation. + +     Make sure other tasks do not access the queue. */ +  vTaskSuspendAll (); + +  /* Capture the current time status for future reference. */ +  vTaskSetTimeOutState (&xTimeOut); + +  /* Make sure interrupts do not access the queue. */ +  prvLockQueue (pxQueue); + +  do +    { +      /* If there are no messages in the queue we may have to block. */ +      if (prvIsQueueEmpty (pxQueue)) +	{ +	  /* There are no messages in the queue, do we want to block or just +	     leave with nothing? */ +	  if (xTicksToWait > (portTickType) 0) +	    { +	      vTaskPlaceOnEventList (&(pxQueue->xTasksWaitingToReceive), +				     xTicksToWait); +	      taskENTER_CRITICAL (); +	      { +		prvUnlockQueue (pxQueue); +		if (!xTaskResumeAll ()) +		  { +		    taskYIELD (); +		  } + +		if (pxQueue->uxMessagesWaiting == (unsigned portBASE_TYPE) 0) +		  { +		    /* We unblocked but the queue is empty.  We probably +		       timed out. */ +		    xReturn = errQUEUE_EMPTY; +		  } + +		vTaskSuspendAll (); +		prvLockQueue (pxQueue); +	      } +	      taskEXIT_CRITICAL (); +	    } +	} + +      if (xReturn != errQUEUE_EMPTY) +	{ +	  taskENTER_CRITICAL (); +	  { +	    if (pxQueue->uxMessagesWaiting > (unsigned portBASE_TYPE) 0) +	      { +		pxQueue->pcReadFrom += pxQueue->uxItemSize; +		if (pxQueue->pcReadFrom >= pxQueue->pcTail) +		  { +		    pxQueue->pcReadFrom = pxQueue->pcHead; +		  } +		--(pxQueue->uxMessagesWaiting); +		memcpy ((void *) pvBuffer, (void *) pxQueue->pcReadFrom, +			(unsigned) pxQueue->uxItemSize); + +		/* Increment the lock count so prvUnlockQueue knows to check for +		   tasks waiting for space to become available on the queue. */ +		++(pxQueue->xRxLock); +		xReturn = pdPASS; +	      } +	    else +	      { +		xReturn = errQUEUE_EMPTY; +	      } +	  } +	  taskEXIT_CRITICAL (); +	} + +      if (xReturn == errQUEUE_EMPTY) +	{ +	  if (xTicksToWait > 0) +	    { +	      if (xTaskCheckForTimeOut (&xTimeOut, &xTicksToWait) == pdFALSE) +		{ +		  xReturn = queueERRONEOUS_UNBLOCK; +		} +	    } +	} +    } +  while (xReturn == queueERRONEOUS_UNBLOCK); + +  /* We no longer require exclusive access to the queue. */ +  prvUnlockQueue (pxQueue); +  xTaskResumeAll (); + +  return xReturn; +} + +/*-----------------------------------------------------------*/ + +signed portBASE_TYPE +xQueueReceiveFromISR (xQueueHandle pxQueue, void *pvBuffer, +		      signed portBASE_TYPE * pxTaskWoken) +{ +  signed portBASE_TYPE xReturn; + +  /* We cannot block from an ISR, so check there is data available. */ +  if (pxQueue->uxMessagesWaiting > (unsigned portBASE_TYPE) 0) +    { +      /* Copy the data from the queue. */ +      pxQueue->pcReadFrom += pxQueue->uxItemSize; +      if (pxQueue->pcReadFrom >= pxQueue->pcTail) +	{ +	  pxQueue->pcReadFrom = pxQueue->pcHead; +	} +      --(pxQueue->uxMessagesWaiting); +      memcpy ((void *) pvBuffer, (void *) pxQueue->pcReadFrom, +	      (unsigned) pxQueue->uxItemSize); + +      /* If the queue is locked we will not modify the event list.  Instead +         we 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) +	{ +	  /* We only want to wake one task per ISR, so check that a task has +	     not already been woken. */ +	  if (!(*pxTaskWoken)) +	    { +	      if (!listLIST_IS_EMPTY (&(pxQueue->xTasksWaitingToSend))) +		{ +		  if (xTaskRemoveFromEventList +		      (&(pxQueue->xTasksWaitingToSend)) != pdFALSE) +		    { +		      /* The task waiting has a higher priority than us so +		         force a context switch. */ +		      *pxTaskWoken = pdTRUE; +		    } +		} +	    } +	} +      else +	{ +	  /* Increment the lock count so the task that unlocks the queue +	     knows that data was removed while it was locked. */ +	  ++(pxQueue->xRxLock); +	} + +      xReturn = pdPASS; +    } +  else +    { +      xReturn = pdFAIL; +    } + +  return xReturn; +} + +/*-----------------------------------------------------------*/ + +unsigned portBASE_TYPE +uxQueueMessagesWaiting (xQueueHandle pxQueue) +{ +  unsigned portBASE_TYPE uxReturn; + +  taskENTER_CRITICAL (); +  uxReturn = pxQueue->uxMessagesWaiting; +  taskEXIT_CRITICAL (); + +  return uxReturn; +} + +/*-----------------------------------------------------------*/ + +void +vQueueDelete (xQueueHandle pxQueue) +{ +  vPortFree (pxQueue->pcHead); +  vPortFree (pxQueue); +} + +/*-----------------------------------------------------------*/ + +static void +prvUnlockQueue (xQueueHandle pxQueue) +{ +  /* THIS FUNCTION MUST BE CALLED WITH THE SCHEDULER SUSPENDED. */ + +  /* The lock counts contains the number of extra data items placed or +     removed from the queue while the queue was locked.  When a queue is +     locked items can be added or removed, but the event lists cannot be +     updated. */ +  taskENTER_CRITICAL (); +  { +    --(pxQueue->xTxLock); + +    /* See if data was added to the queue while it was locked. */ +    if (pxQueue->xTxLock > queueUNLOCKED) +      { +	pxQueue->xTxLock = queueUNLOCKED; + +	/* Data was posted while the queue was locked.  Are any tasks +	   blocked waiting for data to become available? */ +	if (!listLIST_IS_EMPTY (&(pxQueue->xTasksWaitingToReceive))) +	  { +	    /* Tasks that are removed from the event list will get added to +	       the pending ready list as the scheduler is still suspended. */ +	    if (xTaskRemoveFromEventList (&(pxQueue->xTasksWaitingToReceive)) +		!= pdFALSE) +	      { +		/* The task waiting has a higher priority so record that a +		   context      switch is required. */ +		vTaskMissedYield (); +	      } +	  } +      } +  } +  taskEXIT_CRITICAL (); + +  /* Do the same for the Rx lock. */ +  taskENTER_CRITICAL (); +  { +    --(pxQueue->xRxLock); + +    if (pxQueue->xRxLock > queueUNLOCKED) +      { +	pxQueue->xRxLock = queueUNLOCKED; + +	if (!listLIST_IS_EMPTY (&(pxQueue->xTasksWaitingToSend))) +	  { +	    if (xTaskRemoveFromEventList (&(pxQueue->xTasksWaitingToSend)) != +		pdFALSE) +	      { +		vTaskMissedYield (); +	      } +	  } +      } +  } +  taskEXIT_CRITICAL (); +} + +/*-----------------------------------------------------------*/ + +static signed portBASE_TYPE +prvIsQueueEmpty (const xQueueHandle pxQueue) +{ +  signed portBASE_TYPE xReturn; + +  taskENTER_CRITICAL (); +  xReturn = (pxQueue->uxMessagesWaiting == (unsigned portBASE_TYPE) 0); +  taskEXIT_CRITICAL (); + +  return xReturn; +} + +/*-----------------------------------------------------------*/ + +static signed portBASE_TYPE +prvIsQueueFull (const xQueueHandle pxQueue) +{ +  signed portBASE_TYPE xReturn; + +  taskENTER_CRITICAL (); +  xReturn = (pxQueue->uxMessagesWaiting == pxQueue->uxLength); +  taskEXIT_CRITICAL (); + +  return xReturn; +} + +/*-----------------------------------------------------------*/ + +#if configUSE_CO_ROUTINES == 1 +signed portBASE_TYPE +xQueueCRSend (xQueueHandle pxQueue, const void *pvItemToQueue, +	      portTickType xTicksToWait) +{ +  signed portBASE_TYPE xReturn; + +  /* If the queue is already full we may have to block.  A critical section +     is required to prevent an interrupt removing something from the queue  +     between the check to see if the queue is full and blocking on the queue. */ +  portDISABLE_INTERRUPTS (); +  { +    if (prvIsQueueFull (pxQueue)) +      { +	/* The queue is full - do we want to block or just leave without +	   posting? */ +	if (xTicksToWait > (portTickType) 0) +	  { +	    /* As this is called from a coroutine we cannot block directly, but +	       return indicating that we need to block. */ +	    vCoRoutineAddToDelayedList (xTicksToWait, +					&(pxQueue->xTasksWaitingToSend)); +	    portENABLE_INTERRUPTS (); +	    return errQUEUE_BLOCKED; +	  } +	else +	  { +	    portENABLE_INTERRUPTS (); +	    return errQUEUE_FULL; +	  } +      } +  } +  portENABLE_INTERRUPTS (); + +  portNOP (); + +  portDISABLE_INTERRUPTS (); +  { +    if (pxQueue->uxMessagesWaiting < pxQueue->uxLength) +      { +	/* There is room in the queue, copy the data into the queue. */ +	prvCopyQueueData (pxQueue, pvItemToQueue); +	xReturn = pdPASS; + +	/* Were any co-routines waiting for data to become available? */ +	if (!listLIST_IS_EMPTY (&(pxQueue->xTasksWaitingToReceive))) +	  { +	    /* In this instance the co-routine could be placed directly  +	       into the ready list as we are within a critical section.   +	       Instead the same pending ready list mechansim is used as if +	       the event were caused from within an interrupt. */ +	    if (xCoRoutineRemoveFromEventList +		(&(pxQueue->xTasksWaitingToReceive)) != pdFALSE) +	      { +		/* The co-routine waiting has a higher priority so record  +		   that a yield might be appropriate. */ +		xReturn = errQUEUE_YIELD; +	      } +	  } +      } +    else +      { +	xReturn = errQUEUE_FULL; +      } +  } +  portENABLE_INTERRUPTS (); + +  return xReturn; +} +#endif +/*-----------------------------------------------------------*/ + +#if configUSE_CO_ROUTINES == 1 +signed portBASE_TYPE +xQueueCRReceive (xQueueHandle pxQueue, void *pvBuffer, +		 portTickType xTicksToWait) +{ +  signed portBASE_TYPE xReturn; + +  /* If the queue is already empty we may have to block.  A critical section +     is required to prevent an interrupt adding something to the queue  +     between the check to see if the queue is empty and blocking on the queue. */ +  portDISABLE_INTERRUPTS (); +  { +    if (pxQueue->uxMessagesWaiting == (unsigned portBASE_TYPE) 0) +      { +	/* There are no messages in the queue, do we want to block or just +	   leave with nothing? */ +	if (xTicksToWait > (portTickType) 0) +	  { +	    /* As this is a co-routine we cannot block directly, but return +	       indicating that we need to block. */ +	    vCoRoutineAddToDelayedList (xTicksToWait, +					&(pxQueue->xTasksWaitingToReceive)); +	    portENABLE_INTERRUPTS (); +	    return errQUEUE_BLOCKED; +	  } +	else +	  { +	    portENABLE_INTERRUPTS (); +	    return errQUEUE_FULL; +	  } +      } +  } +  portENABLE_INTERRUPTS (); + +  portNOP (); + +  portDISABLE_INTERRUPTS (); +  { +    if (pxQueue->uxMessagesWaiting > (unsigned portBASE_TYPE) 0) +      { +	/* Data is available from the queue. */ +	pxQueue->pcReadFrom += pxQueue->uxItemSize; +	if (pxQueue->pcReadFrom >= pxQueue->pcTail) +	  { +	    pxQueue->pcReadFrom = pxQueue->pcHead; +	  } +	--(pxQueue->uxMessagesWaiting); +	memcpy ((void *) pvBuffer, (void *) pxQueue->pcReadFrom, +		(unsigned) pxQueue->uxItemSize); + +	xReturn = pdPASS; + +	/* Were any co-routines waiting for space to become available? */ +	if (!listLIST_IS_EMPTY (&(pxQueue->xTasksWaitingToSend))) +	  { +	    /* In this instance the co-routine could be placed directly  +	       into the ready list as we are within a critical section.   +	       Instead the same pending ready list mechansim is used as if +	       the event were caused from within an interrupt. */ +	    if (xCoRoutineRemoveFromEventList +		(&(pxQueue->xTasksWaitingToSend)) != pdFALSE) +	      { +		xReturn = errQUEUE_YIELD; +	      } +	  } +      } +    else +      { +	xReturn = pdFAIL; +      } +  } +  portENABLE_INTERRUPTS (); + +  return xReturn; +} +#endif +/*-----------------------------------------------------------*/ + + + +#if configUSE_CO_ROUTINES == 1 +signed portBASE_TYPE +xQueueCRSendFromISR (xQueueHandle pxQueue, const void *pvItemToQueue, +		     signed portBASE_TYPE xCoRoutinePreviouslyWoken) +{ +  /* Cannot block within an ISR so if there is no space on the queue then +     exit without doing anything. */ +  if (pxQueue->uxMessagesWaiting < pxQueue->uxLength) +    { +      prvCopyQueueData (pxQueue, pvItemToQueue); + +      /* We only want to wake one co-routine per ISR, so check that a  +         co-routine has not already been woken. */ +      if (!xCoRoutinePreviouslyWoken) +	{ +	  if (!listLIST_IS_EMPTY (&(pxQueue->xTasksWaitingToReceive))) +	    { +	      if (xCoRoutineRemoveFromEventList +		  (&(pxQueue->xTasksWaitingToReceive)) != pdFALSE) +		{ +		  return pdTRUE; +		} +	    } +	} +    } + +  return xCoRoutinePreviouslyWoken; +} +#endif +/*-----------------------------------------------------------*/ + +#if configUSE_CO_ROUTINES == 1 +signed portBASE_TYPE +xQueueCRReceiveFromISR (xQueueHandle pxQueue, void *pvBuffer, +			signed portBASE_TYPE * pxCoRoutineWoken) +{ +  signed portBASE_TYPE xReturn; + +  /* We cannot block from an ISR, so check there is data available. If +     not then just leave without doing anything. */ +  if (pxQueue->uxMessagesWaiting > (unsigned portBASE_TYPE) 0) +    { +      /* Copy the data from the queue. */ +      pxQueue->pcReadFrom += pxQueue->uxItemSize; +      if (pxQueue->pcReadFrom >= pxQueue->pcTail) +	{ +	  pxQueue->pcReadFrom = pxQueue->pcHead; +	} +      --(pxQueue->uxMessagesWaiting); +      memcpy ((void *) pvBuffer, (void *) pxQueue->pcReadFrom, +	      (unsigned) pxQueue->uxItemSize); + +      if (!(*pxCoRoutineWoken)) +	{ +	  if (!listLIST_IS_EMPTY (&(pxQueue->xTasksWaitingToSend))) +	    { +	      if (xCoRoutineRemoveFromEventList +		  (&(pxQueue->xTasksWaitingToSend)) != pdFALSE) +		{ +		  *pxCoRoutineWoken = pdTRUE; +		} +	    } +	} + +      xReturn = pdPASS; +    } +  else +    { +      xReturn = pdFAIL; +    } + +  return xReturn; +} +#endif +/*-----------------------------------------------------------*/ diff --git a/openpicc/os/core/tasks.c b/openpicc/os/core/tasks.c new file mode 100644 index 0000000..68a0dd9 --- /dev/null +++ b/openpicc/os/core/tasks.c @@ -0,0 +1,1988 @@ +/* +	FreeRTOS.org V4.2.1 - Copyright (C) 2003-2007 Richard Barry. + +	This file is part of the FreeRTOS.org distribution. + +	FreeRTOS.org is free software; you can redistribute it and/or modify +	it under the terms of the GNU General Public License as published by +	the Free Software Foundation; either version 2 of the License, or +	(at your option) any later version. + +	FreeRTOS.org is distributed in the hope that it will be useful, +	but WITHOUT ANY WARRANTY; without even the implied warranty of +	MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the +	GNU General Public License for more details. + +	You should have received a copy of the GNU General Public License +	along with FreeRTOS.org; if not, write to the Free Software +	Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA  02111-1307  USA + +	A special exception to the GPL can be applied should you wish to distribute +	a combined work that includes FreeRTOS.org, without being obliged to provide +	the source code for any proprietary components.  See the licensing section +	of http://www.FreeRTOS.org for full details of how and when the exception +	can be applied. + +	*************************************************************************** +	See http://www.FreeRTOS.org for documentation, latest information, license +	and contact details.  Please ensure to read the configuration and relevant +	port sections of the online documentation. + +	Also see http://www.SafeRTOS.com for an IEC 61508 compliant version, along +	with development and support options. +	*************************************************************************** +*/ + +/* +Changes from V1.00: +	 +	+ Call to portRESTORE_CONTEXT has been removed.  The first context +	  switch is now performed within sPortStartScheduler(). + +Changes from V1.01: + +	+ More use of 8bit data types. +	+ Function name prefixes changed where the data type returned has changed. +	+ configUSE_TRACE_FACILITY is no longer defined by default. + +Changes from V1.2.0 + +	+ Introduced ucTopReadyPriority.  This tracks the highest priority ready +	  queue that contains a valid TCB and thus makes the context switch +	  slightly faster. + +	+ prvAddTaskToReadyQueue() has been made a macro. + +Changes from V1.2.6 + +	+ Added conditional compilation directives. +	+ Extended API. +	+ Rearranged function order. +	+ Creating a task now causes a context switch if the task being created +	  has a higher priority than the calling task - assuming the kernel is +	  running. +	+ vTaskDelete() now only causes a context switch if the calling task is +	  the task being deleted. + +Changes from V2.0.0 + +	+ Allow the type of the tick count to be 16 or 32 bits. +	+ Introduce xPendingReadyList feature to allow the time interrupts have to +	  be disabled to be minimised. +	+ Remove the #if( INCLUDE_vTaskSuspendAll ) statements.  vTaskSuspendAll() +	  is now always included as it is used by the scheduler itself. + +Changes from V2.1.0 + +	+ Bug fix - pxCurrentTCB is now initialised before the call to +	  prvInitializeTaskLists().  Previously pxCurrentTCB could be accessed +	  while null. + +Changed from V2.1.1 + +	+ Change to where lStackSize is declared within sTaskCreate() to prevent +	  compiler warnings with 8051 port. + +Changes from V2.2.0 + +	+ Explicit use of 'signed' qualifier on portCHAR types added. +	+ Changed odd calculation of initial pxTopOfStack value when +	  portSTACK_GROWTH < 0. +	+ Removed pcVersionNumber definition. + +Changes from V2.5.3 + +	+ cTaskResumeAll() modified to ensure it can be called prior to the task +	  lists being initialised. + +Changes from V2.5.5 + +	+ Added API function vTaskDelayUntil(). +	+ Added INCLUDE_vTaskDelay conditional compilation. + +Changes from V2.6.0 + + 	+ Updated the vWriteTraceToBuffer macro to always be 4 byte aligned so it +	  can be used on ARM architectures. +	+ tskMAX_TASK_NAME_LEN definition replaced with the port specific +	  configMAX_TASK_NAME_LEN definition. +	+ Removed the call to strcpy when copying across the task name into the +	  TCB. +	+ Added ucTasksDeleted variable to prevent vTaskSuspendAll() being called +	  too often in the idle task. + +Changes between V3.0.0 and V2.6.1 + +	+ When resuming the scheduler a yield is performed if either a tick has +	  been missed, or a task is moved from the pending ready list into a ready +	  list.  Previously a yield was not performed on this second condition. +	+ Introduced the type portBASE_TYPE.  This necessitates several API +	  changes. +	+ Removed the sUsingPreemption variable.  The constant defined in +	  portmacro.h is now used directly. +	+ The idle task can now include an optional hook function - and no longer +	  completes its time slice if other tasks with equal priority to it are +	  ready to run. +	+ See the FreeRTOS.org documentation for more information on V2.x.x to +	  V3.x.x modifications. + +Changes from V3.1.1 + +	+ Modified vTaskPrioritySet() and vTaskResume() to allow these functions to +	  be called while the scheduler is suspended. +	+ Corrected the task ordering within event lists. + +Changes from V3.2.0 + +	+ Added function xTaskGetCurrentTaskHandle(). + +Changes from V3.2.4 + +	+ Changed the volatile declarations on some variables to reflect the  +	  changes to the list definitions. +	+ Changed the order of the TCB definition so there is commonality between +	  the task control block and a co-routine control block. +	+ Allow the scheduler to be started even if no tasks other than the idle +	  task has been created.  This allows co-routines to run even when no tasks +	  have been created. +	+ The need for a context switch is now signalled if a task woken by an  +	  event has a priority greater or equal to the currently running task. +	  Previously this was only greater than. + +Changes from V4.0.0 + +	+ Added the xMissedYield handling. + +Changes from V4.0.1 + +	+ The function vTaskList() now suspends the scheduler rather than disabling +	  interrupts during the creation of the task list.   +	+ Allow a task to delete itself by passing in its own handle.  Previously  +	  this could only be done by passing in NULL. +	+ The tick hook function is now called only within a tick isr.  Previously +	  it was also called when the tick function was called during the scheduler +	  unlocking process. + +Changes from V4.0.3 + +	+ Extra checks have been placed in vTaskPrioritySet() to avoid unnecessary +	  yields. + +Changed from V4.0.4 + +	+ Bug fix:  The 'value' of the event list item is updated when the priority +	  of a task is changed.  Previously only the priority of the TCB itself was +	  changed. +	+ When resuming a task a check is first made to see if the task is actually +	  suspended. +	+ vTaskPrioritySet() and vTaskResume() no longer use the event list item. +	  This has not been necessary since V4.0.1 when the xMissedYield handling +	  was added. +	+ Implement xTaskResumeFromISR(). + +Changes from V4.0.5 + +	+ Added utility functions and xOverflowCount variable to facilitate the +	  queue.c changes. + +Changes from V4.1.2 +	 +	+ Tasks that block on events with a timeout of portMAX_DELAY are now +	  blocked indefinitely if configINCLUDE_vTaskSuspend is defined.  +	  Previously portMAX_DELAY was just the longest block time possible. + +Changes from V4.1.3 + +	+ Very small change made to xTaskCheckForTimeout() as a result of the  +	SafeRTOS testing.  This corrects the case where the function can return an +	invalid value - but only in an extremely unlikely scenario. +*/ + +#include <stdio.h> +#include <stdlib.h> +#include <string.h> + +#include "FreeRTOS.h" +#include "task.h" + +/* + * Macro to define the amount of stack available to the idle task. + */ +#define tskIDLE_STACK_SIZE	configMINIMAL_STACK_SIZE + + +/* + * Default a definitions for backwards compatibility with old + * portmacro.h files. + */ +#ifndef configMAX_TASK_NAME_LEN +#define configMAX_TASK_NAME_LEN 16 +#endif + +#ifndef INCLUDE_xTaskGetCurrentTaskHandle +#define INCLUDE_xTaskGetCurrentTaskHandle 0 +#endif + +#ifndef configIDLE_SHOULD_YIELD +#define configIDLE_SHOULD_YIELD		1 +#endif + +#if configMAX_TASK_NAME_LEN < 1 +#undef configMAX_TASK_NAME_LEN +#define configMAX_TASK_NAME_LEN 1 +#endif + +#ifndef INCLUDE_xTaskResumeFromISR +#define INCLUDE_xTaskResumeFromISR 1 +#endif + +/* + * Task control block.  A task control block (TCB) is allocated to each task, + * and stores the context of the task. + */ +typedef struct tskTaskControlBlock +{ +  volatile portSTACK_TYPE *pxTopOfStack;	/*< Points to the location of the last item placed on the tasks stack.  THIS MUST BE THE FIRST MEMBER OF THE STRUCT. */ +  xListItem xGenericListItem;	/*< List item used to place the TCB in ready and blocked queues. */ +  xListItem xEventListItem;	/*< List item used to place the TCB in event lists. */ +  unsigned portBASE_TYPE uxPriority;	/*< The priority of the task where 0 is the lowest priority. */ +  portSTACK_TYPE *pxStack;	/*< Points to the start of the stack. */ +  unsigned portBASE_TYPE uxTCBNumber;	/*< This is used for tracing the scheduler and making debugging easier only. */ +  signed portCHAR pcTaskName[configMAX_TASK_NAME_LEN];	/*< Descriptive name given to the task when created.  Facilitates debugging only. */ +  unsigned portSHORT usStackDepth;	/*< Total depth of the stack (when empty).  This is defined as the number of variables the stack can hold, not the number of bytes. */ +} tskTCB; + +/*lint -e956 */ + +tskTCB *volatile pxCurrentTCB = NULL; + +/* Lists for ready and blocked tasks. --------------------*/ + +static xList pxReadyTasksLists[configMAX_PRIORITIES];	/*< Prioritised ready tasks. */ +static xList xDelayedTaskList1;	/*< Delayed tasks. */ +static xList xDelayedTaskList2;	/*< Delayed tasks (two lists are used - one for delays that have overflowed the current tick count. */ +static xList *volatile pxDelayedTaskList;	/*< Points to the delayed task list currently being used. */ +static xList *volatile pxOverflowDelayedTaskList;	/*< Points to the delayed task list currently being used to hold tasks that have overflowed the current tick count. */ +static xList xPendingReadyList;	/*< Tasks that have been readied while the scheduler was suspended.  They will be moved to the ready queue when the scheduler is resumed. */ + +#if ( INCLUDE_vTaskDelete == 1 ) + +static volatile xList xTasksWaitingTermination;	/*< Tasks that have been deleted - but the their memory not yet freed. */ +static volatile unsigned portBASE_TYPE uxTasksDeleted = +  (unsigned portBASE_TYPE) 0; + +#endif + +#if ( INCLUDE_vTaskSuspend == 1 ) + +static xList xSuspendedTaskList;	/*< Tasks that are currently suspended. */ + +#endif + +/* File private variables. --------------------------------*/ +static volatile unsigned portBASE_TYPE uxCurrentNumberOfTasks = +  (unsigned portBASE_TYPE) 0; +static volatile portTickType xTickCount = (portTickType) 0; +static unsigned portBASE_TYPE uxTopUsedPriority = tskIDLE_PRIORITY; +static volatile unsigned portBASE_TYPE uxTopReadyPriority = tskIDLE_PRIORITY; +static volatile signed portBASE_TYPE xSchedulerRunning = pdFALSE; +static volatile unsigned portBASE_TYPE uxSchedulerSuspended = +  (unsigned portBASE_TYPE) pdFALSE; +static volatile unsigned portBASE_TYPE uxMissedTicks = +  (unsigned portBASE_TYPE) 0; +static volatile portBASE_TYPE xMissedYield = (portBASE_TYPE) pdFALSE; +static volatile portBASE_TYPE xNumOfOverflows = (portBASE_TYPE) 0; +/* 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. + */ +#define tskSTACK_FILL_BYTE	( 0xa5 ) + +/* + * Macros used by vListTask to indicate which state a task is in. + */ +#define tskBLOCKED_CHAR		( ( signed portCHAR ) 'B' ) +#define tskREADY_CHAR		( ( signed portCHAR ) 'R' ) +#define tskDELETED_CHAR		( ( signed portCHAR ) 'D' ) +#define tskSUSPENDED_CHAR	( ( signed portCHAR ) 'S' ) + +/* + * Macros and private variables used by the trace facility. + */ +#if ( configUSE_TRACE_FACILITY == 1 ) + +#define tskSIZE_OF_EACH_TRACE_LINE			( ( unsigned portLONG ) ( sizeof( unsigned portLONG ) + sizeof( unsigned portLONG ) ) ) +static volatile signed portCHAR *volatile pcTraceBuffer; +static signed portCHAR *pcTraceBufferStart; +static signed portCHAR *pcTraceBufferEnd; +static signed portBASE_TYPE xTracing = pdFALSE; + +#endif + +/* + * Macro that writes a trace of scheduler activity to a buffer.  This trace + * shows which task is running when and is very useful as a debugging tool. + * As this macro is called each context switch it is a good idea to undefine + * it if not using the facility. + */ +#if ( configUSE_TRACE_FACILITY == 1 ) + +#define vWriteTraceToBuffer()																	\ +	{																								\ +		if( xTracing )																				\ +		{																							\ +			static unsigned portBASE_TYPE uxPreviousTask = 255;										\ +																									\ +			if( uxPreviousTask != pxCurrentTCB->uxTCBNumber )										\ +			{																						\ +				if( ( pcTraceBuffer + tskSIZE_OF_EACH_TRACE_LINE ) < pcTraceBufferEnd )				\ +				{																					\ +					uxPreviousTask = pxCurrentTCB->uxTCBNumber;										\ +					*( unsigned portLONG * ) pcTraceBuffer = ( unsigned portLONG ) xTickCount;		\ +					pcTraceBuffer += sizeof( unsigned portLONG );									\ +					*( unsigned portLONG * ) pcTraceBuffer = ( unsigned portLONG ) uxPreviousTask;	\ +					pcTraceBuffer += sizeof( unsigned portLONG );									\ +				}																					\ +				else																				\ +				{																					\ +					xTracing = pdFALSE;																\ +				}																					\ +			}																						\ +		}																							\ +	} + +#else + +#define vWriteTraceToBuffer() + +#endif + + +/* + * Place the task represented by pxTCB into the appropriate ready queue for + * the task.  It is inserted at the end of the list.  One quirk of this is + * that if the task being inserted is at the same priority as the currently + * executing task, then it will only be rescheduled after the currently + * executing task has been rescheduled. + */ +#define prvAddTaskToReadyQueue( pxTCB )																			\ +{																												\ +	if( pxTCB->uxPriority > uxTopReadyPriority )																\ +	{																											\ +		uxTopReadyPriority = pxTCB->uxPriority;																	\ +	}																											\ +	vListInsertEnd( ( xList * ) &( pxReadyTasksLists[ pxTCB->uxPriority ] ), &( pxTCB->xGenericListItem ) );	\ +} + +/* + * Macro that looks at the list of tasks that are currently delayed to see if + * any require waking. + * + * Tasks are stored in the queue in the order of their wake time - meaning + * once one tasks has been found whose timer has not expired we need not look + * any further down the list. + */ +#define prvCheckDelayedTasks()																						\ +{																													\ +register tskTCB *pxTCB;																								\ +																													\ +	while( ( pxTCB = ( tskTCB * ) listGET_OWNER_OF_HEAD_ENTRY( pxDelayedTaskList ) ) != NULL )						\ +	{																												\ +		if( xTickCount < listGET_LIST_ITEM_VALUE( &( pxTCB->xGenericListItem ) ) )									\ +		{																											\ +			break;																									\ +		}																											\ +		vListRemove( &( pxTCB->xGenericListItem ) );																\ +		/* Is the task waiting on an event also? */																	\ +		if( pxTCB->xEventListItem.pvContainer )																		\ +		{																											\ +			vListRemove( &( pxTCB->xEventListItem ) );																\ +		}																											\ +		prvAddTaskToReadyQueue( pxTCB );														\ +	}																												\ +} + +/* + * Several functions take an xTaskHandle parameter that can optionally be NULL, + * where NULL is used to indicate that the handle of the currently executing + * task should be used in place of the parameter.  This macro simply checks to + * see if the parameter is NULL and returns a pointer to the appropriate TCB. + */ +#define prvGetTCBFromHandle( pxHandle ) ( ( pxHandle == NULL ) ? ( tskTCB * ) pxCurrentTCB : ( tskTCB * ) pxHandle ) + + +/* File private functions. --------------------------------*/ + +/* + * Utility to ready a TCB for a given task.  Mainly just copies the parameters + * into the TCB structure. + */ +static void prvInitialiseTCBVariables (tskTCB * pxTCB, +				       unsigned portSHORT usStackDepth, +				       const signed portCHAR * const pcName, +				       unsigned portBASE_TYPE uxPriority); + +/* + * Utility to ready all the lists used by the scheduler.  This is called + * automatically upon the creation of the first task. + */ +static void prvInitialiseTaskLists (void); + +/* + * The idle task, which as all tasks is implemented as a never ending loop. + * The idle task is automatically created and added to the ready lists upon + * creation of the first user task. + * + * The portTASK_FUNCTION_PROTO() macro is used to allow port/compiler specific + * language extensions.  The equivalent prototype for this function is: + * + * void prvIdleTask( void *pvParameters ); + * + */ +static portTASK_FUNCTION_PROTO (prvIdleTask, pvParameters); + +/* + * Utility to free all memory allocated by the scheduler to hold a TCB, + * including the stack pointed to by the TCB. + * + * This does not free memory allocated by the task itself (i.e. memory + * allocated by calls to pvPortMalloc from within the tasks application code). + */ +#if ( ( INCLUDE_vTaskDelete == 1 ) || ( INCLUDE_vTaskCleanUpResources == 1 ) ) +static void prvDeleteTCB (tskTCB * pxTCB); +#endif + +/* + * Used only by the idle task.  This checks to see if anything has been placed + * in the list of tasks waiting to be deleted.  If so the task is cleaned up + * and its TCB deleted. + */ +static void prvCheckTasksWaitingTermination (void); + +/* + * Allocates memory from the heap for a TCB and associated stack.  Checks the + * allocation was successful. + */ +static tskTCB *prvAllocateTCBAndStack (unsigned portSHORT usStackDepth); + +/* + * Called from vTaskList.  vListTasks details all the tasks currently under + * control of the scheduler.  The tasks may be in one of a number of lists. + * prvListTaskWithinSingleList accepts a list and details the tasks from + * within just that list. + * + * THIS FUNCTION IS INTENDED FOR DEBUGGING ONLY, AND SHOULD NOT BE CALLED FROM + * NORMAL APPLICATION CODE. + */ +#if ( configUSE_TRACE_FACILITY == 1 ) + +static void prvListTaskWithinSingleList (signed portCHAR * pcWriteBuffer, +					 xList * pxList, +					 signed portCHAR cStatus); + +#endif + +/* + * When a task is created, the stack of the task is filled with a known value. + * This function determines the 'high water mark' of the task stack by + * determining how much of the stack remains at the original preset value. + */ +#if ( configUSE_TRACE_FACILITY == 1 ) + +unsigned portSHORT usTaskCheckFreeStackSpace (const unsigned portCHAR * +					      pucStackByte); + +#endif + +/*lint +e956 */ + + + + + +/*----------------------------------------------------------- + * TASK CREATION API documented in task.h + *----------------------------------------------------------*/ + +signed portBASE_TYPE +xTaskCreate (pdTASK_CODE pvTaskCode, const signed portCHAR * const pcName, +	     unsigned portSHORT usStackDepth, void *pvParameters, +	     unsigned portBASE_TYPE uxPriority, xTaskHandle * pxCreatedTask) +{ +  signed portBASE_TYPE xReturn; +  tskTCB *pxNewTCB; +  static unsigned portBASE_TYPE uxTaskNumber = 0;	/*lint !e956 Static is deliberate - this is guarded before use. */ + +  /* Allocate the memory required by the TCB and stack for the new task. +     checking that the allocation was successful. */ +  pxNewTCB = prvAllocateTCBAndStack (usStackDepth); + +  if (pxNewTCB != NULL) +    { +      portSTACK_TYPE *pxTopOfStack; + +      /* Setup the newly allocated TCB with the initial state of the task. */ +      prvInitialiseTCBVariables (pxNewTCB, usStackDepth, pcName, uxPriority); + +      /* Calculate the top of stack address.  This depends on whether the +         stack grows from high memory to low (as per the 80x86) or visa versa. +         portSTACK_GROWTH is used to make the result positive or negative as +         required by the port. */ +#if portSTACK_GROWTH < 0 +      { +	pxTopOfStack = pxNewTCB->pxStack + (pxNewTCB->usStackDepth - 1); +      } +#else +      { +	pxTopOfStack = pxNewTCB->pxStack; +      } +#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. */ +      pxNewTCB->pxTopOfStack = +	pxPortInitialiseStack (pxTopOfStack, pvTaskCode, pvParameters); + +      /* We are going to manipulate the task queues to add this task to a +         ready list, so must make sure no interrupts occur. */ +      portENTER_CRITICAL (); +      { +	uxCurrentNumberOfTasks++; +	if (uxCurrentNumberOfTasks == (unsigned portBASE_TYPE) 1) +	  { +	    /* As this is the first task it must also be the current task. */ +	    pxCurrentTCB = pxNewTCB; + +	    /* 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 +	  { +	    /* 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; +		  } +	      } +	  } + +	/* Remember the top priority to make context switching faster.  Use +	   the priority in pxNewTCB as this has been capped to a valid value. */ +	if (pxNewTCB->uxPriority > uxTopUsedPriority) +	  { +	    uxTopUsedPriority = pxNewTCB->uxPriority; +	  } + +	/* Add a counter into the TCB for tracing only. */ +	pxNewTCB->uxTCBNumber = uxTaskNumber; +	uxTaskNumber++; + +	prvAddTaskToReadyQueue (pxNewTCB); + +	xReturn = pdPASS; +      } +      portEXIT_CRITICAL (); +    } +  else +    { +      xReturn = errCOULD_NOT_ALLOCATE_REQUIRED_MEMORY; +    } + +  if (xReturn == pdPASS) +    { +      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 = (xTaskHandle) pxNewTCB; +	} + +      if (xSchedulerRunning != pdFALSE) +	{ +	  /* If the created task is of a higher priority than the current task +	     then it should run now. */ +	  if (pxCurrentTCB->uxPriority < uxPriority) +	    { +	      taskYIELD (); +	    } +	} +    } + +  return xReturn; +} + +/*-----------------------------------------------------------*/ + +#if ( INCLUDE_vTaskDelete == 1 ) + +void +vTaskDelete (xTaskHandle pxTaskToDelete) +{ +  tskTCB *pxTCB; + +  taskENTER_CRITICAL (); +  { +    /* Ensure a yield is performed if the current task is being  +       deleted. */ +    if (pxTaskToDelete == pxCurrentTCB) +      { +	pxTaskToDelete = NULL; +      } + +    /* If null is passed in here then we are deleting ourselves. */ +    pxTCB = prvGetTCBFromHandle (pxTaskToDelete); + +    /* Remove task from the ready list and place in the     termination list. +       This will stop the task from be scheduled.  The idle task will check +       the termination list and free up any memory allocated by the +       scheduler for the TCB and stack. */ +    vListRemove (&(pxTCB->xGenericListItem)); + +    /* Is the task waiting on an event also? */ +    if (pxTCB->xEventListItem.pvContainer) +      { +	vListRemove (&(pxTCB->xEventListItem)); +      } + +    vListInsertEnd ((xList *) & xTasksWaitingTermination, +		    &(pxTCB->xGenericListItem)); + +    /* Increment the ucTasksDeleted variable so the idle task knows +       there is a task that has been deleted and that it should therefore +       check the xTasksWaitingTermination list. */ +    ++uxTasksDeleted; +  } +  taskEXIT_CRITICAL (); + +  /* Force a reschedule if we have just deleted the current task. */ +  if (xSchedulerRunning != pdFALSE) +    { +      if ((void *) pxTaskToDelete == NULL) +	{ +	  taskYIELD (); +	} +    } +} + +#endif + + + + + + +/*----------------------------------------------------------- + * TASK CONTROL API documented in task.h + *----------------------------------------------------------*/ + +#if ( INCLUDE_vTaskDelayUntil == 1 ) + +void +vTaskDelayUntil (portTickType * pxPreviousWakeTime, +		 portTickType xTimeIncrement) +{ +  portTickType xTimeToWake; +  portBASE_TYPE xAlreadyYielded, xShouldDelay = pdFALSE; + +  vTaskSuspendAll (); +  { +    /* Generate the tick time at which the task wants to wake. */ +    xTimeToWake = *pxPreviousWakeTime + xTimeIncrement; + +    if (xTickCount < *pxPreviousWakeTime) +      { +	/* The tick count has overflowed since this function was +	   lasted called.  In this case the only time we should ever +	   actually delay is if the wake time has also  overflowed, +	   and the wake time is greater than the tick time.  When this +	   is the case it is as if neither time had overflowed. */ +	if ((xTimeToWake < *pxPreviousWakeTime) && (xTimeToWake > xTickCount)) +	  { +	    xShouldDelay = pdTRUE; +	  } +      } +    else +      { +	/* The tick time has not overflowed.  In this case we will +	   delay if either the wake time has overflowed, and/or the +	   tick time is less than the wake time. */ +	if ((xTimeToWake < *pxPreviousWakeTime) || (xTimeToWake > xTickCount)) +	  { +	    xShouldDelay = pdTRUE; +	  } +      } + +    /* Update the wake time ready for the next call. */ +    *pxPreviousWakeTime = xTimeToWake; + +    if (xShouldDelay) +      { +	/* We must remove ourselves from the ready list before adding +	   ourselves to the blocked list as the same list item is used for +	   both lists. */ +	vListRemove ((xListItem *) & (pxCurrentTCB->xGenericListItem)); + +	/* The list item will be inserted in wake time order. */ +	listSET_LIST_ITEM_VALUE (&(pxCurrentTCB->xGenericListItem), +				 xTimeToWake); + +	if (xTimeToWake < xTickCount) +	  { +	    /* Wake time has overflowed.  Place this item in the +	       overflow list. */ +	    vListInsert ((xList *) pxOverflowDelayedTaskList, +			 (xListItem *) & (pxCurrentTCB->xGenericListItem)); +	  } +	else +	  { +	    /* The wake time has not overflowed, so we can use the +	       current block list. */ +	    vListInsert ((xList *) pxDelayedTaskList, +			 (xListItem *) & (pxCurrentTCB->xGenericListItem)); +	  } +      } +  } +  xAlreadyYielded = xTaskResumeAll (); + +  /* Force a reschedule if xTaskResumeAll has not already done so, we may +     have put ourselves to sleep. */ +  if (!xAlreadyYielded) +    { +      taskYIELD (); +    } +} + +#endif +/*-----------------------------------------------------------*/ + +#if ( INCLUDE_vTaskDelay == 1 ) + +void +vTaskDelay (portTickType xTicksToDelay) +{ +  portTickType xTimeToWake; +  signed portBASE_TYPE xAlreadyYielded = pdFALSE; + +  /* A delay time of zero just forces a reschedule. */ +  if (xTicksToDelay > (portTickType) 0) +    { +      vTaskSuspendAll (); +      { +	/* A task that is removed from the event list while the +	   scheduler is suspended will not get placed in the ready +	   list or removed from the blocked list until the scheduler +	   is resumed. + +	   This task cannot be in an event list as it is the currently +	   executing task. */ + +	/* Calculate the time to wake - this may overflow but this is +	   not a problem. */ +	xTimeToWake = xTickCount + xTicksToDelay; + +	/* We must remove ourselves from the ready list before adding +	   ourselves to the blocked list as the same list item is used for +	   both lists. */ +	vListRemove ((xListItem *) & (pxCurrentTCB->xGenericListItem)); + +	/* The list item will be inserted in wake time order. */ +	listSET_LIST_ITEM_VALUE (&(pxCurrentTCB->xGenericListItem), +				 xTimeToWake); + +	if (xTimeToWake < xTickCount) +	  { +	    /* Wake time has overflowed.  Place this item in the +	       overflow list. */ +	    vListInsert ((xList *) pxOverflowDelayedTaskList, +			 (xListItem *) & (pxCurrentTCB->xGenericListItem)); +	  } +	else +	  { +	    /* The wake time has not overflowed, so we can use the +	       current block list. */ +	    vListInsert ((xList *) pxDelayedTaskList, +			 (xListItem *) & (pxCurrentTCB->xGenericListItem)); +	  } +      } +      xAlreadyYielded = xTaskResumeAll (); +    } + +  /* Force a reschedule if xTaskResumeAll has not already done so, we may +     have put ourselves to sleep. */ +  if (!xAlreadyYielded) +    { +      taskYIELD (); +    } +} + +#endif +/*-----------------------------------------------------------*/ + +#if ( INCLUDE_uxTaskPriorityGet == 1 ) + +unsigned portBASE_TYPE +uxTaskPriorityGet (xTaskHandle pxTask) +{ +  tskTCB *pxTCB; +  unsigned portBASE_TYPE uxReturn; + +  taskENTER_CRITICAL (); +  { +    /* If null is passed in here then we are changing the +       priority of the calling function. */ +    pxTCB = prvGetTCBFromHandle (pxTask); +    uxReturn = pxTCB->uxPriority; +  } +  taskEXIT_CRITICAL (); + +  return uxReturn; +} + +#endif +/*-----------------------------------------------------------*/ + +#if ( INCLUDE_vTaskPrioritySet == 1 ) + +void +vTaskPrioritySet (xTaskHandle pxTask, unsigned portBASE_TYPE uxNewPriority) +{ +  tskTCB *pxTCB; +  unsigned portBASE_TYPE uxCurrentPriority, xYieldRequired = pdFALSE; + +  /* Ensure the new priority is valid. */ +  if (uxNewPriority >= configMAX_PRIORITIES) +    { +      uxNewPriority = configMAX_PRIORITIES - 1; +    } + +  taskENTER_CRITICAL (); +  { +    /* If null is passed in here then we are changing the +       priority of the calling function. */ +    pxTCB = prvGetTCBFromHandle (pxTask); +    uxCurrentPriority = pxTCB->uxPriority; + +    if (uxCurrentPriority != uxNewPriority) +      { +	/* The priority change may have readied a task of higher +	   priority than the calling task. */ +	if (uxNewPriority > pxCurrentTCB->uxPriority) +	  { +	    if (pxTask != NULL) +	      { +		/* The priority of another task is being raised.  If we +		   were raising the priority of the currently running task +		   there would be no need to switch as it must have already +		   been the highest priority task. */ +		xYieldRequired = pdTRUE; +	      } +	  } +	else if (pxTask == NULL) +	  { +	    /* Setting our own priority down means there may now be another +	       task of higher priority that is ready to execute. */ +	    xYieldRequired = pdTRUE; +	  } + +	pxTCB->uxPriority = uxNewPriority; +	listSET_LIST_ITEM_VALUE (&(pxTCB->xEventListItem), +				 configMAX_PRIORITIES - +				 (portTickType) uxNewPriority); + +	/* If the task is in the blocked or suspended list we need do +	   nothing more than change it's priority variable. However, if +	   the task is in a ready list it needs to be removed and placed +	   in the queue appropriate to its new priority. */ +	if (listIS_CONTAINED_WITHIN +	    (&(pxReadyTasksLists[uxCurrentPriority]), +	     &(pxTCB->xGenericListItem))) +	  { +	    /* The task is currently in its ready list - remove before adding +	       it to it's new ready list.  As we are in a critical section we +	       can do this even if the scheduler is suspended. */ +	    vListRemove (&(pxTCB->xGenericListItem)); +	    prvAddTaskToReadyQueue (pxTCB); +	  } + +	if (xYieldRequired == pdTRUE) +	  { +	    taskYIELD (); +	  } +      } +  } +  taskEXIT_CRITICAL (); +} + +#endif +/*-----------------------------------------------------------*/ + +#if ( INCLUDE_vTaskSuspend == 1 ) + +void +vTaskSuspend (xTaskHandle pxTaskToSuspend) +{ +  tskTCB *pxTCB; + +  taskENTER_CRITICAL (); +  { +    /* Ensure a yield is performed if the current task is being  +       suspended. */ +    if (pxTaskToSuspend == pxCurrentTCB) +      { +	pxTaskToSuspend = NULL; +      } + +    /* If null is passed in here then we are suspending ourselves. */ +    pxTCB = prvGetTCBFromHandle (pxTaskToSuspend); + +    /* Remove task from the ready/delayed list and place in the     suspended list. */ +    vListRemove (&(pxTCB->xGenericListItem)); + +    /* Is the task waiting on an event also? */ +    if (pxTCB->xEventListItem.pvContainer) +      { +	vListRemove (&(pxTCB->xEventListItem)); +      } + +    vListInsertEnd ((xList *) & xSuspendedTaskList, +		    &(pxTCB->xGenericListItem)); +  } +  taskEXIT_CRITICAL (); + +  /* We may have just suspended the current task. */ +  if ((void *) pxTaskToSuspend == NULL) +    { +      taskYIELD (); +    } +} + +#endif +/*-----------------------------------------------------------*/ + +#if ( INCLUDE_vTaskSuspend == 1 ) + +void +vTaskResume (xTaskHandle pxTaskToResume) +{ +  tskTCB *pxTCB; + +  /* Remove the task from whichever list it is currently in, and place +     it in the ready list. */ +  pxTCB = (tskTCB *) pxTaskToResume; + +  /* The parameter cannot be NULL as it is impossible to resume the +     currently executing task. */ +  if (pxTCB != NULL) +    { +      taskENTER_CRITICAL (); +      { +	/* Is the task we are attempting to resume actually suspended? */ +	if (listIS_CONTAINED_WITHIN +	    (&xSuspendedTaskList, &(pxTCB->xGenericListItem)) != pdFALSE) +	  { +	    /* Has the task already been resumed from within an ISR? */ +	    if (listIS_CONTAINED_WITHIN +		(&xPendingReadyList, &(pxTCB->xEventListItem)) != pdTRUE) +	      { +		/* As we are in a critical section we can access the ready  +		   lists even if the scheduler is suspended. */ +		vListRemove (&(pxTCB->xGenericListItem)); +		prvAddTaskToReadyQueue (pxTCB); + +		/* We may have just resumed a higher priority task. */ +		if (pxTCB->uxPriority >= pxCurrentTCB->uxPriority) +		  { +		    /* This yield may not cause the task just resumed to run, but +		       will leave the lists in the correct state for the next yield. */ +		    taskYIELD (); +		  } +	      } +	  } +      } +      taskEXIT_CRITICAL (); +    } +} + +#endif + +/*-----------------------------------------------------------*/ + +#if ( ( INCLUDE_xTaskResumeFromISR == 1 ) && ( INCLUDE_vTaskSuspend == 1 ) ) + +portBASE_TYPE +xTaskResumeFromISR (xTaskHandle pxTaskToResume) +{ +  portBASE_TYPE xYieldRequired = pdFALSE; +  tskTCB *pxTCB; + +  pxTCB = (tskTCB *) pxTaskToResume; + +  /* Is the task we are attempting to resume actually suspended? */ +  if (listIS_CONTAINED_WITHIN +      (&xSuspendedTaskList, &(pxTCB->xGenericListItem)) != pdFALSE) +    { +      /* Has the task already been resumed from within an ISR? */ +      if (listIS_CONTAINED_WITHIN +	  (&xPendingReadyList, &(pxTCB->xEventListItem)) != pdTRUE) +	{ +	  if (uxSchedulerSuspended == (unsigned portBASE_TYPE) pdFALSE) +	    { +	      xYieldRequired = +		(pxTCB->uxPriority >= pxCurrentTCB->uxPriority); +	      vListRemove (&(pxTCB->xGenericListItem)); +	      prvAddTaskToReadyQueue (pxTCB); +	    } +	  else +	    { +	      /* We cannot access the delayed or ready lists, so will hold this +	         task pending until the scheduler is resumed, at which point a  +	         yield will be preformed if necessary. */ +	      vListInsertEnd ((xList *) & (xPendingReadyList), +			      &(pxTCB->xEventListItem)); +	    } +	} +    } + +  return xYieldRequired; +} + +#endif + + + + +/*----------------------------------------------------------- + * PUBLIC SCHEDULER CONTROL documented in task.h + *----------------------------------------------------------*/ + + +void +vTaskStartScheduler (void) +{ +  portBASE_TYPE xReturn; + +  /* Add the idle task at the lowest priority. */ +  xReturn = +    xTaskCreate (prvIdleTask, (signed portCHAR *) "IDLE", tskIDLE_STACK_SIZE, +		 (void *) NULL, tskIDLE_PRIORITY, (xTaskHandle *) NULL); + +  if (xReturn == pdPASS) +    { +      /* Interrupts are turned off here, to ensure a tick does not occur +         before or during the call to xPortStartScheduler().  The stacks of +         the created tasks contain a status word with interrupts switched on +         so interrupts will automatically get re-enabled when the first task +         starts to run. + +         STEPPING THROUGH HERE USING A DEBUGGER CAN CAUSE BIG PROBLEMS IF THE +         DEBUGGER ALLOWS INTERRUPTS TO BE PROCESSED. */ +      portDISABLE_INTERRUPTS (); + +      xSchedulerRunning = pdTRUE; +      xTickCount = (portTickType) 0; + +      /* Setting up the timer tick is hardware specific and thus in the +         portable interface. */ +      if (xPortStartScheduler ()) +	{ +	  /* Should not reach here as if the scheduler is running the +	     function will not return. */ +	} +      else +	{ +	  /* Should only reach here if a task calls xTaskEndScheduler(). */ +	} +    } +} + +/*-----------------------------------------------------------*/ + +void +vTaskEndScheduler (void) +{ +  /* Stop the scheduler interrupts and call the portable scheduler end +     routine so the original ISRs can be restored if necessary.  The port +     layer must ensure interrupts enable  bit is left in the correct state. */ +  portDISABLE_INTERRUPTS (); +  xSchedulerRunning = pdFALSE; +  vPortEndScheduler (); +} + +/*----------------------------------------------------------*/ + +void +vTaskSuspendAll (void) +{ +  portENTER_CRITICAL (); +  ++uxSchedulerSuspended; +  portEXIT_CRITICAL (); +} + +/*----------------------------------------------------------*/ + +signed portBASE_TYPE +xTaskResumeAll (void) +{ +  register tskTCB *pxTCB; +  signed portBASE_TYPE xAlreadyYielded = pdFALSE; + +  /* It is possible that an ISR caused a task to be removed from an event +     list while the scheduler was suspended.  If this was the case then the +     removed task will have been added to the xPendingReadyList.  Once the +     scheduler has been resumed it is safe to move all the pending ready +     tasks from this list into their appropriate ready list. */ +  portENTER_CRITICAL (); +  { +    --uxSchedulerSuspended; + +    if (uxSchedulerSuspended == (unsigned portBASE_TYPE) pdFALSE) +      { +	if (uxCurrentNumberOfTasks > (unsigned portBASE_TYPE) 0) +	  { +	    portBASE_TYPE xYieldRequired = pdFALSE; + +	    /* Move any readied tasks from the pending list into the +	       appropriate ready list. */ +	    while ((pxTCB = +		    (tskTCB *) +		    listGET_OWNER_OF_HEAD_ENTRY (((xList *) & +						  xPendingReadyList))) != +		   NULL) +	      { +		vListRemove (&(pxTCB->xEventListItem)); +		vListRemove (&(pxTCB->xGenericListItem)); +		prvAddTaskToReadyQueue (pxTCB); + +		/* If we have moved a task that has a priority higher than +		   the current task then we should yield. */ +		if (pxTCB->uxPriority >= pxCurrentTCB->uxPriority) +		  { +		    xYieldRequired = pdTRUE; +		  } +	      } + +	    /* If any ticks occurred while the scheduler was suspended then +	       they should be processed now.  This ensures the tick count does not +	       slip, and that any delayed tasks are resumed at the correct time. */ +	    if (uxMissedTicks > (unsigned portBASE_TYPE) 0) +	      { +		while (uxMissedTicks > (unsigned portBASE_TYPE) 0) +		  { +		    vTaskIncrementTick (); +		    --uxMissedTicks; +		  } + +		/* As we have processed some ticks it is appropriate to yield +		   to ensure the highest priority task that is ready to run is +		   the task actually running. */ +		xYieldRequired = pdTRUE; +	      } + +	    if ((xYieldRequired == pdTRUE) || (xMissedYield == pdTRUE)) +	      { +		xAlreadyYielded = pdTRUE; +		xMissedYield = pdFALSE; +		taskYIELD (); +	      } +	  } +      } +  } +  portEXIT_CRITICAL (); + +  return xAlreadyYielded; +} + + + + + + +/*----------------------------------------------------------- + * PUBLIC TASK UTILITIES documented in task.h + *----------------------------------------------------------*/ + + + +portTickType +xTaskGetTickCount (void) +{ +  portTickType xTicks; + +  /* Critical section required if running on a 16 bit processor. */ +  taskENTER_CRITICAL (); +  { +    xTicks = xTickCount; +  } +  taskEXIT_CRITICAL (); + +  return xTicks; +} + +/*-----------------------------------------------------------*/ + +unsigned portBASE_TYPE +uxTaskGetNumberOfTasks (void) +{ +  unsigned portBASE_TYPE uxNumberOfTasks; + +  taskENTER_CRITICAL (); +  uxNumberOfTasks = uxCurrentNumberOfTasks; +  taskEXIT_CRITICAL (); + +  return uxNumberOfTasks; +} + +/*-----------------------------------------------------------*/ + +#if ( ( configUSE_TRACE_FACILITY == 1 ) && ( INCLUDE_vTaskDelete == 1 ) && ( INCLUDE_vTaskSuspend == 1 ) ) + +void +vTaskList (signed portCHAR * pcWriteBuffer) +{ +  unsigned portBASE_TYPE uxQueue; + +  /* This is a VERY costly function that should be used for debug only. +     It leaves interrupts disabled for a LONG time. */ + +  vTaskSuspendAll (); +  { +    /* Run through all the lists that could potentially contain a TCB and +       report the task name, state and stack high water mark. */ + +    pcWriteBuffer[0] = (signed portCHAR) 0x00; +    strcat ((portCHAR *) pcWriteBuffer, (const portCHAR *) "\r\n"); + +    uxQueue = uxTopUsedPriority + 1; + +    do +      { +	uxQueue--; + +	if (!listLIST_IS_EMPTY (&(pxReadyTasksLists[uxQueue]))) +	  { +	    prvListTaskWithinSingleList (pcWriteBuffer, +					 (xList *) & +					 (pxReadyTasksLists[uxQueue]), +					 tskREADY_CHAR); +	  } +      } +    while (uxQueue > (unsigned portSHORT) tskIDLE_PRIORITY); + +    if (!listLIST_IS_EMPTY (pxDelayedTaskList)) +      { +	prvListTaskWithinSingleList (pcWriteBuffer, +				     (xList *) pxDelayedTaskList, +				     tskBLOCKED_CHAR); +      } + +    if (!listLIST_IS_EMPTY (pxOverflowDelayedTaskList)) +      { +	prvListTaskWithinSingleList (pcWriteBuffer, +				     (xList *) pxOverflowDelayedTaskList, +				     tskBLOCKED_CHAR); +      } + +    if (!listLIST_IS_EMPTY (&xTasksWaitingTermination)) +      { +	prvListTaskWithinSingleList (pcWriteBuffer, +				     (xList *) & xTasksWaitingTermination, +				     tskDELETED_CHAR); +      } + +    if (!listLIST_IS_EMPTY (&xSuspendedTaskList)) +      { +	prvListTaskWithinSingleList (pcWriteBuffer, +				     (xList *) & xSuspendedTaskList, +				     tskSUSPENDED_CHAR); +      } +  } +  xTaskResumeAll (); +} + +#endif +/*----------------------------------------------------------*/ + +#if ( configUSE_TRACE_FACILITY == 1 ) + +void +vTaskStartTrace (signed portCHAR * pcBuffer, unsigned portLONG ulBufferSize) +{ +  portENTER_CRITICAL (); +  { +    pcTraceBuffer = (volatile signed portCHAR * volatile) pcBuffer; +    pcTraceBufferStart = pcBuffer; +    pcTraceBufferEnd = pcBuffer + (ulBufferSize - tskSIZE_OF_EACH_TRACE_LINE); +    xTracing = pdTRUE; +  } +  portEXIT_CRITICAL (); +} + +#endif +/*----------------------------------------------------------*/ + +#if ( configUSE_TRACE_FACILITY == 1 ) + +unsigned portLONG +ulTaskEndTrace (void) +{ +  unsigned portLONG ulBufferLength; + +  portENTER_CRITICAL (); +  xTracing = pdFALSE; +  portEXIT_CRITICAL (); + +  ulBufferLength = (unsigned portLONG) (pcTraceBuffer - pcTraceBufferStart); + +  return ulBufferLength; +} + +#endif + + + +/*----------------------------------------------------------- + * SCHEDULER INTERNALS AVAILABLE FOR PORTING PURPOSES + * documented in task.h + *----------------------------------------------------------*/ + + +inline void +vTaskIncrementTick (void) +{ +  /* Called by the portable layer each time a tick interrupt occurs. +     Increments the tick then checks to see if the new tick value will cause any +     tasks to be unblocked. */ +  if (uxSchedulerSuspended == (unsigned portBASE_TYPE) pdFALSE) +    { +      ++xTickCount; +      if (xTickCount == (portTickType) 0) +	{ +	  xList *pxTemp; + +	  /* Tick count has overflowed so we need to swap the delay lists.   +	     If there are any items in pxDelayedTaskList here then there is  +	     an error! */ +	  pxTemp = pxDelayedTaskList; +	  pxDelayedTaskList = pxOverflowDelayedTaskList; +	  pxOverflowDelayedTaskList = pxTemp; +	  xNumOfOverflows++; +	} + +      /* See if this tick has made a timeout expire. */ +      prvCheckDelayedTasks (); +    } +  else +    { +      ++uxMissedTicks; + +      /* The tick hook gets called at regular intervals, even if the  +         scheduler is locked. */ +#if ( configUSE_TICK_HOOK == 1 ) +      { +	extern void vApplicationTickHook (void); + +	vApplicationTickHook (); +      } +#endif +    } + +#if ( configUSE_TICK_HOOK == 1 ) +  { +    extern void vApplicationTickHook (void); + +    /* Guard against the tick hook being called when the missed tick +       count is being unwound (when the scheduler is being unlocked. */ +    if (uxMissedTicks == 0) +      { +	vApplicationTickHook (); +      } +  } +#endif +} + +/*-----------------------------------------------------------*/ + +#if ( ( INCLUDE_vTaskCleanUpResources == 1 ) && ( INCLUDE_vTaskSuspend == 1 ) ) + +void +vTaskCleanUpResources (void) +{ +  unsigned portSHORT usQueue; +  volatile tskTCB *pxTCB; + +  usQueue = (unsigned portSHORT) uxTopUsedPriority + (unsigned portSHORT) 1; + +  /* Remove any TCB's from the ready queues. */ +  do +    { +      usQueue--; + +      while (!listLIST_IS_EMPTY (&(pxReadyTasksLists[usQueue]))) +	{ +	  listGET_OWNER_OF_NEXT_ENTRY (pxTCB, &(pxReadyTasksLists[usQueue])); +	  vListRemove ((xListItem *) & (pxTCB->xGenericListItem)); + +	  prvDeleteTCB ((tskTCB *) pxTCB); +	} +    } +  while (usQueue > (unsigned portSHORT) tskIDLE_PRIORITY); + +  /* Remove any TCB's from the delayed queue. */ +  while (!listLIST_IS_EMPTY (&xDelayedTaskList1)) +    { +      listGET_OWNER_OF_NEXT_ENTRY (pxTCB, &xDelayedTaskList1); +      vListRemove ((xListItem *) & (pxTCB->xGenericListItem)); + +      prvDeleteTCB ((tskTCB *) pxTCB); +    } + +  /* Remove any TCB's from the overflow delayed queue. */ +  while (!listLIST_IS_EMPTY (&xDelayedTaskList2)) +    { +      listGET_OWNER_OF_NEXT_ENTRY (pxTCB, &xDelayedTaskList2); +      vListRemove ((xListItem *) & (pxTCB->xGenericListItem)); + +      prvDeleteTCB ((tskTCB *) pxTCB); +    } + +  while (!listLIST_IS_EMPTY (&xSuspendedTaskList)) +    { +      listGET_OWNER_OF_NEXT_ENTRY (pxTCB, &xSuspendedTaskList); +      vListRemove ((xListItem *) & (pxTCB->xGenericListItem)); + +      prvDeleteTCB ((tskTCB *) pxTCB); +    } + +  while (!listLIST_IS_EMPTY (&xPendingReadyList)) +    { +      listGET_OWNER_OF_NEXT_ENTRY (pxTCB, &xPendingReadyList); +      vListRemove ((xListItem *) & (pxTCB->xGenericListItem)); + +      prvDeleteTCB ((tskTCB *) pxTCB); +    } +} + +#endif +/*-----------------------------------------------------------*/ + +void +vTaskSwitchContext (void) +{ +  if (uxSchedulerSuspended != (unsigned portBASE_TYPE) pdFALSE) +    { +      /* The scheduler is currently suspended - do not allow a context +         switch. */ +      xMissedYield = pdTRUE; +      return; +    } + +  /* Find the highest priority queue that contains ready tasks. */ +  while (listLIST_IS_EMPTY (&(pxReadyTasksLists[uxTopReadyPriority]))) +    { +      --uxTopReadyPriority; +    } + +  /* listGET_OWNER_OF_NEXT_ENTRY walks through the list, so the tasks of the +     same priority get an equal share of the processor time. */ +  listGET_OWNER_OF_NEXT_ENTRY (pxCurrentTCB, +			       &(pxReadyTasksLists[uxTopReadyPriority])); +  vWriteTraceToBuffer (); +} + +/*-----------------------------------------------------------*/ + +void +vTaskPlaceOnEventList (xList * pxEventList, portTickType xTicksToWait) +{ +  portTickType xTimeToWake; + +  /* THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED OR THE +     SCHEDULER SUSPENDED. */ + +  /* Place the event list item of the TCB in the appropriate event list. +     This is placed in the list in priority order so the highest priority task +     is the first to be woken by the event. */ +  vListInsert ((xList *) pxEventList, +	       (xListItem *) & (pxCurrentTCB->xEventListItem)); + +  /* We must remove ourselves from the ready list before adding ourselves +     to the blocked list as the same list item is used for both lists.  We have +     exclusive access to the ready lists as the scheduler is locked. */ +  vListRemove ((xListItem *) & (pxCurrentTCB->xGenericListItem)); + + +#if ( INCLUDE_vTaskSuspend == 1 ) +  { +    if (xTicksToWait == portMAX_DELAY) +      { +	/* Add ourselves to the suspended task list instead of a delayed task +	   list to ensure we are not woken by a timing event.  We will block +	   indefinitely. */ +	vListInsertEnd ((xList *) & xSuspendedTaskList, +			(xListItem *) & (pxCurrentTCB->xGenericListItem)); +      } +    else +      { +	/* Calculate the time at which the task should be woken if the event does +	   not occur.  This may overflow but this doesn't matter. */ +	xTimeToWake = xTickCount + xTicksToWait; + +	listSET_LIST_ITEM_VALUE (&(pxCurrentTCB->xGenericListItem), +				 xTimeToWake); + +	if (xTimeToWake < xTickCount) +	  { +	    /* Wake time has overflowed.  Place this item in the overflow list. */ +	    vListInsert ((xList *) pxOverflowDelayedTaskList, +			 (xListItem *) & (pxCurrentTCB->xGenericListItem)); +	  } +	else +	  { +	    /* The wake time has not overflowed, so we can use the current block list. */ +	    vListInsert ((xList *) pxDelayedTaskList, +			 (xListItem *) & (pxCurrentTCB->xGenericListItem)); +	  } +      } +  } +#else +  { +    /* Calculate the time at which the task should be woken if the event does +       not occur.  This may overflow but this doesn't matter. */ +    xTimeToWake = xTickCount + xTicksToWait; + +    listSET_LIST_ITEM_VALUE (&(pxCurrentTCB->xGenericListItem), xTimeToWake); + +    if (xTimeToWake < xTickCount) +      { +	/* Wake time has overflowed.  Place this item in the overflow list. */ +	vListInsert ((xList *) pxOverflowDelayedTaskList, +		     (xListItem *) & (pxCurrentTCB->xGenericListItem)); +      } +    else +      { +	/* The wake time has not overflowed, so we can use the current block list. */ +	vListInsert ((xList *) pxDelayedTaskList, +		     (xListItem *) & (pxCurrentTCB->xGenericListItem)); +      } +  } +#endif +} + +/*-----------------------------------------------------------*/ + +signed portBASE_TYPE +xTaskRemoveFromEventList (const xList * pxEventList) +{ +  tskTCB *pxUnblockedTCB; +  portBASE_TYPE xReturn; + +  /* THIS FUNCTION MUST BE CALLED WITH INTERRUPTS DISABLED OR THE +     SCHEDULER SUSPENDED.  It can also be called from within an ISR. */ + +  /* The event list is sorted in priority order, so we can remove the +     first in the list, remove the TCB from the delayed list, and add +     it to the ready list. + +     If an event is for a queue that is locked then this function will never +     get called - the lock count on the queue will get modified instead.  This +     means we can always expect exclusive access to the event list here. */ +  pxUnblockedTCB = (tskTCB *) listGET_OWNER_OF_HEAD_ENTRY (pxEventList); +  vListRemove (&(pxUnblockedTCB->xEventListItem)); + +  if (uxSchedulerSuspended == (unsigned portBASE_TYPE) pdFALSE) +    { +      vListRemove (&(pxUnblockedTCB->xGenericListItem)); +      prvAddTaskToReadyQueue (pxUnblockedTCB); +    } +  else +    { +      /* We cannot access the delayed or ready lists, so will hold this +         task pending until the scheduler is resumed. */ +      vListInsertEnd ((xList *) & (xPendingReadyList), +		      &(pxUnblockedTCB->xEventListItem)); +    } + +  if (pxUnblockedTCB->uxPriority >= pxCurrentTCB->uxPriority) +    { +      /* Return true if the task removed from the event list has +         a higher priority than the calling task.  This allows +         the calling task to know if it should force a context +         switch now. */ +      xReturn = pdTRUE; +    } +  else +    { +      xReturn = pdFALSE; +    } + +  return xReturn; +} + +/*-----------------------------------------------------------*/ + +void +vTaskSetTimeOutState (xTimeOutType * pxTimeOut) +{ +  pxTimeOut->xOverflowCount = xNumOfOverflows; +  pxTimeOut->xTimeOnEntering = xTickCount; +} + +/*-----------------------------------------------------------*/ + +portBASE_TYPE +xTaskCheckForTimeOut (xTimeOutType * pxTimeOut, portTickType * pxTicksToWait) +{ +  portBASE_TYPE xReturn; + +  if ((xNumOfOverflows != pxTimeOut->xOverflowCount) +      && (xTickCount >= pxTimeOut->xTimeOnEntering)) +    { +      /* The tick count is greater than the time at which vTaskSetTimeout()  +         was called, but has also overflowed since vTaskSetTimeOut() was called. +         It must have wrapped all the way around and gone past us again. This +         passed since vTaskSetTimeout() was called. */ +      xReturn = pdTRUE; +    } +  else if ((xTickCount - pxTimeOut->xTimeOnEntering) < *pxTicksToWait) +    { +      /* Not a genuine timeout. Adjust parameters for time remaining. */ +      *pxTicksToWait -= (xTickCount - pxTimeOut->xTimeOnEntering); +      vTaskSetTimeOutState (pxTimeOut); +      xReturn = pdFALSE; +    } +  else +    { +      xReturn = pdTRUE; +    } + +  return xReturn; +} + +/*-----------------------------------------------------------*/ + +void +vTaskMissedYield (void) +{ +  xMissedYield = pdTRUE; +} + +/* + * ----------------------------------------------------------- + * The Idle task. + * ---------------------------------------------------------- + * + * The portTASK_FUNCTION() macro is used to allow port/compiler specific + * language extensions.  The equivalent prototype for this function is: + * + * void prvIdleTask( void *pvParameters ); + * + */ +static +portTASK_FUNCTION (prvIdleTask, pvParameters) +{ +  /* Stop warnings. */ +  (void) pvParameters; + +  for (;;) +    { +      /* See if any tasks have been deleted. */ +      prvCheckTasksWaitingTermination (); + +#if ( configUSE_PREEMPTION == 0 ) +      { +	/* If we are not using preemption we keep forcing a task switch to +	   see if any other task has become available.  If we are using +	   preemption we don't need to do this as any task becoming available +	   will automatically get the processor anyway. */ +	taskYIELD (); +      } +#endif + +#if ( ( configUSE_PREEMPTION == 1 ) && ( configIDLE_SHOULD_YIELD == 1 ) ) +      { +	/* When using preemption tasks of equal priority will be +	   timesliced.  If a task that is sharing the idle priority is ready +	   to run then the idle task should yield before the end of the +	   timeslice. + +	   A critical region is not required here as we are just reading from +	   the list, and an occasional incorrect value will not matter.  If +	   the ready list at the idle priority contains more than one task +	   then a task other than the idle task is ready to execute. */ +	if (listCURRENT_LIST_LENGTH (&(pxReadyTasksLists[tskIDLE_PRIORITY])) > +	    (unsigned portBASE_TYPE) 1) +	  { +	    taskYIELD (); +	  } +      } +#endif + +#if ( configUSE_IDLE_HOOK == 1 ) +      { +	extern void vApplicationIdleHook (void); + +	/* Call the user defined function from within the idle task.  This +	   allows the application designer to add background functionality +	   without the overhead of a separate task. +	   NOTE: vApplicationIdleHook() MUST NOT, UNDER ANY CIRCUMSTANCES, +	   CALL A FUNCTION THAT MIGHT BLOCK. */ +	vApplicationIdleHook (); +      } +#endif +    } +}				/*lint !e715 pvParameters is not accessed but all task functions require the same prototype. */ + + + + + + + +/*----------------------------------------------------------- + * File private functions documented at the top of the file. + *----------------------------------------------------------*/ + + + +static void +prvInitialiseTCBVariables (tskTCB * pxTCB, unsigned portSHORT usStackDepth, +			   const signed portCHAR * const pcName, +			   unsigned portBASE_TYPE uxPriority) +{ +  pxTCB->usStackDepth = usStackDepth; + +  /* Store the function name in the TCB. */ +  strncpy ((char *) pxTCB->pcTaskName, (const char *) pcName, +	   (unsigned portSHORT) configMAX_TASK_NAME_LEN); +  pxTCB->pcTaskName[(unsigned portSHORT) configMAX_TASK_NAME_LEN - +		    (unsigned portSHORT) 1] = '\0'; + +  /* This is used as an array index so must ensure it's not too large. */ +  if (uxPriority >= configMAX_PRIORITIES) +    { +      uxPriority = configMAX_PRIORITIES - 1; +    } + +  pxTCB->uxPriority = uxPriority; + +  vListInitialiseItem (&(pxTCB->xGenericListItem)); +  vListInitialiseItem (&(pxTCB->xEventListItem)); + +  /* Set the pxTCB as a link back from the xListItem.  This is so we can get +     back to      the containing TCB from a generic item in a list. */ +  listSET_LIST_ITEM_OWNER (&(pxTCB->xGenericListItem), pxTCB); + +  /* Event lists are always in priority order. */ +  listSET_LIST_ITEM_VALUE (&(pxTCB->xEventListItem), +			   configMAX_PRIORITIES - (portTickType) uxPriority); +  listSET_LIST_ITEM_OWNER (&(pxTCB->xEventListItem), pxTCB); +} + +/*-----------------------------------------------------------*/ + +static void +prvInitialiseTaskLists (void) +{ +  unsigned portBASE_TYPE uxPriority; + +  for (uxPriority = 0; uxPriority < configMAX_PRIORITIES; uxPriority++) +    { +      vListInitialise ((xList *) & (pxReadyTasksLists[uxPriority])); +    } + +  vListInitialise ((xList *) & xDelayedTaskList1); +  vListInitialise ((xList *) & xDelayedTaskList2); +  vListInitialise ((xList *) & xPendingReadyList); + +#if ( INCLUDE_vTaskDelete == 1 ) +  { +    vListInitialise ((xList *) & xTasksWaitingTermination); +  } +#endif + +#if ( INCLUDE_vTaskSuspend == 1 ) +  { +    vListInitialise ((xList *) & xSuspendedTaskList); +  } +#endif + +  /* Start with pxDelayedTaskList using list1 and the pxOverflowDelayedTaskList +     using list2. */ +  pxDelayedTaskList = &xDelayedTaskList1; +  pxOverflowDelayedTaskList = &xDelayedTaskList2; +} + +/*-----------------------------------------------------------*/ + +static void +prvCheckTasksWaitingTermination (void) +{ +#if ( INCLUDE_vTaskDelete == 1 ) +  { +    portBASE_TYPE xListIsEmpty; + +    /* ucTasksDeleted is used to prevent vTaskSuspendAll() being called +       too often in the idle task. */ +    if (uxTasksDeleted > (unsigned portBASE_TYPE) 0) +      { +	vTaskSuspendAll (); +	xListIsEmpty = listLIST_IS_EMPTY (&xTasksWaitingTermination); +	xTaskResumeAll (); + +	if (!xListIsEmpty) +	  { +	    tskTCB *pxTCB; + +	    portENTER_CRITICAL (); +	    { +	      pxTCB = +		(tskTCB *) +		listGET_OWNER_OF_HEAD_ENTRY (((xList *) & +					      xTasksWaitingTermination)); +	      vListRemove (&(pxTCB->xGenericListItem)); +	      --uxCurrentNumberOfTasks; +	      --uxTasksDeleted; +	    } +	    portEXIT_CRITICAL (); + +	    prvDeleteTCB (pxTCB); +	  } +      } +  } +#endif +} + +/*-----------------------------------------------------------*/ + +static tskTCB * +prvAllocateTCBAndStack (unsigned portSHORT usStackDepth) +{ +  tskTCB *pxNewTCB; + +  /* Allocate space for the TCB.  Where the memory comes from depends on +     the implementation of the port malloc function. */ +  pxNewTCB = (tskTCB *) pvPortMalloc (sizeof (tskTCB)); + +  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 = +	(portSTACK_TYPE *) pvPortMalloc (((size_t) usStackDepth) * +					 sizeof (portSTACK_TYPE)); + +      if (pxNewTCB->pxStack == NULL) +	{ +	  /* Could not allocate the stack.  Delete the allocated TCB. */ +	  vPortFree (pxNewTCB); +	  pxNewTCB = NULL; +	} +      else +	{ +	  /* Just to help debugging. */ +	  memset (pxNewTCB->pxStack, tskSTACK_FILL_BYTE, +		  usStackDepth * sizeof (portSTACK_TYPE)); +	} +    } + +  return pxNewTCB; +} + +/*-----------------------------------------------------------*/ + +#if ( configUSE_TRACE_FACILITY == 1 ) + +static void +prvListTaskWithinSingleList (signed portCHAR * pcWriteBuffer, xList * pxList, +			     signed portCHAR cStatus) +{ +  volatile tskTCB *pxNextTCB, *pxFirstTCB; +  static portCHAR pcStatusString[50]; +  unsigned portSHORT usStackRemaining; + +  /* Write the details of all the TCB's in pxList into the buffer. */ +  listGET_OWNER_OF_NEXT_ENTRY (pxFirstTCB, pxList); +  do +    { +      listGET_OWNER_OF_NEXT_ENTRY (pxNextTCB, pxList); +      usStackRemaining = +	usTaskCheckFreeStackSpace ((unsigned portCHAR *) pxNextTCB->pxStack); +      sprintf (pcStatusString, (portCHAR *) "%s\t\t%c\t%u\t%u\t%u\r\n", +	       pxNextTCB->pcTaskName, cStatus, +	       (unsigned int) pxNextTCB->uxPriority, usStackRemaining, +	       (unsigned int) pxNextTCB->uxTCBNumber); +      strcat ((portCHAR *) pcWriteBuffer, (portCHAR *) pcStatusString); + +    } +  while (pxNextTCB != pxFirstTCB); +} + +#endif +/*-----------------------------------------------------------*/ + +#if ( configUSE_TRACE_FACILITY == 1 ) +unsigned portSHORT +usTaskCheckFreeStackSpace (const unsigned portCHAR * pucStackByte) +{ +  register unsigned portSHORT usCount = 0; + +  while (*pucStackByte == tskSTACK_FILL_BYTE) +    { +      pucStackByte -= portSTACK_GROWTH; +      usCount++; +    } + +  usCount /= sizeof (portSTACK_TYPE); + +  return usCount; +} +#endif +/*-----------------------------------------------------------*/ + + + +#if ( ( INCLUDE_vTaskDelete == 1 ) || ( INCLUDE_vTaskCleanUpResources == 1 ) ) + +static void +prvDeleteTCB (tskTCB * pxTCB) +{ +  /* Free up the memory allocated by the scheduler for the task.  It is up to +     the task to free any memory allocated at the application level. */ +  vPortFree (pxTCB->pxStack); +  vPortFree (pxTCB); +} + +#endif + + +/*-----------------------------------------------------------*/ + +#if ( INCLUDE_xTaskGetCurrentTaskHandle == 1 ) + +xTaskHandle +xTaskGetCurrentTaskHandle (void) +{ +  xTaskHandle xReturn; + +  portENTER_CRITICAL (); +  { +    xReturn = (xTaskHandle) pxCurrentTCB; +  } +  portEXIT_CRITICAL (); + +  return xReturn; +} + +#endif | 
