import ChibiOS 2.0.8

This commit is contained in:
NIIBE Yutaka
2010-11-30 13:54:43 +09:00
parent 27543cfeca
commit c560d0ad0c
1982 changed files with 5318 additions and 4046 deletions

View File

@@ -0,0 +1,102 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file ch.h
* @brief ChibiOS/RT main include file.
* @details This header includes all the required kernel headers so it is the
* only kernel header you usually want to include in your application.
*
* @addtogroup kernel_info
* @details Kernel related info.
* @{
*/
#ifndef _CH_H_
#define _CH_H_
/**
* @brief ChibiOS/RT identification macro.
*/
#define _CHIBIOS_RT_
/**
* @brief Kernel version string.
*/
#define CH_KERNEL_VERSION "2.0.8"
/**
* @brief Kernel version major number.
*/
#define CH_KERNEL_MAJOR 2
/**
* @brief Kernel version minor number.
*/
#define CH_KERNEL_MINOR 0
/**
* @brief Kernel version patch number.
*/
#define CH_KERNEL_PATCH 8
/*
* Common values.
*/
#ifndef FALSE
#define FALSE 0
#endif
#ifndef TRUE
#define TRUE (!FALSE)
#endif
#include "chconf.h"
#include "chtypes.h"
#include "chlists.h"
#include "chcore.h"
#include "chsys.h"
#include "chvt.h"
#include "chschd.h"
#include "chsem.h"
#include "chmtx.h"
#include "chcond.h"
#include "chevents.h"
#include "chmsg.h"
#include "chmboxes.h"
#include "chmemcore.h"
#include "chheap.h"
#include "chmempools.h"
#include "chthreads.h"
#include "chregistry.h"
#include "chinline.h"
#include "chqueues.h"
#include "chstreams.h"
#include "chioch.h"
#include "chdebug.h"
#endif /* _CH_H_ */
/** @} */

View File

@@ -0,0 +1,98 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/*
Concepts and parts of this file are contributed by and Copyright (C) 2008
of Leon Woestenberg.
*/
/**
* @file chcond.h
* @brief Condition Variables macros and structures.
*
* @addtogroup condvars
* @{
*/
#ifndef _CHCOND_H_
#define _CHCOND_H_
#if CH_USE_CONDVARS
/*
* Module dependencies check.
*/
#if !CH_USE_MUTEXES
#error "CH_USE_CONDVARS requires CH_USE_MUTEXES"
#endif
/**
* @brief CondVar structure.
*/
typedef struct CondVar {
ThreadsQueue c_queue; /**< @brief CondVar threads queue.*/
} CondVar;
#ifdef __cplusplus
extern "C" {
#endif
void chCondInit(CondVar *cp);
void chCondSignal(CondVar *cp);
void chCondSignalI(CondVar *cp);
void chCondBroadcast(CondVar *cp);
void chCondBroadcastI(CondVar *cp);
msg_t chCondWait(CondVar *cp);
msg_t chCondWaitS(CondVar *cp);
#if CH_USE_CONDVARS_TIMEOUT
msg_t chCondWaitTimeout(CondVar *cp, systime_t time);
msg_t chCondWaitTimeoutS(CondVar *cp, systime_t time);
#endif
#ifdef __cplusplus
}
#endif
/**
* @brief Data part of a static condition variable initializer.
* @details This macro should be used when statically initializing a condition
* variable that is part of a bigger structure.
*
* @param[in] name the name of the condition variable
*/
#define _CONDVAR_DATA(name) {_THREADSQUEUE_DATA(name.c_queue)}
/**
* @brief Static condition variable initializer.
* @details Statically initialized condition variables require no explicit
* initialization using @p chCondInit().
*
* @param[in] name the name of the condition variable
*/
#define CONDVAR_DECL(name) CondVar name = _CONDVAR_DATA(name)
#endif /* CH_USE_CONDVARS */
#endif /* _CHCOND_H_ */
/** @} */

View File

@@ -0,0 +1,170 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chdebug.h
* @brief Debug macros and structures.
*
* @addtogroup debug
* @{
*/
#ifndef _CHDEBUG_H_
#define _CHDEBUG_H_
/**
* @brief Trace buffer entries.
*/
#ifndef TRACE_BUFFER_SIZE
#define TRACE_BUFFER_SIZE 64
#endif
/**
* @brief Fill value for thread stack area in debug mode.
*/
#ifndef STACK_FILL_VALUE
#define STACK_FILL_VALUE 0x55
#endif
/**
* @brief Fill value for thread area in debug mode.
* @note The chosen default value is 0xFF in order to make evident which
* thread fields were not initialized when inspecting the memory with
* a debugger. A uninitialized field is not an error in itself but it
* better to know it.
*/
#ifndef THREAD_FILL_VALUE
#define THREAD_FILL_VALUE 0xFF
#endif
#if CH_DBG_ENABLE_TRACE || defined(__DOXYGEN__)
/**
* @brief Trace buffer record.
*/
typedef struct {
void *cse_wtobjp; /**< @brief Object where going to
sleep. */
systime_t cse_time; /**< @brief Time of the switch
event. */
uint16_t cse_state: 4; /**< @brief Switched out thread
state. */
uint16_t cse_tid: 12; /**< @brief Switched in thread id. */
} CtxSwcEvent;
/**
* @brief Trace buffer header.
*/
typedef struct {
unsigned tb_size; /**< @brief Trace buffer size
(entries). */
CtxSwcEvent *tb_ptr; /**< @brief Pointer to the ring buffer
front. */
/** @brief Ring buffer.*/
CtxSwcEvent tb_buffer[TRACE_BUFFER_SIZE];
} TraceBuffer;
#endif /* CH_DBG_ENABLE_TRACE */
#define __QUOTE_THIS(p) #p
#if CH_DBG_ENABLE_CHECKS
/**
* @brief Function parameter check.
* @details If the condition check fails then the kernel panics and halts.
* @note The condition is tested only if the @p CH_DBG_ENABLE_CHECKS switch
* is specified in @p chconf.h else the macro does nothing.
*
* @param[in] c the condition to be verified to be true
* @param[in] func the undecorated function name
*/
#define chDbgCheck(c, func) { \
if (!(c)) \
chDbgPanic(__QUOTE_THIS(func)"(), line "__QUOTE_THIS(__LINE__)); \
}
#else /* !CH_DBG_ENABLE_CHECKS */
#define chDbgCheck(c, func) { \
(void)(c), (void)__QUOTE_THIS(func)"(), line "__QUOTE_THIS(__LINE__); \
}
#endif /* !CH_DBG_ENABLE_CHECKS */
#if CH_DBG_ENABLE_ASSERTS
/**
* @brief Condition assertion.
* @details If the condition check fails then the kernel panics with the
* specified message and halts.
* @note The condition is tested only if the @p CH_DBG_ENABLE_ASSERTS switch
* is specified in @p chconf.h else the macro does nothing.
* @note The convention for the message is the following:<br>
* @<function_name@>(), #@<assert_number@>
* @note The remark string is not currently used except for putting a
* comment in the code about the assertion.
*
* @param[in] c the condition to be verified to be true
* @param[in] m the text message
* @param[in] r a remark string
*/
#define chDbgAssert(c, m, r) { \
if (!(c)) \
chDbgPanic(m); \
}
#else /* !CH_DBG_ENABLE_ASSERTS */
#define chDbgAssert(c, m, r) {(void)(c);}
#endif /* !CH_DBG_ENABLE_ASSERTS */
#if !(CH_DBG_ENABLE_ASSERTS || \
CH_DBG_ENABLE_CHECKS || \
CH_DBG_ENABLE_STACK_CHECK)
/* When the debug features are disabled this function is replaced by an empty
macro.*/
#define chDbgPanic(msg) {}
#endif
#if !CH_DBG_ENABLE_TRACE
/* When the trace feature is disabled this function is replaced by an empty
macro.*/
#define chDbgTrace(otp) {}
#endif
#if !defined(__DOXYGEN__)
#ifdef __cplusplus
extern "C" {
#endif
#if CH_DBG_ENABLE_TRACE
extern TraceBuffer trace_buffer;
void trace_init(void);
void chDbgTrace(Thread *otp);
#endif
#if CH_DBG_ENABLE_ASSERTS || CH_DBG_ENABLE_CHECKS || CH_DBG_ENABLE_STACK_CHECK
extern char *panic_msg;
void chDbgPanic(char *msg);
#endif
#ifdef __cplusplus
}
#endif
#endif /* !defined(__DOXYGEN__) */
#endif /* _CHDEBUG_H_ */
/** @} */

View File

@@ -0,0 +1,164 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chevents.h
* @brief Events macros and structures.
*
* @addtogroup events
* @{
*/
#ifndef _CHEVENTS_H_
#define _CHEVENTS_H_
#if CH_USE_EVENTS
typedef struct EventListener EventListener;
/**
* @brief Event Listener structure.
*/
struct EventListener {
EventListener *el_next; /**< @brief Next Event Listener
registered on the Event
Source. */
Thread *el_listener; /**< @brief Thread interested in the
Event Source. */
eventmask_t el_mask; /**< @brief Event flags mask associated
by the thread to the Event
Source. */
};
/**
* @brief Event Source structure.
*/
typedef struct EventSource {
EventListener *es_next; /**< @brief First Event Listener
registered on the Event
Source. */
} EventSource;
/**
* @brief Data part of a static event source initializer.
* @details This macro should be used when statically initializing an event
* source that is part of a bigger structure.
* @param name the name of the event source variable
*/
#define _EVENTSOURCE_DATA(name) {(void *)(&name)}
/**
* @brief Static event source initializer.
* @details Statically initialized event sources require no explicit
* initialization using @p chEvtInit().
*
* @param name the name of the event source variable
*/
#define EVENTSOURCE_DECL(name) EventSource name = _EVENTSOURCE_DATA(name)
/** All events allowed mask.*/
#define ALL_EVENTS ((eventmask_t)-1)
/** Returns the event mask from the event identifier.*/
#define EVENT_MASK(eid) ((eventmask_t)(1 << (eid)))
/**
* @brief Registers an Event Listener on an Event Source.
* @note Multiple Event Listeners can use the same event identifier, the
* listener will share the callback function.
*
* @param[in] esp pointer to the @p EventSource structure
* @param[out] elp pointer to the @p EventListener structure
* @param[in] eid numeric identifier assigned to the Event Listener. The
* identifier is used as index for the event callback
* function.
* The value must range between zero and the size, in bit,
* of the @p eventid_t type minus one.
*/
#define chEvtRegister(esp, elp, eid) chEvtRegisterMask(esp, elp, EVENT_MASK(eid))
/**
* @brief Initializes an Event Source.
* @note Can be used with interrupts disabled or enabled.
*
* @param[in] esp pointer to the @p EventSource structure
*/
#define chEvtInit(esp) \
((esp)->es_next = (EventListener *)(void *)(esp))
/**
* @brief Verifies if there is at least one @p EventListener registered.
* @note Can be called with interrupts disabled or enabled.
*
* @param[in] esp pointer to the @p EventSource structure
*/
#define chEvtIsListening(esp) \
((void *)(esp) != (void *)(esp)->es_next)
/**
* @brief Event Handler callback function.
*/
typedef void (*evhandler_t)(eventid_t);
#ifdef __cplusplus
extern "C" {
#endif
void chEvtRegisterMask(EventSource *esp,
EventListener *elp,
eventmask_t mask);
void chEvtUnregister(EventSource *esp, EventListener *elp);
eventmask_t chEvtClear(eventmask_t mask);
eventmask_t chEvtPend(eventmask_t mask);
void chEvtSignal(Thread *tp, eventmask_t mask);
void chEvtSignalI(Thread *tp, eventmask_t mask);
void chEvtBroadcast(EventSource *esp);
void chEvtBroadcastI(EventSource *esp);
void chEvtDispatch(const evhandler_t *handlers, eventmask_t mask);
#if CH_OPTIMIZE_SPEED || !CH_USE_EVENTS_TIMEOUT
eventmask_t chEvtWaitOne(eventmask_t mask);
eventmask_t chEvtWaitAny(eventmask_t mask);
eventmask_t chEvtWaitAll(eventmask_t mask);
#endif
#if CH_USE_EVENTS_TIMEOUT
eventmask_t chEvtWaitOneTimeout(eventmask_t mask, systime_t time);
eventmask_t chEvtWaitAnyTimeout(eventmask_t mask, systime_t time);
eventmask_t chEvtWaitAllTimeout(eventmask_t mask, systime_t time);
#endif
#ifdef __cplusplus
}
#endif
#if !CH_OPTIMIZE_SPEED && CH_USE_EVENTS_TIMEOUT
#define chEvtWaitOne(mask) chEvtWaitOneTimeout(mask, TIME_INFINITE)
#define chEvtWaitAny(mask) chEvtWaitAnyTimeout(mask, TIME_INFINITE)
#define chEvtWaitAll(mask) chEvtWaitAllTimeout(mask, TIME_INFINITE)
#endif
#endif /* CH_USE_EVENTS */
#endif /* _CHEVENTS_H_ */
/** @} */

View File

@@ -0,0 +1,97 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chheap.h
* @brief Heaps macros and structures.
*
* @addtogroup heaps
* @{
*/
#ifndef _CHHEAP_H_
#define _CHHEAP_H_
#if CH_USE_HEAP
/*
* Module dependencies check.
*/
#if !CH_USE_MEMCORE && !CH_USE_MALLOC_HEAP
#error "CH_USE_HEAP requires CH_USE_MEMCORE or CH_USE_MALLOC_HEAP"
#endif
#if !CH_USE_MUTEXES && !CH_USE_SEMAPHORES
#error "CH_USE_HEAP requires CH_USE_MUTEXES and/or CH_USE_SEMAPHORES"
#endif
typedef struct memory_heap MemoryHeap;
/**
* @brief Memory heap block header.
*/
union heap_header {
stkalign_t align;
struct {
union {
union heap_header *next; /**< @brief Next block in free list. */
MemoryHeap *heap; /**< @brief Block owner heap. */
} u; /**< @brief Overlapped fields. */
size_t size; /**< @brief Size of the memory block. */
} h;
};
/**
* @brief Structure describing a memory heap.
*/
struct memory_heap {
memgetfunc_t h_provider; /**< @brief Memory blocks provider for
this heap. */
union heap_header h_free; /**< @brief Free blocks list header. */
#if CH_USE_MUTEXES
Mutex h_mtx; /**< @brief Heap access mutex. */
#else
Semaphore h_sem; /**< @brief Heap access semaphore. */
#endif
};
#ifdef __cplusplus
extern "C" {
#endif
void heap_init(void);
void chHeapInit(MemoryHeap *heapp, void *buf, size_t size);
void *chHeapAlloc(MemoryHeap *heapp, size_t size);
void chHeapFree(void *p);
size_t chHeapStatus(MemoryHeap *heapp, size_t *sizep);
#ifdef __cplusplus
}
#endif
#endif /* CH_USE_HEAP */
#endif /* _CHHEAP_H_ */
/** @} */

View File

@@ -0,0 +1,93 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chinline.h
* @brief Kernel inlined functions.
* @details In this file there are a set of inlined functions if the
* @p CH_OPTIMIZE_SPEED is enabled.
*/
#ifndef _CHINLINE_H_
#define _CHINLINE_H_
/* If the performance code path has been chosen then all the following
functions are inlined into the various kernel modules.*/
#if CH_OPTIMIZE_SPEED
static INLINE void prio_insert(Thread *tp, ThreadsQueue *tqp) {
Thread *cp = (Thread *)tqp;
do {
cp = cp->p_next;
} while ((cp != (Thread *)tqp) && (cp->p_prio >= tp->p_prio));
tp->p_next = cp;
tp->p_prev = cp->p_prev;
tp->p_prev->p_next = cp->p_prev = tp;
}
static INLINE void queue_insert(Thread *tp, ThreadsQueue *tqp) {
tp->p_next = (Thread *)tqp;
tp->p_prev = tqp->p_prev;
tp->p_prev->p_next = tqp->p_prev = tp;
}
static INLINE Thread *fifo_remove(ThreadsQueue *tqp) {
Thread *tp = tqp->p_next;
(tqp->p_next = tp->p_next)->p_prev = (Thread *)tqp;
return tp;
}
static INLINE Thread *lifo_remove(ThreadsQueue *tqp) {
Thread *tp = tqp->p_prev;
(tqp->p_prev = tp->p_prev)->p_next = (Thread *)tqp;
return tp;
}
static INLINE Thread *dequeue(Thread *tp) {
tp->p_prev->p_next = tp->p_next;
tp->p_next->p_prev = tp->p_prev;
return tp;
}
static INLINE void list_insert(Thread *tp, ThreadsList *tlp) {
tp->p_next = tlp->p_next;
tlp->p_next = tp;
}
static INLINE Thread *list_remove(ThreadsList *tlp) {
Thread *tp = tlp->p_next;
tlp->p_next = tp->p_next;
return tp;
}
#endif /* CH_OPTIMIZE_SPEED */
#endif /* _CHINLINE_H_ */

View File

@@ -0,0 +1,284 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chioch.h
* @brief I/O channels.
* @details This header defines abstract interfaces useful to access generic
* I/O resources in a standardized way.
*
* @addtogroup io_channels
* @details This module defines an abstract interface for I/O channels by
* extending the @p BaseSequentialStream interface. Note that no code
* is present, I/O channels are just abstract interface like
* structures, you should look at the systems as to a set of abstract
* C++ classes (even if written in C). Specific device drivers can
* use/extend the interface and implement them.<br>
* This system has the advantage to make the access to channels
* independent from the implementation logic.
* @{
*/
#ifndef _CHIOCH_H_
#define _CHIOCH_H_
/**
* @brief @p BaseChannel specific methods.
*/
#define _base_channel_methods \
_base_sequential_stream_methods \
/* Channel output check.*/ \
bool_t (*putwouldblock)(void *instance); \
/* Channel input check.*/ \
bool_t (*getwouldblock)(void *instance); \
/* Channel put method with timeout specification.*/ \
msg_t (*put)(void *instance, uint8_t b, systime_t time); \
/* Channel get method with timeout specification.*/ \
msg_t (*get)(void *instance, systime_t time); \
/* Channel write method with timeout specification.*/ \
size_t (*writet)(void *instance, const uint8_t *bp, \
size_t n, systime_t time); \
/* Channel read method with timeout specification.*/ \
size_t (*readt)(void *instance, uint8_t *bp, size_t n, systime_t time);
/**
* @brief @p BaseChannel specific data.
* @note It is empty because @p BaseChannel is only an interface without
* implementation.
*/
#define _base_channel_data \
_base_sequential_stream_data
/**
* @brief @p BaseChannel virtual methods table.
*/
struct BaseChannelVMT { \
_base_channel_methods \
};
/**
* @extends BaseSequentialStream
*
* @brief Base channel class.
* @details This class represents a generic, byte-wide, I/O channel. This class
* introduces generic I/O primitives with timeout specification.
*/
typedef struct {
/** @brief Virtual Methods Table.*/
const struct BaseChannelVMT *vmt;
_base_channel_data
} BaseChannel;
/**
* @brief Channel output check.
* @details This function verifies if a subsequent put/write operation would
* block.
*
* @param[in] ip pointer to a @p BaseChannel or derived class
* @return The output queue status:
* @retval FALSE if the output queue has space and would not block a
* write operation.
* @retval TRUE if the output queue is full and would block a write
* operation.
*/
#define chIOPutWouldBlock(ip) ((ip)->vmt->putwouldblock(ip))
/**
* @brief Channel input check.
* @details This function verifies if a subsequent get/read operation would
* block.
*
* @param[in] ip pointer to a @p BaseChannel or derived class
* @return The input queue status:
* @retval FALSE if the input queue contains data and would not block a
* read operation.
* @retval TRUE if the input queue is empty and would block a read
* operation.
*/
#define chIOGetWouldBlock(ip) ((ip)->vmt->getwouldblock(ip))
/**
* @brief Channel blocking byte write.
* @details This function writes a byte value to a channel. If the channel
* is not ready to accept data then the calling thread is suspended.
*
* @param[in] ip pointer to a @p BaseChannel or derived class
* @param[in] b the byte value to be written to the channel
* @return The operation status:
* @retval Q_OK if the operation succeeded.
* @retval Q_RESET if the channel associated queue (if any) was reset.
*/
#define chIOPut(ip, b) ((ip)->vmt->put(ip, b, TIME_INFINITE))
/**
* @brief Channel blocking byte write with timeout.
* @details This function writes a byte value to a channel. If the channel
* is not ready to accept data then the calling thread is suspended.
*
* @param[in] ip pointer to a @p BaseChannel or derived class
* @param[in] b the byte value to be written to the channel
* @param[in] time the number of ticks before the operation timeouts,
* the following special values are allowed:
* - @a TIME_IMMEDIATE immediate timeout.
* - @a TIME_INFINITE no timeout.
* .
* @return The operation status:
* @retval Q_OK if the operation succeeded.
* @retval Q_TIMEOUT if the specified time expired.
* @retval Q_RESET if the channel associated queue (if any) was reset.
*/
#define chIOPutTimeout(ip, b, time) ((ip)->vmt->put(ip, b, time))
/**
* @brief Channel blocking byte read.
* @details This function reads a byte value from a channel. If the data
* is not available then the calling thread is suspended.
*
* @param[in] ip pointer to a @p BaseChannel or derived class
* @return A byte value from the queue or:
* @retval Q_RESET if the channel associated queue (if any) was reset.
*/
#define chIOGet(ip) ((ip)->vmt->get(ip, TIME_INFINITE))
/**
* @brief Channel blocking byte read with timeout.
* @details This function reads a byte value from a channel. If the data
* is not available then the calling thread is suspended.
*
* @param[in] ip pointer to a @p BaseChannel or derived class
* @param[in] time the number of ticks before the operation timeouts,
* the following special values are allowed:
* - @a TIME_IMMEDIATE immediate timeout.
* - @a TIME_INFINITE no timeout.
* .
* @return A byte value from the queue or:
* @retval Q_TIMEOUT if the specified time expired.
* @retval Q_RESET if the channel associated queue (if any) was reset.
*/
#define chIOGetTimeout(ip, time) ((ip)->vmt->get(ip, time))
/**
* @brief Channel blocking write with timeout.
* @details The function writes data from a buffer to a channel. If the channel
* is not ready to accept data then the calling thread is suspended.
*
* @param[in] ip pointer to a @p BaseChannel or derived class
* @param[out] bp pointer to the data buffer
* @param[in] n the maximum amount of data to be transferred
* @param[in] time the number of ticks before the operation timeouts,
* the following special values are allowed:
* - @a TIME_IMMEDIATE immediate timeout.
* - @a TIME_INFINITE no timeout.
* .
* @return The number of bytes transferred.
*/
#define chIOWriteTimeout(ip, bp, n, time) \
((ip)->vmt->writet(ip, bp, n, time))
/**
* @brief Channel blocking read with timeout.
* @details The function reads data from a channel into a buffer. If the data
* is not available then the calling thread is suspended.
*
* @param[in] ip pointer to a @p BaseChannel or derived class
* @param[in] bp pointer to the data buffer
* @param[in] n the maximum amount of data to be transferred
* @param[in] time the number of ticks before the operation timeouts,
* the following special values are allowed:
* - @a TIME_IMMEDIATE immediate timeout.
* - @a TIME_INFINITE no timeout.
* .
* @return The number of bytes transferred.
*/
#define chIOReadTimeout(ip, bp, n, time) \
((ip)->vmt->readt(ip, bp, n, time))
#if CH_USE_EVENTS
/**
* @brief @p BaseAsynchronousChannel specific methods.
*/
#define _base_asynchronous_channel_methods \
_base_channel_methods
/**
* @brief @p BaseAsynchronousChannel specific data.
*/
#define _base_asynchronous_channel_data \
_base_channel_data \
/* Data Available EventSource.*/ \
EventSource ievent; \
/* Data Transmitted EventSource.*/ \
EventSource oevent;
/**
* @brief @p BaseAsynchronousChannel virtual methods table.
*/
struct BaseAsynchronousChannelVMT {
_base_asynchronous_channel_methods
};
/**
* @extends BaseChannel
*
* @brief Base asynchronous channel class.
* @details This class extends @p BaseChannel by adding event sources fields
* for asynchronous I/O for use in an event-driven environment.
*/
typedef struct {
/** @brief Virtual Methods Table.*/
const struct BaseAsynchronousChannelVMT *vmt;
_base_asynchronous_channel_data
} BaseAsynchronousChannel;
/**
* @brief Returns the write event source.
* @details The write event source is broadcasted when the channel is ready
* for write operations. This usually happens when the internal
* output queue becomes empty.
*
* @param[in] ip pointer to a @p BaseAsynchronousChannel or derived
* class
* @return A pointer to an @p EventSource object.
*/
#define chIOGetWriteEventSource(ip) (&((ip)->vmt->oevent))
/**
* @brief Returns the read event source.
* @details The read event source is broadcasted when the channel is ready
* for read operations. This usually happens when the internal
* input queue becomes non-empty.
*
* @param[in] ip pointer to a @p BaseAsynchronousChannel or derived
* class
* @return A pointer to an @p EventSource object.
*/
#define chIOGetReadEventSource(ip) (&((ip)->vmt->ievent))
#endif /* CH_USE_EVENTS */
#endif /* _CHIOCH_H_ */
/** @} */

View File

@@ -0,0 +1,125 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chlists.h
* @brief Thread queues/lists macros and structures.
* @note All the macros present in this module, while public, are not
* an OS API and should not be directly used in the user applications
* code.
*
* @addtogroup internals
* @{
*/
#ifndef _CHLISTS_H_
#define _CHLISTS_H_
typedef struct Thread Thread;
/**
* @brief Threads queue initialization.
*/
#define queue_init(tqp) ((tqp)->p_next = (tqp)->p_prev = (Thread *)(tqp));
/**
* @brief Threads list initialization.
*/
#define list_init(tlp) ((tlp)->p_next = (Thread *)(tlp))
/**
* @brief Evaluates to @p TRUE if the specified threads queue or list is
* empty.
*/
#define isempty(p) ((p)->p_next == (Thread *)(p))
/**
* @brief Evaluates to @p TRUE if the specified threads queue or list is
* not empty.
*/
#define notempty(p) ((p)->p_next != (Thread *)(p))
/**
* @brief Data part of a static threads queue initializer.
* @details This macro should be used when statically initializing a threads
* queue that is part of a bigger structure.
*
* @param[in] name the name of the threads queue variable
*/
#define _THREADSQUEUE_DATA(name) {(Thread *)&name, (Thread *)&name}
/**
* @brief Static threads queue initializer.
* @details Statically initialized threads queues require no explicit
* initialization using @p queue_init().
*
* @param[in] name the name of the threads queue variable
*/
#define THREADSQUEUE_DECL(name) ThreadsQueue name = _THREADSQUEUE_DATA(name)
/**
* @extends ThreadsList
*
* @brief Generic threads bidirectional linked list header and element.
*/
typedef struct {
Thread *p_next; /**< First @p Thread in the queue, or
@p ThreadQueue when empty. */
Thread *p_prev; /**< Last @p Thread in the queue, or
@p ThreadQueue when empty. */
} ThreadsQueue;
/**
* @brief Generic threads single link list, it works like a stack.
*/
typedef struct {
Thread *p_next; /**< Last pushed @p Thread on the stack
list, or pointer to itself if
empty. */
} ThreadsList;
#if !CH_OPTIMIZE_SPEED
#ifdef __cplusplus
extern "C" {
#endif
void prio_insert(Thread *tp, ThreadsQueue *tqp);
void queue_insert(Thread *tp, ThreadsQueue *tqp);
Thread *fifo_remove(ThreadsQueue *tqp);
Thread *lifo_remove(ThreadsQueue *tqp);
Thread *dequeue(Thread *tp);
void list_insert(Thread *tp, ThreadsList *tlp);
Thread *list_remove(ThreadsList *tlp);
#ifdef __cplusplus
}
#endif
#endif /* !CH_OPTIMIZE_SPEED */
#endif /* _CHLISTS_H_ */
/** @} */

View File

@@ -0,0 +1,150 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chmboxes.h
* @brief Mailboxes macros and structures.
*
* @addtogroup mailboxes
* @{
*/
#ifndef _CHMBOXES_H_
#define _CHMBOXES_H_
#if CH_USE_MAILBOXES
/*
* Module dependencies check.
*/
#if !CH_USE_SEMAPHORES
#error "CH_USE_MAILBOXES requires CH_USE_SEMAPHORES"
#endif
typedef struct {
msg_t *mb_buffer; /**< @brief Pointer to the mailbox
buffer. */
msg_t *mb_top; /**< @brief Pointer to the location
after the buffer. */
msg_t *mb_wrptr; /**< @brief Write pointer. */
msg_t *mb_rdptr; /**< @brief Read pointer. */
Semaphore mb_fullsem; /**< @brief Full counter
@p Semaphore. */
Semaphore mb_emptysem; /**< @brief Empty counter
@p Semaphore. */
} Mailbox;
#ifdef __cplusplus
extern "C" {
#endif
void chMBInit(Mailbox *mbp, msg_t *buf, cnt_t n);
void chMBReset(Mailbox *mbp);
msg_t chMBPost(Mailbox *mbp, msg_t msg, systime_t timeout);
msg_t chMBPostS(Mailbox *mbp, msg_t msg, systime_t timeout);
msg_t chMBPostAhead(Mailbox *mbp, msg_t msg, systime_t timeout);
msg_t chMBPostAheadS(Mailbox *mbp, msg_t msg, systime_t timeout);
msg_t chMBFetch(Mailbox *mbp, msg_t *msgp, systime_t timeout);
msg_t chMBFetchS(Mailbox *mbp, msg_t *msgp, systime_t timeout);
#ifdef __cplusplus
}
#endif
/**
* @brief Returns the mailbox buffer size.
*
* @param[in] mbp the pointer to an initialized Mailbox object
*/
#define chMBSize(mbp) \
((mbp)->mb_top - (mbp)->mb_buffer)
/**
* @brief Returns the free space into the mailbox.
* @note Can be invoked in any system state but if invoked out of a locked
* state then the returned value may change after reading.
* @note The returned value can be less than zero when there are waiting
* threads on the internal semaphore.
*
* @param[in] mbp the pointer to an initialized Mailbox object
* @return The number of empty message slots.
*/
#define chMBGetEmpty(mbp) chSemGetCounterI(&(mbp)->mb_emptysem)
/**
* @brief Returns the number of messages into the mailbox.
* @note Can be invoked in any system state but if invoked out of a locked
* state then the returned value may change after reading.
* @note The returned value can be less than zero when there are waiting
* threads on the internal semaphore.
*
* @param[in] mbp the pointer to an initialized Mailbox object
* @return The number of queued messages.
*/
#define chMBGetFull(mbp) chSemGetCounterI(&(mbp)->mb_fullsem)
/**
* @brief Returns the next message in the queue without removing it.
* @note A message must be waiting in the queue for this function to work or
* it would return garbage. The correct way to use this macro is to
* use @p chMBGetFull() and then use this macro, all within a lock
* state.
*/
#define chMBPeek(mbp) (*(mbp)->mb_rdptr)
/**
* @brief Data part of a static mailbox initializer.
* @details This macro should be used when statically initializing a
* mailbox that is part of a bigger structure.
*
* @param[in] name the name of the mailbox variable
* @param[in] buffer pointer to the mailbox buffer area
* @param[in] size size of the mailbox buffer area
*/
#define _MAILBOX_DATA(name, buffer, size) { \
(msg_t *)(buffer), \
(msg_t *)(buffer) + size, \
(msg_t *)(buffer), \
(msg_t *)(buffer), \
_SEMAPHORE_DATA(name.mb_fullsem, 0), \
_SEMAPHORE_DATA(name.mb_emptysem, size), \
}
/**
* @brief Static mailbox initializer.
* @details Statically initialized mailboxes require no explicit
* initialization using @p chMBInit().
*
* @param[in] name the name of the mailbox variable
* @param[in] buffer pointer to the mailbox buffer area
* @param[in] size size of the mailbox buffer area
*/
#define MAILBOX_DECL(name, buffer, size) \
Mailbox name = _MAILBOX_DATA(name, buffer, size)
#endif /* CH_USE_MAILBOXES */
#endif /* _CHMBOXES_H_ */
/** @} */

View File

@@ -0,0 +1,78 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chmemcore.h
* @brief Core memory manager macros and structures.
*
* @addtogroup memcore
* @{
*/
#ifndef _CHMEMCORE_H_
#define _CHMEMCORE_H_
/**
* @brief Memory get function.
* @note This type must be assignment compatible with the @p chMemAlloc()
* function.
*/
typedef void *(*memgetfunc_t)(size_t size);
/**
* @brief Alignment mask constant.
*/
#define MEM_ALIGN_MASK (sizeof(stkalign_t) - 1)
/**
* @brief Alignment helper macro.
*/
#define MEM_ALIGN_SIZE(p) (((size_t)(p) + MEM_ALIGN_MASK) & ~MEM_ALIGN_MASK)
/**
* @brief Returns whatever a pointer or memory size is aligned to
* the type @p align_t.
*/
#define MEM_IS_ALIGNED(p) (((size_t)(p) & MEM_ALIGN_MASK) == 0)
#if CH_USE_MEMCORE
#ifdef __cplusplus
extern "C" {
#endif
void core_init(void);
void *chCoreAlloc(size_t size);
void *chCoreAllocI(size_t size);
size_t chCoreStatus(void);
#ifdef __cplusplus
}
#endif
#endif /* CH_USE_MEMCORE */
#endif /* _CHMEMCORE_H_ */
/** @} */

View File

@@ -0,0 +1,100 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chmempools.h
* @brief Memory Pools macros and structures.
*
* @addtogroup pools
* @{
*/
#ifndef _CHMEMPOOLS_H_
#define _CHMEMPOOLS_H_
#if CH_USE_MEMPOOLS
/**
* @brief Memory pool free object header.
*/
struct pool_header {
struct pool_header *ph_next; /**< @brief Pointer to the next pool
header in the list. */
};
/**
* @brief Memory pool descriptor.
*/
typedef struct {
struct pool_header *mp_next; /**< @brief Pointer to the header. */
size_t mp_object_size; /**< @brief Memory pool objects
size. */
memgetfunc_t mp_provider; /**< @brief Memory blocks provider for
this pool. */
} MemoryPool;
/**
* @brief Data part of a static memory pool initializer.
* @details This macro should be used when statically initializing a
* memory pool that is part of a bigger structure.
*
* @param[in] name the name of the memory pool variable
* @param[in] size size of the memory pool contained objects
* @param[in] provider memory provider function for the memory pool
*/
#define _MEMORYPOOL_DATA(name, size, provider) \
{NULL, MEM_ALIGN_SIZE(size), provider}
/**
* @brief Static memory pool initializer in hungry mode.
* @details Statically initialized memory pools require no explicit
* initialization using @p chPoolInit().
*
* @param[in] name the name of the memory pool variable
* @param[in] size size of the memory pool contained objects
* @param[in] provider memory provider function for the memory pool or @p NULL
* if the pool is not allowed to grow automatically
*/
#define MEMORYPOOL_DECL(name, size, provider) \
MemoryPool name = _MEMORYPOOL_DATA(name, size, provider)
#ifdef __cplusplus
extern "C" {
#endif
void chPoolInit(MemoryPool *mp, size_t size, memgetfunc_t provider);
void *chPoolAllocI(MemoryPool *mp);
void *chPoolAlloc(MemoryPool *mp);
void chPoolFreeI(MemoryPool *mp, void *objp);
void chPoolFree(MemoryPool *mp, void *objp);
#ifdef __cplusplus
}
#endif
#endif /* CH_USE_MEMPOOLS */
#endif /* _CHMEMPOOLS_H_ */
/** @} */

View File

@@ -0,0 +1,67 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chmsg.h
* @brief Messages macros and structures.
*
* @addtogroup messages
* @{
*/
#ifndef _CHMSG_H_
#define _CHMSG_H_
#if CH_USE_MESSAGES
/**
* @brief Evaluates to TRUE if the thread has pending messages.
*/
#define chMsgIsPendingI(tp) \
((tp)->p_msgqueue.p_next != (Thread *)&(tp)->p_msgqueue)
/**
* @brief Returns the first message in the queue.
*/
#define chMsgGetI(tp) \
((tp)->p_msgqueue.p_next->p_msg)
#ifdef __cplusplus
extern "C" {
#endif
msg_t chMsgSend(Thread *tp, msg_t msg);
msg_t chMsgWait(void);
msg_t chMsgGet(void);
void chMsgRelease(msg_t msg);
#ifdef __cplusplus
}
#endif
#endif /* CH_USE_MESSAGES */
#endif /* _CHMSG_H_ */
/** @} */

View File

@@ -0,0 +1,95 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chmtx.h
* @brief Mutexes macros and structures.
*
* @addtogroup mutexes
* @{
*/
#ifndef _CHMTX_H_
#define _CHMTX_H_
#if CH_USE_MUTEXES
/**
* @brief Mutex structure.
*/
typedef struct Mutex {
ThreadsQueue m_queue; /**< @brief Queue of the threads sleeping
on this Mutex. */
Thread *m_owner; /**< @brief Owner @p Thread pointer or
@p NULL. */
struct Mutex *m_next; /**< @brief Next @p Mutex into an
owner-list or @p NULL. */
} Mutex;
#ifdef __cplusplus
extern "C" {
#endif
void chMtxInit(Mutex *mp);
void chMtxLock(Mutex *mp);
void chMtxLockS(Mutex *mp);
bool_t chMtxTryLock(Mutex *mp);
bool_t chMtxTryLockS(Mutex *mp);
Mutex *chMtxUnlock(void);
Mutex *chMtxUnlockS(void);
void chMtxUnlockAll(void);
#ifdef __cplusplus
}
#endif
/**
* @brief Data part of a static mutex initializer.
* @details This macro should be used when statically initializing a mutex
* that is part of a bigger structure.
*
* @param[in] name the name of the mutex variable
*/
#define _MUTEX_DATA(name) {_THREADSQUEUE_DATA(name.m_queue), NULL, NULL}
/**
* @brief Static mutex initializer.
* @details Statically initialized mutexes require no explicit initialization
* using @p chMtxInit().
*
* @param[in] name the name of the mutex variable
*/
#define MUTEX_DECL(name) Mutex name = _MUTEX_DATA(name)
/**
* @brief Returns @p TRUE if the mutex queue contains at least a waiting
* thread.
*/
#define chMtxQueueNotEmptyS(mp) notempty(&(mp)->m_queue)
#endif /* CH_USE_MUTEXES */
#endif /* _CHMTX_H_ */
/** @} */

View File

@@ -0,0 +1,249 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chqueues.h I/O
* @brief Queues macros and structures.
*
* @addtogroup io_queues
* @{
*/
#ifndef _CHQUEUES_H_
#define _CHQUEUES_H_
#if CH_USE_QUEUES
/*
* Module dependencies check.
*/
#if !CH_USE_SEMAPHORES
#error "CH_USE_QUEUES requires CH_USE_SEMAPHORES"
#endif
/** @brief Queue notification callback type.*/
typedef void (*qnotify_t)(void);
/** @brief Returned by the queue functions if the operation is successful.*/
#define Q_OK RDY_OK
/** @brief Returned by the queue functions if a timeout occurs.*/
#define Q_TIMEOUT RDY_TIMEOUT
/** @brief Returned by the queue functions if the queue is reset.*/
#define Q_RESET RDY_RESET
/** @brief Returned by the queue functions if the queue is empty.*/
#define Q_EMPTY -3
/** @brief Returned by the queue functions if the queue is full.*/
#define Q_FULL -4
/**
* @brief Generic I/O queue structure.
* @details This structure represents a generic Input or Output asymmetrical
* queue. The queue is asymmetrical because one end is meant to be
* accessed from a thread context, and thus can be blocking, the other
* end is accessible from interrupt handlers or from within a kernel
* lock zone (see <b>I-Locked</b> and <b>S-Locked</b> states in
* @ref system_states) and is non-blocking.
*/
typedef struct {
uint8_t *q_buffer; /**< @brief Pointer to the queue buffer.*/
uint8_t *q_top; /**< @brief Pointer to the first location
after the buffer. */
uint8_t *q_wrptr; /**< @brief Write pointer. */
uint8_t *q_rdptr; /**< @brief Read pointer. */
Semaphore q_sem; /**< @brief Counter @p Semaphore. */
qnotify_t q_notify; /**< @brief Data notification callback. */
} GenericQueue;
/**
* @brief Returns the queue's buffer size.
*/
#define chQSize(q) ((q)->q_top - (q)->q_buffer)
/**
* @brief Queue space.
* @details Returns the used space if used on an Input Queue and the empty
* space if used on an Output Queue.
* @note The returned value can be less than zero when there are waiting
* threads on the internal semaphore.
*/
#define chQSpace(q) chSemGetCounterI(&(q)->q_sem)
/**
* @extends GenericQueue
*
* @brief Input queue structure.
* @details This structure represents a generic asymmetrical input queue.
* Writing in the queue is non-blocking and can be performed from
* interrupt handlers or from within a kernel lock zone (see
* <b>I-Locked</b> and <b>S-Locked</b> states in @ref system_states).
* Reading the queue can be a blocking operation and is supposed to
* be performed by a system thread.
*/
typedef GenericQueue InputQueue;
/** @brief Evaluates to @p TRUE if the specified Input Queue is empty.*/
#define chIQIsEmpty(q) ((bool_t)(chQSpace(q) <= 0))
/** @brief Evaluates to @p TRUE if the specified Input Queue is full.*/
#define chIQIsFull(q) ((bool_t)(chQSpace(q) >= chQSize(q)))
/**
* @brief Input queue read.
* @details This function reads a byte value from an input queue. If the queue
* is empty then the calling thread is suspended until a byte arrives
* in the queue.
*
* @param[in] iqp pointer to an @p InputQueue structure
* @return A byte value from the queue or:
* @retval Q_RESET if the queue was reset.
*/
#define chIQGet(iqp) chIQGetTimeout(iqp, TIME_INFINITE)
/**
* @brief Data part of a static input queue initializer.
* @details This macro should be used when statically initializing an
* input queue that is part of a bigger structure.
*
* @param[in] name the name of the input queue variable
* @param[in] buffer pointer to the queue buffer area
* @param[in] size size of the queue buffer area
* @param[in] inotify input notification callback pointer
*/
#define _INPUTQUEUE_DATA(name, buffer, size, inotify) { \
(uint8_t *)(buffer), \
(uint8_t *)(buffer) + size, \
(uint8_t *)(buffer), \
(uint8_t *)(buffer), \
_SEMAPHORE_DATA(name.q_sem, 0), \
inotify \
}
/**
* @brief Static input queue initializer.
* @details Statically initialized input queues require no explicit
* initialization using @p chIQInit().
*
* @param[in] name the name of the input queue variable
* @param[in] buffer pointer to the queue buffer area
* @param[in] size size of the queue buffer area
* @param[in] inotify input notification callback pointer
*/
#define INPUTQUEUE_DECL(name, buffer, size, inotify) \
InputQueue name = _INPUTQUEUE_DATA(name, buffer, size, inotify)
/**
* @extends GenericQueue
*
* @brief Output queue structure.
* @details This structure represents a generic asymmetrical output queue.
* Reading from the queue is non-blocking and can be performed from
* interrupt handlers or from within a kernel lock zone (see
* <b>I-Locked</b> and <b>S-Locked</b> states in @ref system_states).
* Writing the queue can be a blocking operation and is supposed to
* be performed by a system thread.
*/
typedef GenericQueue OutputQueue;
/**
* @brief Evaluates to @p TRUE if the specified Output Queue is empty.
*/
#define chOQIsEmpty(q) ((bool_t)(chQSpace(q) >= chQSize(q)))
/**
* @brief Evaluates to @p TRUE if the specified Output Queue is full.
*/
#define chOQIsFull(q) ((bool_t)(chQSpace(q) <= 0))
/**
* @brief Output queue write.
* @details This function writes a byte value to an output queue. If the queue
* is full then the calling thread is suspended until there is space
* in the queue.
*
* @param[in] oqp pointer to an @p OutputQueue structure
* @param[in] b the byte value to be written in the queue
* @return The operation status:
* @retval Q_OK if the operation succeeded.
* @retval Q_RESET if the queue was reset.
*/
#define chOQPut(oqp, b) chOQPutTimeout(oqp, b, TIME_INFINITE)
/**
* @brief Data part of a static output queue initializer.
* @details This macro should be used when statically initializing an
* output queue that is part of a bigger structure.
*
* @param[in] name the name of the output queue variable.
* @param[in] buffer pointer to the queue buffer area
* @param[in] size size of the queue buffer area
* @param[in] onotify output notification callback pointer
*/
#define _OUTPUTQUEUE_DATA(name, buffer, size, onotify) { \
(uint8_t *)(buffer), \
(uint8_t *)(buffer) + size, \
(uint8_t *)(buffer), \
(uint8_t *)(buffer), \
_SEMAPHORE_DATA(name.q_sem, size), \
onotify \
}
/**
* @brief Static output queue initializer.
* @details Statically initialized output queues require no explicit
* initialization using @p chOQInit().
*
* @param[in] name the name of the output queue variable
* @param[in] buffer pointer to the queue buffer area
* @param[in] size size of the queue buffer area
* @param[in] onotify output notification callback pointer
*/
#define OUTPUTQUEUE_DECL(name, buffer, size, onotify) \
InputQueue name = _OUTPUTQUEUE_DATA(name, buffer, size, onotify)
#ifdef __cplusplus
extern "C" {
#endif
void chIQInit(InputQueue *qp, uint8_t *bp, size_t size, qnotify_t infy);
void chIQResetI(InputQueue *qp);
msg_t chIQPutI(InputQueue *qp, uint8_t b);
msg_t chIQGetTimeout(InputQueue *qp, systime_t time);
size_t chIQReadTimeout(InputQueue *qp, uint8_t *bp,
size_t n, systime_t time);
void chOQInit(OutputQueue *queue, uint8_t *bp, size_t size, qnotify_t onfy);
void chOQResetI(OutputQueue *queue);
msg_t chOQPutTimeout(OutputQueue *queue, uint8_t b, systime_t time);
msg_t chOQGetI(OutputQueue *queue);
size_t chOQWriteTimeout(OutputQueue *queue, const uint8_t *bp,
size_t n, systime_t time);
#ifdef __cplusplus
}
#endif
#endif /* CH_USE_QUEUES */
#endif /* _CHQUEUES_H_ */
/** @} */

View File

@@ -0,0 +1,76 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chregistry.h
* @brief Threads registry macros and structures.
*
* @addtogroup registry
* @{
*/
#ifndef _CHREGISTRY_H_
#define _CHREGISTRY_H_
#if CH_USE_REGISTRY
/**
* @brief Removes a thread from the registry list.
* @note This macro is not meant for use in application code.
*
* @param[in] tp thread to remove from the registry
*/
#define REG_REMOVE(tp) { \
(tp)->p_older->p_newer = (tp)->p_newer; \
(tp)->p_newer->p_older = (tp)->p_older; \
}
/**
* @brief Adds a thread to the registry list.
* @note This macro is not meant for use in application code.
*
* @param[in] tp thread to add to the registry
*/
#define REG_INSERT(tp) { \
(tp)->p_newer = (Thread *)&rlist; \
(tp)->p_older = rlist.r_older; \
(tp)->p_older->p_newer = rlist.r_older = (tp); \
}
#ifdef __cplusplus
extern "C" {
#endif
Thread *chRegFirstThread(void);
Thread *chRegNextThread(Thread *tp);
#ifdef __cplusplus
}
#endif
#endif /* CH_USE_REGISTRY */
#endif /* _CHREGISTRY_H_ */
/** @} */

View File

@@ -0,0 +1,190 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chschd.h
* @brief Scheduler macros and structures.
*
* @addtogroup scheduler
* @{
*/
#ifndef _CHSCHD_H_
#define _CHSCHD_H_
/** @brief Default thread wakeup low level message.*/
#define RDY_OK 0
/** @brief Low level message sent to a thread awakened by a timeout.*/
#define RDY_TIMEOUT -1
/** @brief Low level message sent to a thread awakened by a reset operation.*/
#define RDY_RESET -2
#define NOPRIO 0 /**< @brief Ready list header priority. */
#define IDLEPRIO 1 /**< @brief Idle thread priority. */
#define LOWPRIO 2 /**< @brief Lowest user priority. */
#define NORMALPRIO 64 /**< @brief Normal user priority. */
#define HIGHPRIO 127 /**< @brief Highest user priority. */
#define ABSPRIO 255 /**< @brief Greatest possible priority. */
/**
* @brief Zero time specification for some syscalls with a timeout
* specification.
* @note Not all functions accept @p TIME_IMMEDIATE as timeout parameter,
* see the specific function documentation.
*/
#define TIME_IMMEDIATE ((systime_t)-1)
/**
* @brief Infinite time specification for all the syscalls with a timeout
* specification.
*/
#define TIME_INFINITE ((systime_t)0)
/**
* @brief Returns the priority of the first thread on the given ready list.
*/
#define firstprio(rlp) ((rlp)->p_next->p_prio)
/**
* @extends ThreadsQueue
*
* @brief Ready list header.
*/
#if !defined(PORT_OPTIMIZED_READYLIST_STRUCT) || defined(__DOXYGEN__)
typedef struct {
ThreadsQueue r_queue; /**< @brief Threads queue. */
tprio_t r_prio; /**< @brief This field must be
initialized to zero. */
struct context r_ctx; /**< @brief Not used, present because
offsets. */
#if CH_USE_REGISTRY
Thread *r_newer; /**< @brief Newer registry element. */
Thread *r_older; /**< @brief Older registry element. */
#endif
/* End of the fields shared with the Thread structure.*/
#if CH_TIME_QUANTUM > 0
cnt_t r_preempt; /**< @brief Round robin counter. */
#endif
#ifndef CH_CURRP_REGISTER_CACHE
Thread *r_current; /**< @brief The currently running
thread. */
#endif
} ReadyList;
#endif /* !defined(PORT_OPTIMIZED_READYLIST_STRUCT) */
#if !defined(PORT_OPTIMIZED_RLIST_EXT) && !defined(__DOXYGEN__)
extern ReadyList rlist;
#endif /* !defined(PORT_OPTIMIZED_RLIST_EXT) */
/**
* @brief Current thread pointer access macro.
* @note This macro is not meant to be used in the application code but
* only from within the kernel, use the @p chThdSelf() API instead.
* @note It is forbidden to use this macro in order to change the pointer
* (currp = something), use @p setcurrp() instead.
*/
#if !defined(PORT_OPTIMIZED_CURRP) || defined(__DOXYGEN__)
#if !defined(CH_CURRP_REGISTER_CACHE) || defined(__DOXYGEN__)
#define currp rlist.r_current
#else /* defined(CH_CURRP_REGISTER_CACHE) */
register Thread *currp asm(CH_CURRP_REGISTER_CACHE);
#endif /* defined(CH_CURRP_REGISTER_CACHE) */
#endif /* !defined(PORT_OPTIMIZED_CURRP) */
/**
* @brief Current thread pointer change macro.
* @note This macro is not meant to be used in the application code but
* only from within the kernel.
*/
#if !defined(PORT_OPTIMIZED_SETCURRP) || defined(__DOXYGEN__)
#define setcurrp(tp) (currp = (tp))
#endif /* !defined(PORT_OPTIMIZED_SETCURRP) */
/*
* Scheduler APIs.
*/
#ifdef __cplusplus
extern "C" {
#endif
void scheduler_init(void);
#if !defined(PORT_OPTIMIZED_READYI)
Thread *chSchReadyI(Thread *tp);
#endif
#if !defined(PORT_OPTIMIZED_GOSLEEPS)
void chSchGoSleepS(tstate_t newstate);
#endif
#if !defined(PORT_OPTIMIZED_GOSLEEPTIMEOUTS)
msg_t chSchGoSleepTimeoutS(tstate_t newstate, systime_t time);
#endif
#if !defined(PORT_OPTIMIZED_WAKEUPS)
void chSchWakeupS(Thread *tp, msg_t msg);
#endif
#if !defined(PORT_OPTIMIZED_DORESCHEDULEI)
void chSchDoRescheduleI(void);
#endif
#if !defined(PORT_OPTIMIZED_RESCHEDULES)
void chSchRescheduleS(void);
#endif
#if !defined(PORT_OPTIMIZED_ISRESCHREQUIREDEXI)
bool_t chSchIsRescRequiredExI(void);
#endif
#ifdef __cplusplus
}
#endif
/**
* @brief Determines if the current thread must reschedule.
* @details This function returns @p TRUE if there is a ready thread with
* higher priority.
*/
#if !defined(PORT_OPTIMIZED_ISRESCHREQUIREDI) || defined(__DOXYGEN__)
#define chSchIsRescRequiredI() (firstprio(&rlist.r_queue) > currp->p_prio)
#endif /* !defined(PORT_OPTIMIZED_ISRESCHREQUIREDI) */
/**
* @brief Determines if yielding is possible.
* @details This function returns @p TRUE if there is a ready thread with
* equal or higher priority.
*/
#if !defined(PORT_OPTIMIZED_CANYIELDS) || defined(__DOXYGEN__)
#define chSchCanYieldS() (firstprio(&rlist.r_queue) >= currp->p_prio)
#endif /* !defined(PORT_OPTIMIZED_CANYIELDS) */
/**
* @brief Yields the time slot.
* @details Yields the CPU control to the next thread in the ready list with
* equal or higher priority, if any.
*/
#if !defined(PORT_OPTIMIZED_DOYIELDS) || defined(__DOXYGEN__)
#define chSchDoYieldS() { \
if (chSchCanYieldS()) \
chSchDoRescheduleI(); \
}
#endif /* !defined(PORT_OPTIMIZED_DOYIELDS) */
#endif /* _CHSCHD_H_ */
/** @} */

View File

@@ -0,0 +1,111 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chsem.h
* @brief Semaphores macros and structures.
*
* @addtogroup semaphores
* @{
*/
#ifndef _CHSEM_H_
#define _CHSEM_H_
#if CH_USE_SEMAPHORES
/**
* @brief Semaphore structure.
*/
typedef struct Semaphore {
ThreadsQueue s_queue; /**< @brief Queue of the threads sleeping
on this semaphore. */
cnt_t s_cnt; /**< @brief The semaphore counter. */
} Semaphore;
#ifdef __cplusplus
extern "C" {
#endif
void chSemInit(Semaphore *sp, cnt_t n);
void chSemReset(Semaphore *sp, cnt_t n);
void chSemResetI(Semaphore *sp, cnt_t n);
msg_t chSemWait(Semaphore *sp);
msg_t chSemWaitS(Semaphore *sp);
msg_t chSemWaitTimeout(Semaphore *sp, systime_t time);
msg_t chSemWaitTimeoutS(Semaphore *sp, systime_t time);
void chSemSignal(Semaphore *sp);
void chSemSignalI(Semaphore *sp);
#if CH_USE_SEMSW
msg_t chSemSignalWait(Semaphore *sps, Semaphore *spw);
#endif
#ifdef __cplusplus
}
#endif
/**
* @brief Data part of a static semaphore initializer.
* @details This macro should be used when statically initializing a semaphore
* that is part of a bigger structure.
*
* @param[in] name the name of the semaphore variable
* @param[in] n the counter initial value, this value must be
* non-negative
*/
#define _SEMAPHORE_DATA(name, n) {_THREADSQUEUE_DATA(name.s_queue), n}
/**
* @brief Static semaphore initializer.
* @details Statically initialized semaphores require no explicit
* initialization using @p chSemInit().
*
* @param[in] name the name of the semaphore variable
* @param[in] n the counter initial value, this value must be
* non-negative
*/
#define SEMAPHORE_DECL(name, n) Semaphore name = _SEMAPHORE_DATA(name, n)
/**
* @brief Decreases the semaphore counter.
* @details This macro can be used when the counter is known to be positive.
*/
#define chSemFastWaitI(sp) ((sp)->s_cnt--)
/**
* @brief Increases the semaphore counter.
* @details This macro can be used when the counter is known to be not negative.
*/
#define chSemFastSignalI(sp) ((sp)->s_cnt++)
/**
* @brief Returns the semaphore counter current value.
*/
#define chSemGetCounterI(sp) ((sp)->s_cnt)
#endif /* CH_USE_SEMAPHORES */
#endif /* _CHSEM_H_ */
/** @} */

View File

@@ -0,0 +1,111 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chstreams.h
* @brief Data streams.
* @details This header defines abstract interfaces useful to access generic
* data streams in a standardized way.
*
* @addtogroup data_streams
* @details This module define an abstract interface for generic data streams.
* Note that no code is present, streams are just abstract interfaces
* like structures, you should look at the systems as to a set of
* abstract C++ classes (even if written in C). This system has the
* advantage to make the access to streams independent from the
* implementation logic.<br>
* The stream interface can be used as base class for high level
* object types such as files, sockets, serial ports, pipes etc.
* @{
*/
#ifndef _CHSTREAMS_H_
#define _CHSTREAMS_H_
/**
* @brief BaseSequentialStream specific methods.
*/
#define _base_sequential_stream_methods \
/* Stream write buffer method.*/ \
size_t (*write)(void *instance, const uint8_t *bp, size_t n); \
/* Stream read buffer method.*/ \
size_t (*read)(void *instance, uint8_t *bp, size_t n);
/**
* @brief @p BaseSequentialStream specific data.
* @note It is empty because @p BaseSequentialStream is only an interface
* without implementation.
*/
#define _base_sequential_stream_data
/**
* @brief @p BaseSequentialStream virtual methods table.
*/
struct BaseSequentialStreamVMT {
_base_sequential_stream_methods
};
/**
* @brief Base stream class.
* @details This class represents a generic blocking unbuffered sequential
* data stream.
*/
typedef struct {
/** @brief Virtual Methods Table.*/
const struct BaseSequentialStreamVMT *vmt;
_base_sequential_stream_data
} BaseSequentialStream;
/**
* @brief Sequential Stream write.
* @details The function writes data from a buffer to a stream.
*
* @param[in] ip pointer to a @p BaseSequentialStream or derived class
* @param[in] bp pointer to the data buffer
* @param[in] n the maximum amount of data to be transferred
* @return The number of bytes transferred. The return value can
* be less than the specified number of bytes if the
* stream reaches a physical end of file and cannot be
* extended.
*/
#define chSequentialStreamWrite(ip, bp, n) ((ip)->vmt->write(ip, bp, n))
/**
* @brief Sequential Stream read.
* @details The function reads data from a stream into a buffer.
*
* @param[in] ip pointer to a @p BaseSequentialStream or derived class
* @param[out] bp pointer to the data buffer
* @param[in] n the maximum amount of data to be transferred
* @return The number of bytes transferred. The return value can
* be less than the specified number of bytes if the
* stream reaches the end of the available data.
*/
#define chSequentialStreamRead(ip, bp, n) ((ip)->vmt->read(ip, bp, n))
#endif /* _CHSTREAMS_H_ */
/** @} */

View File

@@ -0,0 +1,193 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chsys.h
* @brief System related macros and structures.
*
* @addtogroup system
* @{
*/
#ifndef _CHSYS_H_
#define _CHSYS_H_
/**
* @brief Halts the system.
* @details This function is invoked by the operating system when an
* unrecoverable error is detected, as example because a programming
* error in the application code that triggers an assertion while
* in debug mode.
*/
#define chSysHalt() port_halt()
/**
* @brief Performs a context switch.
*
* @param[in] ntp the thread to be switched in
* @param[in] otp the thread to be switched out
*/
#define chSysSwitchI(ntp, otp) port_switch(ntp, otp)
/**
* @brief Raises the system interrupt priority mask to the maximum level.
* @details All the maskable interrupt sources are disabled regardless their
* hardware priority.
* @note The implementation is architecture dependent, it may just disable
* the interrupts or be exactly equivalent to @p chSysDisable().
* @note Do not invoke this API from within a kernel lock.
*/
#define chSysDisable() port_disable()
/**
* @brief Raises the system interrupt priority mask to system level.
* @details The interrupt sources that should not be able to preempt the kernel
* are disabled, interrupt sources with higher priority are still
* enabled.
* @note The implementation is architecture dependent, it may just disable
* the interrupts.
* @note Do not invoke this API from within a kernel lock.
* @note This API is no replacement for @p chSysLock(), the @p chSysLock()
* could do more than just disable the interrupts.
*/
#define chSysSuspend() port_suspend()
/**
* @brief Lowers the system interrupt priority mask to user level.
* @details All the interrupt sources are enabled.
* @note The implementation is architecture dependent, it may just enable
* the interrupts.
* @note Do not invoke this API from within a kernel lock.
* @note This API is no replacement for @p chSysUnlock(), the
* @p chSysUnlock() could do more than just enable the interrupts.
*/
#define chSysEnable() port_enable()
/**
* @brief Enters the kernel lock mode.
* @note The use of kernel lock mode is not recommended in the user code,
* it is a better idea to use the semaphores or mutexes instead.
* @see CH_USE_NESTED_LOCKS
*/
#if CH_USE_NESTED_LOCKS || defined(__DOXYGEN__)
#if CH_OPTIMIZE_SPEED || defined(__DOXYGEN__)
#define chSysLock() { \
if (currp->p_locks++ == 0) \
port_lock(); \
}
#endif /* CH_OPTIMIZE_SPEED */
#else /* !CH_USE_NESTED_LOCKS */
#define chSysLock() port_lock()
#endif /* !CH_USE_NESTED_LOCKS */
/**
* @brief Leaves the kernel lock mode.
* @note The use of kernel lock mode is not recommended in the user code,
* it is a better idea to use the semaphores or mutexes instead.
* @see CH_USE_NESTED_LOCKS
*/
#if CH_USE_NESTED_LOCKS || defined(__DOXYGEN__)
#if CH_OPTIMIZE_SPEED || defined(__DOXYGEN__)
#define chSysUnlock() { \
if (--currp->p_locks == 0) \
port_unlock(); \
}
#endif /* CH_OPTIMIZE_SPEED */
#else /* !CH_USE_NESTED_LOCKS */
#define chSysUnlock() port_unlock()
#endif /* !CH_USE_NESTED_LOCKS */
/**
* @brief Enters the kernel lock mode from within an interrupt handler.
* @note This API may do nothing on some architectures, it is required
* because on ports that support preemptable interrupt handlers
* it is required to raise the interrupt mask to the same level of
* the system mutual exclusion zone.<br>
* It is good practice to invoke this API before invoking any I-class
* syscall from an interrupt handler.
* @note This API must be invoked exclusively from interrupt handlers.
*/
#define chSysLockFromIsr() port_lock_from_isr()
/**
* @brief Leaves the kernel lock mode from within an interrupt handler.
*
* @note This API may do nothing on some architectures, it is required
* because on ports that support preemptable interrupt handlers
* it is required to raise the interrupt mask to the same level of
* the system mutual exclusion zone.<br>
* It is good practice to invoke this API after invoking any I-class
* syscall from an interrupt handler.
* @note This API must be invoked exclusively from interrupt handlers.
*/
#define chSysUnlockFromIsr() port_unlock_from_isr()
/**
* @brief IRQ handler enter code.
* @note Usually IRQ handlers functions are also declared naked.
* @note On some architectures this macro can be empty.
*/
#define CH_IRQ_PROLOGUE() PORT_IRQ_PROLOGUE()
/**
* @brief IRQ handler exit code.
* @note Usually IRQ handlers function are also declared naked.
* @note This macro usually performs the final reschedule by using
* @p chSchRescRequiredI() and @p chSchDoRescheduleI().
*/
#define CH_IRQ_EPILOGUE() PORT_IRQ_EPILOGUE()
/**
* @brief Standard normal IRQ handler declaration.
* @note @p id can be a function name or a vector number depending on the
* port implementation.
*/
#define CH_IRQ_HANDLER(id) PORT_IRQ_HANDLER(id)
/**
* @brief Standard fast IRQ handler declaration.
* @note @p id can be a function name or a vector number depending on the
* port implementation.
* @note Not all architectures support fast interrupts.
*/
#define CH_FAST_IRQ_HANDLER(id) PORT_FAST_IRQ_HANDLER(id)
#ifdef __cplusplus
extern "C" {
#endif
void chSysInit(void);
void chSysTimerHandlerI(void);
#if CH_USE_NESTED_LOCKS && !CH_OPTIMIZE_SPEED
void chSysLock(void);
void chSysUnlock(void);
#endif /* CH_USE_NESTED_LOCKS && !CH_OPTIMIZE_SPEED */
#ifdef __cplusplus
}
#endif
#endif /* _CHSYS_H_ */
/** @} */

View File

@@ -0,0 +1,337 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chthreads.h
* @brief Threads macros and structures.
*
* @addtogroup threads
* @{
*/
#ifndef _CHTHREADS_H_
#define _CHTHREADS_H_
/*
* Module dependencies check.
*/
#if CH_USE_DYNAMIC && !CH_USE_WAITEXIT
#error "CH_USE_DYNAMIC requires CH_USE_WAITEXIT"
#endif
#if CH_USE_DYNAMIC && !CH_USE_HEAP && !CH_USE_MEMPOOLS
#error "CH_USE_DYNAMIC requires CH_USE_HEAP and/or CH_USE_MEMPOOLS"
#endif
/**
* @extends ThreadsQueue
*
* @brief Structure representing a thread.
* @note Not all the listed fields are always needed, by switching off some
* not needed ChibiOS/RT subsystems it is possible to save RAM space
* by shrinking the @p Thread structure.
*/
struct Thread {
Thread *p_next; /**< @brief Next in the list/queue. */
/* End of the fields shared with the ThreadsList structure. */
Thread *p_prev; /**< @brief Previous in the queue. */
/* End of the fields shared with the ThreadsQueue structure. */
tprio_t p_prio; /**< @brief Thread priority. */
struct context p_ctx; /**< @brief Processor context. */
#if CH_USE_REGISTRY
Thread *p_newer; /**< @brief Newer registry element. */
Thread *p_older; /**< @brief Older registry element. */
#endif
/* End of the fields shared with the ReadyList structure. */
/**
* @brief Current thread state.
*/
tstate_t p_state;
/**
* @brief Various thread flags.
*/
tmode_t p_flags;
#if CH_USE_DYNAMIC
/**
* @brief References to this thread.
*/
trefs_t p_refs;
#endif
#if CH_USE_NESTED_LOCKS
/**
* @brief Number of nested locks.
*/
cnt_t p_locks;
#endif
#if CH_DBG_THREADS_PROFILING
/**
* @brief Thread consumed time in ticks.
* @note This field can overflow.
*/
volatile systime_t p_time;
#endif
/**
* @brief State-specific fields.
* @note All the fields declared in this union are only valid in the
* specified state or condition and are thus volatile.
*/
union {
/**
* @brief Thread wakeup code.
* @note This field contains the low level message sent to the thread
* by the waking thread or interrupt handler. The value is valid
* after exiting the @p chSchWakeupS() function.
*/
msg_t rdymsg;
/**
* @brief Thread exit code.
* @note The thread termination code is stored in this field in order
* to be retrieved by the thread performing a @p chThdWait() on
* this thread.
*/
msg_t exitcode;
/**
* @brief Pointer to a generic "wait" object.
* @note This field is used to get a generic pointer to a synchronization
* object and is valid when the thread is in one of the wait
* states.
*/
void *wtobjp;
#if CH_USE_EVENTS
/**
* @brief Enabled events mask.
* @note This field is only valied while the thread is in the
* @p THD_STATE_WTOREVT or @p THD_STATE_WTANDEVT states.
*/
eventmask_t ewmask;
#endif
} p_u;
#if CH_USE_WAITEXIT
/**
* @brief Termination waiting list.
*/
ThreadsList p_waiting;
#endif
#if CH_USE_MESSAGES
/**
* @brief Messages queue.
*/
ThreadsQueue p_msgqueue;
/**
* @brief Thread message.
*/
msg_t p_msg;
#endif
#if CH_USE_EVENTS
/**
* @brief Pending events mask.
*/
eventmask_t p_epending;
#endif
#if CH_USE_MUTEXES
/**
* @brief List of the mutexes owned by this thread.
* @note The list is terminated by a @p NULL in this field.
*/
Mutex *p_mtxlist;
/**
* @brief Thread's own, non-inherited, priority.
*/
tprio_t p_realprio;
#endif
#if CH_USE_DYNAMIC && CH_USE_MEMPOOLS
/**
* @brief Memory Pool where the thread workspace is returned.
*/
void *p_mpool;
#endif
/* Extra fields defined in chconf.h.*/
THREAD_EXT_FIELDS
};
/** @brief Thread state: Ready to run, waiting on the ready list.*/
#define THD_STATE_READY 0
/** @brief Thread state: Currently running.*/
#define THD_STATE_CURRENT 1
/** @brief Thread state: Thread created in suspended state.*/
#define THD_STATE_SUSPENDED 2
/** @brief Thread state: Waiting on a semaphore.*/
#define THD_STATE_WTSEM 3
/** @brief Thread state: Waiting on a mutex.*/
#define THD_STATE_WTMTX 4
/** @brief Thread state: Waiting in @p chCondWait().*/
#define THD_STATE_WTCOND 5
/** @brief Thread state: Waiting in @p chThdSleep() or @p chThdSleepUntil().*/
#define THD_STATE_SLEEPING 6
/** @brief Thread state: Waiting in @p chThdWait().*/
#define THD_STATE_WTEXIT 7
/** @brief Thread state: Waiting in @p chEvtWaitXXX().*/
#define THD_STATE_WTOREVT 8
/** @brief Thread state: Waiting in @p chEvtWaitAllTimeout().*/
#define THD_STATE_WTANDEVT 9
/** @brief Thread state: Waiting in @p chMsgSend().*/
#define THD_STATE_SNDMSG 10
/** @brief Thread state: Waiting in @p chMsgWait().*/
#define THD_STATE_WTMSG 11
/** @brief Thread state: After termination.*/
#define THD_STATE_FINAL 12
/*
* Various flags into the thread p_flags field.
*/
#define THD_MEM_MODE_MASK 3 /**< @brief Thread memory mode mask. */
#define THD_MEM_MODE_STATIC 0 /**< @brief Thread memory mode: static. */
#define THD_MEM_MODE_HEAP 1 /**< @brief Thread memory mode: heap. */
#define THD_MEM_MODE_MEMPOOL 2 /**< @brief Thread memory mode: pool. */
#define THD_TERMINATE 4 /**< @brief Termination requested. */
/** @brief Thread function.*/
typedef msg_t (*tfunc_t)(void *);
/*
* Threads APIs.
*/
#ifdef __cplusplus
extern "C" {
#endif
Thread *init_thread(Thread *tp, tprio_t prio);
Thread *chThdCreateI(void *wsp, size_t size,
tprio_t prio, tfunc_t pf, void *arg);
Thread *chThdCreateStatic(void *wsp, size_t size,
tprio_t prio, tfunc_t pf, void *arg);
#if CH_USE_DYNAMIC && CH_USE_WAITEXIT && CH_USE_HEAP
Thread *chThdCreateFromHeap(MemoryHeap *heapp, size_t size,
tprio_t prio, tfunc_t pf, void *arg);
#endif
#if CH_USE_DYNAMIC && CH_USE_WAITEXIT && CH_USE_MEMPOOLS
Thread *chThdCreateFromMemoryPool(MemoryPool *mp, tprio_t prio,
tfunc_t pf, void *arg);
#endif
tprio_t chThdSetPriority(tprio_t newprio);
Thread *chThdResume(Thread *tp);
void chThdTerminate(Thread *tp);
void chThdSleep(systime_t time);
void chThdSleepUntil(systime_t time);
void chThdYield(void);
void chThdExit(msg_t msg);
#if CH_USE_DYNAMIC
Thread *chThdAddRef(Thread *tp);
void chThdRelease(Thread *tp);
#endif
#if CH_USE_WAITEXIT
msg_t chThdWait(Thread *tp);
#endif
#ifdef __cplusplus
}
#endif
/**
* @brief Returns a pointer to the current @p Thread.
*/
#define chThdSelf() currp
/**
* @brief Returns the current thread priority.
*/
#define chThdGetPriority() (currp->p_prio)
/**
* @brief Returns the pointer to the @p Thread local storage area, if any.
*/
#define chThdLS() (void *)(currp + 1)
/**
* @brief Verifies if the specified thread is in the @p THD_STATE_FINAL state.
*
* @param[in] tp the pointer to the thread
* @retval TRUE thread terminated.
* @retval FALSE thread not terminated.
*/
#define chThdTerminated(tp) ((tp)->p_state == THD_STATE_FINAL)
/**
* @brief Verifies if the current thread has a termination request pending.
*
* @retval TRUE termination request pended.
* @retval FALSE termination request not pended.
*/
#define chThdShouldTerminate() (currp->p_flags & THD_TERMINATE)
/**
* @brief Resumes a thread created with @p chThdInit().
*
* @param[in] tp the pointer to the thread
*/
#define chThdResumeI(tp) chSchReadyI(tp)
/**
* @brief Suspends the invoking thread for the specified time.
*
* @param[in] time the delay in system ticks, the special values are
* handled as follow:
* - @a TIME_INFINITE the thread enters an infinite sleep
* state.
* - @a TIME_IMMEDIATE this value is accepted but
* interpreted as a normal time specification not as
* an immediate timeout specification.
* .
*/
#define chThdSleepS(time) chSchGoSleepTimeoutS(THD_STATE_SLEEPING, time)
/**
* @brief Delays the invoking thread for the specified number of seconds.
* @note The specified time is rounded up to a value allowed by the real
* system clock.
* @note The maximum specified value is implementation dependent.
*
* @param[in] sec the time in seconds
*/
#define chThdSleepSeconds(sec) chThdSleep(S2ST(sec))
/**
* @brief Delays the invoking thread for the specified number of
* milliseconds.
* @note The specified time is rounded up to a value allowed by the real
* system clock.
* @note The maximum specified value is implementation dependent.
*
* @param[in] msec the time in milliseconds
*/
#define chThdSleepMilliseconds(msec) chThdSleep(MS2ST(msec))
/**
* @brief Delays the invoking thread for the specified number of
* microseconds.
* @note The specified time is rounded up to a value allowed by the real
* system clock.
* @note The maximum specified value is implementation dependent.
*
* @param[in] usec the time in microseconds
*/
#define chThdSleepMicroseconds(usec) chThdSleep(US2ST(usec))
#endif /* _CHTHREADS_H_ */
/** @} */

View File

@@ -0,0 +1,154 @@
/*
ChibiOS/RT - Copyright (C) 2006,2007,2008,2009,2010 Giovanni Di Sirio.
This file is part of ChibiOS/RT.
ChibiOS/RT is free software; you can redistribute it and/or modify
it under the terms of the GNU General Public License as published by
the Free Software Foundation; either version 3 of the License, or
(at your option) any later version.
ChibiOS/RT 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 this program. If not, see <http://www.gnu.org/licenses/>.
---
A special exception to the GPL can be applied should you wish to distribute
a combined work that includes ChibiOS/RT, without being obliged to provide
the source code for any proprietary components. See the file exception.txt
for full details of how and when the exception can be applied.
*/
/**
* @file chvt.h
* @brief Time macros and structures.
*
* @addtogroup time
* @{
*/
#ifndef _CHVT_H_
#define _CHVT_H_
/**
* @brief Time conversion utility.
* @details Converts from seconds to system ticks number.
* @note The result is rounded upward to the next tick boundary.
*/
#define S2ST(sec) ((systime_t)((sec) * CH_FREQUENCY))
/**
* @brief Time conversion utility.
* @details Converts from milliseconds to system ticks number.
* @note The result is rounded upward to the next tick boundary.
*/
#define MS2ST(msec) ((systime_t)(((((msec) - 1L) * CH_FREQUENCY) / 1000L) + 1L))
/**
* @brief Time conversion utility.
* @details Converts from microseconds to system ticks number.
* @note The result is rounded upward to the next tick boundary.
*/
#define US2ST(usec) ((systime_t)(((((usec) - 1L) * CH_FREQUENCY) / 1000000L) + 1L))
/**
* @brief Virtual Timer callback function.
*/
typedef void (*vtfunc_t)(void *);
/**
* @brief Virtual Timer structure type.
*/
typedef struct VirtualTimer VirtualTimer;
/**
* @extends DeltaList
*
* @brief Virtual Timer descriptor structure.
*/
struct VirtualTimer {
VirtualTimer *vt_next; /**< @brief Next timer in the delta
list. */
VirtualTimer *vt_prev; /**< @brief Previous timer in the delta
list. */
systime_t vt_time; /**< @brief Time delta before timeout. */
vtfunc_t vt_func; /**< @brief Timer callback function
pointer. */
void *vt_par; /**< @brief Timer callback function
parameter. */
};
/**
* @brief Virtual timers list header.
* @note The delta list is implemented as a double link bidirectional list
* in order to make the unlink time constant, the reset of a virtual
* timer is often used in the code.
*/
typedef struct {
VirtualTimer *vt_next; /**< @brief Next timer in the delta
list. */
VirtualTimer *vt_prev; /**< @brief Last timer in the delta
list. */
systime_t vt_time; /**< @brief Must be initialized to -1. */
volatile systime_t vt_systime; /**< @brief System Time counter. */
} VTList;
extern VTList vtlist;
/**
* @brief Virtual timers ticker.
*/
#define chVTDoTickI() { \
vtlist.vt_systime++; \
if (&vtlist != (VTList *)vtlist.vt_next) { \
VirtualTimer *vtp; \
\
--vtlist.vt_next->vt_time; \
while (!(vtp = vtlist.vt_next)->vt_time) { \
vtfunc_t fn = vtp->vt_func; \
vtp->vt_func = (vtfunc_t)NULL; \
vtp->vt_next->vt_prev = (void *)&vtlist; \
(&vtlist)->vt_next = vtp->vt_next; \
fn(vtp->vt_par); \
} \
} \
}
/*
* Virtual Timers APIs.
*/
#ifdef __cplusplus
extern "C" {
#endif
void vt_init(void);
void chVTSetI(VirtualTimer *vtp, systime_t time, vtfunc_t vtfunc, void *par);
void chVTResetI(VirtualTimer *vtp);
bool_t chTimeIsWithin(systime_t start, systime_t end);
#ifdef __cplusplus
}
#endif
/**
* @brief Returns TRUE if the speciified timer is armed.
*/
#define chVTIsArmedI(vtp) ((vtp)->vt_func != NULL)
/**
* @brief Current system time.
* @details Returns the number of system ticks since the @p chSysInit()
* invocation.
* @note The counter can reach its maximum and then restart from zero.
* @note This function is designed to work with the @p chThdSleepUntil().
*
* @return The system time in ticks.r
*/
#define chTimeNow() (vtlist.vt_systime)
#endif /* _CHVT_H_ */
/** @} */