C++ wrapper prototype, not complete yet.

git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@5008 35acf78f-673a-0410-8e92-d51de3d6d3f4
master
gdisirio 2013-01-01 15:42:44 +00:00
parent 6ffd46f608
commit 1be8fe145c
3 changed files with 445 additions and 248 deletions

View File

@ -24,6 +24,7 @@
#include "evtimer.h" #include "evtimer.h"
using namespace chibios_rt; using namespace chibios_rt;
#if 0
/* /*
* LED blink sequences. * LED blink sequences.
@ -130,16 +131,17 @@ static void TimerHandler(eventid_t id) {
tester.Wait(); tester.Wait();
}; };
} }
#endif
/* /*
* Application entry point. * Application entry point.
*/ */
int main(void) { int main(void) {
static const evhandler_t evhndl[] = { /* static const evhandler_t evhndl[] = {
TimerHandler TimerHandler
}; };
static EvTimer evt; static EvTimer evt;
struct EventListener el0; struct EventListener el0;*/
/* /*
* System initializations. * System initializations.
@ -149,28 +151,28 @@ int main(void) {
* RTOS is active. * RTOS is active.
*/ */
halInit(); halInit();
System::Init(); System::init();
/* /*
* Activates the serial driver 2 using the driver default configuration. * Activates the serial driver 2 using the driver default configuration.
*/ */
sdStart(&SD2, NULL); sdStart(&SD2, NULL);
/*
evtInit(&evt, 500); // Initializes an event timer. evtInit(&evt, 500); // Initializes an event timer.
evtStart(&evt); // Starts the event timer. evtStart(&evt); // Starts the event timer.
chEvtRegister(&evt.et_es, &el0, 0); // Registers a listener on the source. chEvtRegister(&evt.et_es, &el0, 0); // Registers a listener on the source.
*/
/* /*
* Starts several instances of the SequencerThread class, each one operating * Starts several instances of the SequencerThread class, each one operating
* on a different LED. * on a different LED.
*/ */
SequencerThread blinker1(LED1_sequence); // SequencerThread blinker1(LED1_sequence);
/* /*
* Serves timer events. * Serves timer events.
*/ */
while (true) // while (true)
Event::Dispatch(evhndl, Event::WaitOne(ALL_EVENTS)); // Event::Dispatch(evhndl, Event::WaitOne(ALL_EVENTS));
return 0; return 0;
} }

View File

@ -32,22 +32,22 @@ namespace chibios_rt {
/*------------------------------------------------------------------------* /*------------------------------------------------------------------------*
* chibios_rt::System * * chibios_rt::System *
*------------------------------------------------------------------------*/ *------------------------------------------------------------------------*/
void System::Init(void) { void System::init(void) {
chSysInit(); chSysInit();
} }
void System::Lock(void) { void System::lock(void) {
chSysLock(); chSysLock();
} }
void System::Unlock(void) { void System::unlock(void) {
chSysUnlock(); chSysUnlock();
} }
systime_t System::GetTime(void) { systime_t System::getTime(void) {
return chTimeNow(); return chTimeNow();
} }
@ -55,108 +55,170 @@ namespace chibios_rt {
/*------------------------------------------------------------------------* /*------------------------------------------------------------------------*
* chibios_rt::Timer * * chibios_rt::Timer *
*------------------------------------------------------------------------*/ *------------------------------------------------------------------------*/
void Timer::Set(systime_t time, vtfunc_t vtfunc, void *par) { void Timer::setI(systime_t time, vtfunc_t vtfunc, void *par) {
chVTSetI(&timer, time, vtfunc, par); chVTSetI(&timer_ref, time, vtfunc, par);
} }
void Timer::Reset() { void Timer::resetI() {
chVTResetI(&timer); if (chVTIsArmedI(&timer_ref))
chVTResetI(&timer_ref);
} }
bool Timer::IsArmed(void) { bool Timer::isArmedI(void) {
return chVTIsArmedI(&timer); return (bool)chVTIsArmedI(&timer_ref);
} }
/*------------------------------------------------------------------------* /*------------------------------------------------------------------------*
* chibios_rt::BaseThread * * chibios_rt::ThreadReference *
*------------------------------------------------------------------------*/ *------------------------------------------------------------------------*/
static msg_t thdstart(void *arg) { msg_t ThreadReference::suspend(void) {
msg_t msg;
return ((BaseThread *)arg)->Main(); chSysLock();
chDbgAssert(thread_ref != NULL,
"ThreadReference, #1",
"already referenced");
thread_ref = chThdSelf();
chSchGoSleepS(THD_STATE_SUSPENDED);
msg = thread_ref->p_u.rdymsg;
chSysUnlock();
return msg;
} }
BaseThread::BaseThread(void *workspace, size_t wsize, tprio_t prio) { msg_t ThreadReference::suspendS(void) {
thread_ref = chThdCreateStatic(workspace, wsize, prio, thdstart, this); chDbgAssert(thread_ref == NULL,
"ThreadReference, #2",
"already referenced");
thread_ref = chThdSelf();
chSchGoSleepS(THD_STATE_SUSPENDED);
return thread_ref->p_u.rdymsg;
} }
void BaseThread::Exit(msg_t msg) { void ThreadReference::resume(msg_t msg) {
chThdExit(msg); chSysLock()
chDbgAssert(thread_ref != NULL,
"ThreadReference, #3",
"not referenced");
if (thread_ref) {
Thread *tp = thread_ref;
thread_ref = NULL;
chSchWakeupS(tp, msg);
} }
#if CH_USE_WAITEXIT chSysUnlock();
msg_t BaseThread::Wait(void) {
return chThdWait(thread_ref);
}
#endif /* CH_USE_WAITEXIT */
void BaseThread::SetPriority(tprio_t newprio) {
chThdSetPriority(newprio);
} }
void BaseThread::Resume(void) { void ThreadReference::resumeI(msg_t msg) {
chThdResume(thread_ref); chDbgAssert(thread_ref != NULL,
"ThreadReference, #4",
"not referenced");
if (thread_ref) {
Thread *tp = thread_ref;
thread_ref = NULL;
tp->p_msg = msg;
chSchReadyI(tp);
}
} }
void BaseThread::Terminate(void) { void ThreadReference::requestTerminate(void) {
chThdTerminate(thread_ref); chThdTerminate(thread_ref);
} }
void BaseThread::Sleep(systime_t n) { #if CH_USE_WAITEXIT || defined(__DOXYGEN__)
msg_t ThreadReference::wait(void) {
chThdSleep(n); chDbgAssert(thread_ref != NULL,
"ThreadReference, #5",
"not referenced");
msg_t msg = chThdWait(thread_ref);
thread_ref = NULL;
return msg;
}
#endif /* CH_USE_WAITEXIT */
#if CH_USE_MESSAGES || defined(__DOXYGEN__)
msg_t ThreadReference::sendMessage(msg_t msg) {
chDbgAssert(thread_ref != NULL,
"ThreadReference, #6",
"not referenced");
return chMsgSend(thread_ref, msg);
} }
void BaseThread::SleepUntil(systime_t time) { bool ThreadReference::isPendingMessage(void) {
return (bool)chMsgIsPendingI(thread_ref);
}
#endif /* CH_USE_MESSAGES */
#if CH_USE_DYNAMIC
#endif /* CH_USE_DYNAMIC */
/*------------------------------------------------------------------------*
* chibios_rt::BaseThread *
*------------------------------------------------------------------------*/
BaseThread::BaseThread() : ThreadReference(NULL) {
}
msg_t _thd_start(void *arg) {
return ((BaseThread *)arg)->Main();
}
void BaseThread::exit(msg_t msg) {
chThdExit(msg);
}
tprio_t BaseThread::setPriority(tprio_t newprio) {
return chThdSetPriority(newprio);
}
bool BaseThread::shouldTerminate(void) {
return (bool)chThdShouldTerminate();
}
void BaseThread::sleep(systime_t interval){
chThdSleep(interval);
}
void BaseThread::sleepUntil(systime_t time) {
chThdSleepUntil(time); chThdSleepUntil(time);
} }
#if CH_USE_MESSAGES #if CH_USE_MESSAGES
msg_t BaseThread::SendMessage(::Thread* tp, msg_t msg) { msg_t BaseThread::getMessage(ThreadReference* trp) {
return chMsgSend(tp, msg); return chMsgGet(trp->thread_ref);
} }
msg_t BaseThread::SendMessage(msg_t msg) { void BaseThread::releaseMessage(ThreadReference* trp, msg_t msg) {
return chMsgSend(thread_ref, msg); chMsgRelease(trp->thread_ref, msg);
}
Thread *BaseThread::WaitMessage(void) {
return chMsgWait();
}
msg_t BaseThread::GetMessage(Thread* tp) {
return chMsgGet(tp);
}
void BaseThread::ReleaseMessage(Thread* tp, msg_t msg) {
chMsgRelease(tp, msg);
}
bool BaseThread::IsPendingMessage(void) {
return chMsgIsPendingI(currp);
} }
#endif /* CH_USE_MESSAGES */ #endif /* CH_USE_MESSAGES */
msg_t BaseThread::Main(void) {
return 0;
}
#if CH_USE_SEMAPHORES #if CH_USE_SEMAPHORES
/*------------------------------------------------------------------------* /*------------------------------------------------------------------------*
* chibios_rt::Semaphore * * chibios_rt::Semaphore *
@ -166,28 +228,28 @@ namespace chibios_rt {
chSemInit(&sem, n); chSemInit(&sem, n);
} }
void Semaphore::Reset(cnt_t n) { void Semaphore::reset(cnt_t n) {
chSemReset(&sem, n); chSemReset(&sem, n);
} }
msg_t Semaphore::Wait(void) { msg_t Semaphore::wait(void) {
return chSemWait(&sem); return chSemWait(&sem);
} }
msg_t Semaphore::WaitTimeout(systime_t time) { msg_t Semaphore::waitTimeout(systime_t time) {
return chSemWaitTimeout(&sem, time); return chSemWaitTimeout(&sem, time);
} }
void Semaphore::Signal(void) { void Semaphore::signal(void) {
chSemSignal(&sem); chSemSignal(&sem);
} }
#if CH_USE_SEMSW #if CH_USE_SEMSW
msg_t Semaphore::SignalWait(Semaphore *ssem, Semaphore *wsem) { msg_t Semaphore::signalWait(Semaphore *ssem, Semaphore *wsem) {
return chSemSignalWait(&ssem->sem, &wsem->sem); return chSemSignalWait(&ssem->sem, &wsem->sem);
} }
@ -203,22 +265,22 @@ namespace chibios_rt {
chMtxInit(&mutex); chMtxInit(&mutex);
} }
bool Mutex::TryLock(void) { bool Mutex::tryLock(void) {
return chMtxTryLock(&mutex); return chMtxTryLock(&mutex);
} }
void Mutex::Lock(void) { void Mutex::lock(void) {
chMtxLock(&mutex); chMtxLock(&mutex);
} }
void Mutex::Unlock(void) { void Mutex::unlock(void) {
chMtxUnlock(); chMtxUnlock();
} }
void UnlockAll(void) { void Mutex::unlockAll(void) {
chMtxUnlockAll(); chMtxUnlockAll();
} }
@ -232,23 +294,23 @@ namespace chibios_rt {
chCondInit(&condvar); chCondInit(&condvar);
} }
void CondVar::Signal(void) { void CondVar::signal(void) {
chCondSignal(&condvar); chCondSignal(&condvar);
} }
void CondVar::Broadcast(void) { void CondVar::broadcast(void) {
chCondBroadcast(&condvar); chCondBroadcast(&condvar);
} }
msg_t CondVar::Wait(void) { msg_t CondVar::wait(void) {
return chCondWait(&condvar); return chCondWait(&condvar);
} }
#if CH_USE_CONDVARS_TIMEOUT #if CH_USE_CONDVARS_TIMEOUT
msg_t CondVar::WaitTimeout(systime_t time) { msg_t CondVar::waitTimeout(systime_t time) {
return chCondWaitTimeout(&condvar, time); return chCondWaitTimeout(&condvar, time);
} }
@ -265,73 +327,73 @@ namespace chibios_rt {
chEvtInit(&event); chEvtInit(&event);
} }
void Event::Register(EventListener *elp, eventid_t eid) { void Event::registerOne(EventListener *elp, eventid_t eid) {
chEvtRegister(&event,elp, eid); chEvtRegister(&event,elp, eid);
} }
void Event::RegisterMask(EventListener *elp, eventmask_t emask) { void Event::registerMask(EventListener *elp, eventmask_t emask) {
chEvtRegisterMask(&event,elp, emask); chEvtRegisterMask(&event,elp, emask);
} }
void Event::Unregister(EventListener *elp) { void Event::unregister(EventListener *elp) {
chEvtUnregister(&event, elp); chEvtUnregister(&event, elp);
} }
void Event::BroadcastFlags(flagsmask_t flags) { void Event::broadcastFlags(flagsmask_t flags) {
chEvtBroadcastFlags(&event, flags); chEvtBroadcastFlags(&event, flags);
} }
flagsmask_t GetAndClearFlags(EventListener *elp) { flagsmask_t Event::getAndClearFlags(EventListener *elp) {
return chEvtGetAndClearFlags(elp); return chEvtGetAndClearFlags(elp);
} }
eventmask_t Event::GetAndClearEvents(eventmask_t mask) { eventmask_t Event::getAndClearEvents(eventmask_t mask) {
return chEvtGetAndClearEvents(mask); return chEvtGetAndClearEvents(mask);
} }
eventmask_t Event::AddEvents(eventmask_t mask) { eventmask_t Event::addEvents(eventmask_t mask) {
return chEvtAddEvents(mask); return chEvtAddEvents(mask);
} }
void Event::Dispatch(const evhandler_t handlers[], eventmask_t mask) { void Event::dispatch(const evhandler_t handlers[], eventmask_t mask) {
chEvtDispatch(handlers, mask); chEvtDispatch(handlers, mask);
} }
eventmask_t Event::WaitOne(eventmask_t ewmask) { eventmask_t Event::waitOne(eventmask_t ewmask) {
return chEvtWaitOne(ewmask); return chEvtWaitOne(ewmask);
} }
eventmask_t Event::WaitAny(eventmask_t ewmask) { eventmask_t Event::waitAny(eventmask_t ewmask) {
return chEvtWaitAny(ewmask); return chEvtWaitAny(ewmask);
} }
eventmask_t Event::WaitAll(eventmask_t ewmask) { eventmask_t Event::waitAll(eventmask_t ewmask) {
return chEvtWaitAll(ewmask); return chEvtWaitAll(ewmask);
} }
#if CH_USE_EVENTS_TIMEOUT #if CH_USE_EVENTS_TIMEOUT
eventmask_t Event::WaitOneTimeout(eventmask_t ewmask, systime_t time) { eventmask_t Event::waitOneTimeout(eventmask_t ewmask, systime_t time) {
return chEvtWaitOneTimeout(ewmask, time); return chEvtWaitOneTimeout(ewmask, time);
} }
eventmask_t Event::WaitAnyTimeout(eventmask_t ewmask, systime_t time) { eventmask_t Event::waitAnyTimeout(eventmask_t ewmask, systime_t time) {
return chEvtWaitAnyTimeout(ewmask, time); return chEvtWaitAnyTimeout(ewmask, time);
} }
eventmask_t Event::WaitAllTimeout(eventmask_t ewmask, systime_t time) { eventmask_t Event::waitAllTimeout(eventmask_t ewmask, systime_t time) {
return chEvtWaitAllTimeout(ewmask, time); return chEvtWaitAllTimeout(ewmask, time);
} }

View File

@ -33,6 +33,9 @@
namespace chibios_rt { namespace chibios_rt {
/*------------------------------------------------------------------------*
* chibios_rt::System *
*------------------------------------------------------------------------*/
/** /**
* @brief Class encapsulating the base system functionalities. * @brief Class encapsulating the base system functionalities.
*/ */
@ -43,32 +46,43 @@ namespace chibios_rt {
* @details The system is initialized, the idle thread is spawned and the * @details The system is initialized, the idle thread is spawned and the
* current instruction flow becomes the main thread with priority * current instruction flow becomes the main thread with priority
* @p NORMALPRIO. * @p NORMALPRIO.
*
* @api
*/ */
static void Init(void); static void init(void);
/** /**
* @brief Kernel lock. * @brief Kernel lock.
* @note On some ports it is faster to invoke chSysLock() directly because * @note On some ports it is faster to invoke chSysLock() directly
* inlining. * because inlining.
*
* @special
*/ */
static void Lock(void); static void lock(void);
/** /**
* @brief Kernel unlock. * @brief Kernel unlock.
* @note On some ports it is faster to invoke chSysUnlock() directly * @note On some ports it is faster to invoke chSysUnlock() directly
* because inlining. * because inlining.
*
* @special
*/ */
static void Unlock(void); static void unlock(void);
/** /**
* @brief Returns the system time as system ticks. * @brief Returns the system time as system ticks.
* @note The system tick time interval is implementation dependent. * @note The system tick time interval is implementation dependent.
* *
* @return The system time. * @return The system time.
*
* @api
*/ */
static systime_t GetTime(void); static systime_t getTime(void);
}; };
/*------------------------------------------------------------------------*
* chibios_rt::Timer *
*------------------------------------------------------------------------*/
/** /**
* @brief Timer class. * @brief Timer class.
*/ */
@ -77,7 +91,7 @@ namespace chibios_rt {
/** /**
* @brief Embedded @p VirtualTimer structure. * @brief Embedded @p VirtualTimer structure.
*/ */
struct ::VirtualTimer timer; struct ::VirtualTimer timer_ref;
/** /**
* @brief Starts the timer. * @brief Starts the timer.
@ -87,30 +101,37 @@ namespace chibios_rt {
* @param[in] time the time in system ticks * @param[in] time the time in system ticks
* @param[in] vtfunc the timer callback function * @param[in] vtfunc the timer callback function
* @param[in] par the parameter for the callback function * @param[in] par the parameter for the callback function
*
* @iclass
*/ */
void Set(systime_t time, vtfunc_t vtfunc, void *par); void setI(systime_t time, vtfunc_t vtfunc, void *par);
/** /**
* @brief Resets the timer. * @brief Resets the timer, if armed.
* @note It must be called with the interrupts disabled. *
* @note The timer MUST be active when this function is invoked. * @iclass
*/ */
void Reset(); void resetI();
/** /**
* @brief Returns the timer status. * @brief Returns the timer status.
* *
* @retval TRUE The timer is armed. * @retval TRUE The timer is armed.
* @retval FALSE The timer already fired its callback. * @retval FALSE The timer already fired its callback.
*
* @iclass
*/ */
bool IsArmed(void); bool isArmedI(void);
}; };
/*------------------------------------------------------------------------*
* chibios_rt::ThreadReference *
*------------------------------------------------------------------------*/
/** /**
* @brief Base class for a ChibiOS/RT thread. * @brief Thread reference class.
* @details The thread body is the virtual function @p Main(). * @details This class encapsulates a reference to a system thread.
*/ */
class BaseThread { class ThreadReference {
public: public:
/** /**
* @brief Pointer to the system thread. * @brief Pointer to the system thread.
@ -118,169 +139,281 @@ namespace chibios_rt {
::Thread *thread_ref; ::Thread *thread_ref;
/** /**
* @brief Thread constructor. * @brief Thread reference constructor.
* @details The thread object is initialized and a system thread is
* started.
* *
* @param[in] workspace pointer to the workspace area * @param[in] tp the target thread. This parameter can be
* @param[in] wsize size of the workspace area * @p NULL if the thread is not known at
* @param[in] prio thread priority * creation time.
*
* @api
*/ */
BaseThread(void *workspace, size_t wsize, tprio_t prio); ThreadReference(Thread * tp);
/** /**
* @brief Thread exit. * @brief Suspends the current thread on the reference.
* @details The suspended thread becomes the referenced thread. It is
* possible to use this method only if the thread reference
* was set to @p NULL.
* *
* @param[in] msg the exit message * @return The incoming message.
*
* @api
*/ */
static void Exit(msg_t msg); msg_t suspend(void);
#if CH_USE_WAITEXIT /**
* @brief Suspends the current thread on the reference.
* @details The suspended thread becomes the referenced thread. It is
* possible to use this method only if the thread reference
* was set to @p NULL.
*
* @return The incoming message.
*
* @sclass
*/
msg_t suspendS(void);
/**
* @brief Resumes the currently referenced thread, if any.
*
* @api
*/
void resume(msg_t msg);
/**
* @brief Resumes the currently referenced thread, if any.
*
* @iclass
*/
void resumeI(msg_t msg);
/**
* @brief Requests thread termination.
* @details A termination flag is added to the thread, it is thread
* responsibility to detect it and exit.
*/
void requestTerminate(void);
#if CH_USE_WAITEXIT || defined(__DOXYGEN__)
/** /**
* @brief Synchronization on Thread exit. * @brief Synchronization on Thread exit.
* *
* @return The exit message from the thread. * @return The exit message from the thread.
*
* @api
*/ */
msg_t Wait(void); msg_t wait(void);
#endif /* CH_USE_WAITEXIT */ #endif /* CH_USE_WAITEXIT */
/** #if CH_USE_MESSAGES || defined(__DOXYGEN__)
* @brief Resumes the thread.
* @details The thread encapsulated into the object is resumed.
*/
void Resume(void);
/**
* @brief Changes the thread priority.
*
* @param[in] newprio The new priority level
*/
static void SetPriority(tprio_t newprio);
/**
* @brief Requests thread termination.
* @details A termination flag is pended on the thread, it is thread
* responsibility to detect it and exit.
*/
void Terminate(void);
/**
* @brief Suspends the thread execution for the specified number of
* system ticks.
*
* @param[in] n the number of system ticks
*/
static void Sleep(systime_t n);
/**
* @brief Suspends the thread execution until the specified time arrives.
*
* @param[in] time the system time
*/
static void SleepUntil(systime_t time);
#if CH_USE_MESSAGES
/**
* @brief Sends a message to the thread and returns the answer.
*
* @param[in] tp the target thread
* @param[in] msg the sent message
* @return The returned message.
*/
static msg_t SendMessage(::Thread *tp, msg_t msg);
/** /**
* @brief Sends a message to the thread and returns the answer. * @brief Sends a message to the thread and returns the answer.
* *
* @param[in] msg the sent message * @param[in] msg the sent message
* @return The returned message. * @return The returned message.
*/
msg_t SendMessage(msg_t msg);
/**
* @brief Waits for a message.
* *
* @return The sebder thread. * @api
*/ */
static Thread *WaitMessage(void); msg_t sendMessage(msg_t msg);
/**
* @brief Returns an enqueued message or @p NULL.
*
* @param[in] tp the sender thread
* @return The incoming message.
*/
static msg_t GetMessage(Thread* tp);
/**
* @brief Releases the next message in queue with a reply.
*
* @param[in] tp the sender thread
* @param[in] msg the answer message
*/
static void ReleaseMessage(Thread* tp, msg_t msg);
/** /**
* @brief Returns true if there is at least one message in queue. * @brief Returns true if there is at least one message in queue.
* *
* @retval TRUE A message is waiting in queue. * @retval true A message is waiting in queue.
* @retval FALSE A message is not waiting in queue. * @retval false A message is not waiting in queue.
*
* @api
*/ */
static bool IsPendingMessage(void); bool isPendingMessage(void);
#endif /* CH_USE_MESSAGES */ #endif /* CH_USE_MESSAGES */
#if CH_USE_DYNAMIC
#endif /* CH_USE_DYNAMIC */
};
/*------------------------------------------------------------------------*
* chibios_rt::BaseThread *
*------------------------------------------------------------------------*/
/**
* @brief Abstract base class for a ChibiOS/RT thread.
* @details The thread body is the virtual function @p Main().
*/
class BaseThread : ThreadReference{
public:
/**
* @brief BaseThread constructor.
*
* @api
*/
BaseThread(void);
/** /**
* @brief Thread body function. * @brief Thread body function.
* *
* @return The exit message. * @return The exit message.
*
* @api
*/ */
virtual msg_t Main(void); virtual msg_t Main(void);
};
/** /**
* @brief Enhanced threads template class. * @brief Creates and starts a system thread.
* @details This class introduces thread names and static working area *
* allocation. * @param[in] tname the name to be assigned to the thread
* @param[in] prio thread priority
* @return Error flag.
* @retval false if the operation failed.
* @retval true if the operation succeeded.
*
* @api
*/
virtual bool start(const char *tname, tprio_t prio);
/**
* @brief Thread exit.
*
* @param[in] msg the exit message
*
* @api
*/
static void exit(msg_t msg);
#if CH_USE_WAITEXIT || defined(__DOXYGEN__)
/**
* @brief Synchronization on Thread exit.
*
* @return The exit message from the thread.
*
* @api
*/
msg_t wait(void);
#endif /* CH_USE_WAITEXIT */
/**
* @brief Changes the current thread priority.
*
* @param[in] newprio The new priority level
* @return The old priority level.
*
* @api
*/
static tprio_t setPriority(tprio_t newprio);
/**
* @brief Requests thread termination.
* @details A termination flag is added to the thread, it is thread
* responsibility to detect it and exit.
*
* @api
*/
void requestTerminate(void);
/**
* @brief Determines if there is a pending termination request.
*
* @return The termination status.
* @retval false if there is no termination request pending.
* @retval true if there is a termination request pending.
*
* @api
*/
bool shouldTerminate(void);
/**
* @brief Suspends the thread execution for the specified number of
* system ticks.
*
* @param[in] interval the number of system ticks
*
* @api
*/
static void sleep(systime_t interval);
/**
* @brief Suspends the thread execution until the specified time arrives.
*
* @param[in] time the system time
*
* @api
*/
static void sleepUntil(systime_t time);
#if CH_USE_MESSAGES
/**
* @brief Waits for a message.
*
* @return The sender thread.
*
* @api
*/
static ThreadReference waitMessage(void);
/**
* @brief Returns an enqueued message or @p NULL.
*
* @param[in] trp the sender thread reference
* @return The incoming message.
*
* @api
*/
static msg_t getMessage(ThreadReference* trp);
/**
* @brief Releases the next message in queue with a reply.
*
* @param[in] trp the sender thread reference
* @param[in] msg the answer message
*
* @api
*/
static void releaseMessage(ThreadReference* trp, msg_t msg);
#endif /* CH_USE_MESSAGES */
};
/*------------------------------------------------------------------------*
* chibios_rt::BaseStaticThread *
*------------------------------------------------------------------------*/
/**
* @brief Static threads template class.
* @details This class introduces static working area allocation.
* *
* @param N the working area size for the thread class * @param N the working area size for the thread class
*/ */
template <int N> template <int N>
class EnhancedThread : public BaseThread { class BaseStaticThread : public BaseThread {
protected: protected:
WORKING_AREA(wa, N); // Thread working area. WORKING_AREA(wa, N); // Thread working area.
public: public:
/** /**
* @brief The thread name. * @brief Thread constructor.
*/ * @details The thread object is initialized but the thread is not
const char *name; * started here.
/**
* @brief Full constructor.
* @details This constructor allows to set a priority level for the new
* thread.
* *
* @param[in] tname the name to be assigned to the thread * @api
* @param[in] prio the priority to be assigned to the thread
*/ */
EnhancedThread(const char *tname, tprio_t prio) : BaseStaticThread(void) : BaseThread() {
BaseThread(wa, sizeof wa, prio) {
name = tname;
} }
/** /**
* @brief Simplified constructor. * @brief Creates and starts a system thread.
* @details This constructor allows to create a thread by simply
* specifying a name. In is assumed @p NORMALPRIO as initial
* priority.
* *
* @param[in] tname the name to be assigned to the thread * @param[in] tname the name to be assigned to the thread
* @param[in] prio thread priority
* @return Error flag.
* @retval false if the operation failed.
* @retval true if the operation succeeded.
*
* @api
*/ */
EnhancedThread(const char *tname) : bool start(const char *tname, tprio_t prio) {
BaseThread(wa, sizeof wa, NORMALPRIO) { msg_t _thd_start(void *arg);
name = tname; thread_ref = chThdCreateStatic(wa, sizeof(wa), prio, _thd_start, this);
return thread_ref != NULL;
} }
}; };
@ -310,7 +443,7 @@ namespace chibios_rt {
* @param[in] n the new semaphore counter value, must be * @param[in] n the new semaphore counter value, must be
* greater or equal to zero * greater or equal to zero
*/ */
void Reset(cnt_t n); void reset(cnt_t n);
/** /**
* @brief Wait operation on the semaphore. * @brief Wait operation on the semaphore.
@ -318,7 +451,7 @@ namespace chibios_rt {
* @retval RDY_OK if the semaphore was signaled or not taken. * @retval RDY_OK if the semaphore was signaled or not taken.
* @retval RDY_RESET if the semaphore was reset. * @retval RDY_RESET if the semaphore was reset.
*/ */
msg_t Wait(void); msg_t wait(void);
/** /**
* @brief Wait operation on the semaphore with timeout. * @brief Wait operation on the semaphore with timeout.
@ -329,14 +462,14 @@ namespace chibios_rt {
* @retval RDY_TIMEOUT if the semaphore was not signaled or reset * @retval RDY_TIMEOUT if the semaphore was not signaled or reset
* within the specified timeout. * within the specified timeout.
*/ */
msg_t WaitTimeout(systime_t time); msg_t waitTimeout(systime_t time);
/** /**
* @brief Signal operation on the semaphore. * @brief Signal operation on the semaphore.
* @details The semaphore is signaled, the next thread in queue, if any, * @details The semaphore is signaled, the next thread in queue, if any,
* is awakened. * is awakened.
*/ */
void Signal(void); void signal(void);
#if CH_USE_SEMSW #if CH_USE_SEMSW
/** /**
@ -347,7 +480,7 @@ namespace chibios_rt {
* @retval RDY_OK if the semaphore was signaled or not taken. * @retval RDY_OK if the semaphore was signaled or not taken.
* @retval RDY_RESET if the semaphore was reset. * @retval RDY_RESET if the semaphore was reset.
*/ */
static msg_t SignalWait(Semaphore *ssem, Semaphore *wsem); static msg_t signalWait(Semaphore *ssem, Semaphore *wsem);
#endif /* CH_USE_SEMSW */ #endif /* CH_USE_SEMSW */
}; };
#endif /* CH_USE_SEMAPHORES */ #endif /* CH_USE_SEMAPHORES */
@ -375,7 +508,7 @@ namespace chibios_rt {
* @retval TRUE if the mutex was successfully acquired * @retval TRUE if the mutex was successfully acquired
* @retval FALSE if the lock attempt failed. * @retval FALSE if the lock attempt failed.
*/ */
bool TryLock(void); bool tryLock(void);
/** /**
* @brief Locks the mutex. * @brief Locks the mutex.
@ -383,14 +516,14 @@ namespace chibios_rt {
* already locked then the thread enters the mutex priority * already locked then the thread enters the mutex priority
* queue and waits. * queue and waits.
*/ */
void Lock(void); void lock(void);
/** /**
* @brief Unlocks the mutex. * @brief Unlocks the mutex.
* @details Performs an unlock operation on the mutex, the next waiting * @details Performs an unlock operation on the mutex, the next waiting
* thread, if any, is resumed and locks the mutex. * thread, if any, is resumed and locks the mutex.
*/ */
static void Unlock(void); static void unlock(void);
/** /**
* @brief Unlocks all the mutexes owned by the invoking thread. * @brief Unlocks all the mutexes owned by the invoking thread.
@ -399,7 +532,7 @@ namespace chibios_rt {
* this function does not have any overhead related to the * this function does not have any overhead related to the
* priority inheritance mechanism. * priority inheritance mechanism.
*/ */
static void UnlockAll(void); static void unlockAll(void);
}; };
#if CH_USE_CONDVARS #if CH_USE_CONDVARS
@ -423,13 +556,13 @@ namespace chibios_rt {
* @brief Signals the CondVar. * @brief Signals the CondVar.
* @details The next thread waiting on the @p CondVar, if any, is awakened. * @details The next thread waiting on the @p CondVar, if any, is awakened.
*/ */
void Signal(void); void signal(void);
/** /**
* @brief Broadcasts the CondVar. * @brief Broadcasts the CondVar.
* @details All the threads waiting on the @p CondVar, if any, are awakened. * @details All the threads waiting on the @p CondVar, if any, are awakened.
*/ */
void Broadcast(void); void broadcast(void);
/** /**
* @brief Waits on the CondVar while releasing the controlling mutex. * @brief Waits on the CondVar while releasing the controlling mutex.
@ -440,7 +573,7 @@ namespace chibios_rt {
* @retval RDY_RESET if the condvar was signaled using * @retval RDY_RESET if the condvar was signaled using
* @p chCondBroadcast(). * @p chCondBroadcast().
*/ */
msg_t Wait(void); msg_t wait(void);
#if CH_USE_CONDVARS_TIMEOUT #if CH_USE_CONDVARS_TIMEOUT
/** /**
@ -455,7 +588,7 @@ namespace chibios_rt {
* @retval RDY_TIMEOUT if the condvar was not signaled within the * @retval RDY_TIMEOUT if the condvar was not signaled within the
* specified timeout. * specified timeout.
*/ */
msg_t WaitTimeout(systime_t time); msg_t waitTimeout(systime_t time);
#endif /* CH_USE_CONDVARS_TIMEOUT */ #endif /* CH_USE_CONDVARS_TIMEOUT */
}; };
#endif /* CH_USE_CONDVARS */ #endif /* CH_USE_CONDVARS */
@ -485,7 +618,7 @@ namespace chibios_rt {
* @param[in] eid numeric identifier assigned to the Event * @param[in] eid numeric identifier assigned to the Event
* Listener * Listener
*/ */
void Register(EventListener *elp, eventid_t eid); void registerOne(EventListener *elp, eventid_t eid);
/** /**
* @brief Registers an Event Listener on an Event Source. * @brief Registers an Event Listener on an Event Source.
@ -495,7 +628,7 @@ namespace chibios_rt {
* @param[in] emask the mask of event flags to be pended to the * @param[in] emask the mask of event flags to be pended to the
* thread when the event source is broadcasted * thread when the event source is broadcasted
*/ */
void RegisterMask(EventListener *elp, eventmask_t emask); void registerMask(EventListener *elp, eventmask_t emask);
/** /**
* @brief Unregisters a listener. * @brief Unregisters a listener.
@ -504,7 +637,7 @@ namespace chibios_rt {
* *
* @param[in] elp the listener to be unregistered * @param[in] elp the listener to be unregistered
*/ */
void Unregister(EventListener *elp); void unregister(EventListener *elp);
/** /**
* @brief Broadcasts an event. * @brief Broadcasts an event.
@ -513,7 +646,7 @@ namespace chibios_rt {
* @param[in] flags the flags set to be added to the listener * @param[in] flags the flags set to be added to the listener
* flags mask * flags mask
*/ */
void BroadcastFlags(flagsmask_t flags); void broadcastFlags(flagsmask_t flags);
/** /**
* @brief Clears specified events from the pending events mask. * @brief Clears specified events from the pending events mask.
@ -523,7 +656,7 @@ namespace chibios_rt {
* @return The flags added to the listener by the * @return The flags added to the listener by the
* associated event source. * associated event source.
*/ */
static flagsmask_t GetAndClearFlags(EventListener *elp); static flagsmask_t getAndClearFlags(EventListener *elp);
/** /**
* @brief Clears specified events from the pending events mask. * @brief Clears specified events from the pending events mask.
@ -531,7 +664,7 @@ namespace chibios_rt {
* @param[in] mask the events to be cleared * @param[in] mask the events to be cleared
* @return The pending events that were cleared. * @return The pending events that were cleared.
*/ */
static eventmask_t GetAndClearEvents(eventmask_t mask); static eventmask_t getAndClearEvents(eventmask_t mask);
/** /**
* @brief Makes an events mask pending in the current thread. * @brief Makes an events mask pending in the current thread.
@ -540,7 +673,7 @@ namespace chibios_rt {
* @param[in] mask the events to be pended * @param[in] mask the events to be pended
* @return The current pending events mask. * @return The current pending events mask.
*/ */
static eventmask_t AddEvents(eventmask_t mask); static eventmask_t addEvents(eventmask_t mask);
/** /**
* @brief Invokes the event handlers associated with a mask. * @brief Invokes the event handlers associated with a mask.
@ -550,7 +683,7 @@ namespace chibios_rt {
* have indexes from zero up the higher registered * have indexes from zero up the higher registered
* event identifier. * event identifier.
*/ */
static void Dispatch(const evhandler_t handlers[], eventmask_t mask); static void dispatch(const evhandler_t handlers[], eventmask_t mask);
/** /**
* @brief Waits for a single event. * @brief Waits for a single event.
@ -567,7 +700,7 @@ namespace chibios_rt {
* @return The mask of the lowest id served and cleared * @return The mask of the lowest id served and cleared
* event. * event.
*/ */
static eventmask_t WaitOne(eventmask_t ewmask); static eventmask_t waitOne(eventmask_t ewmask);
/** /**
* @brief Waits for any of the specified events. * @brief Waits for any of the specified events.
@ -579,7 +712,7 @@ namespace chibios_rt {
* wait for, @p ALL_EVENTS enables all the events * wait for, @p ALL_EVENTS enables all the events
* @return The mask of the served and cleared events. * @return The mask of the served and cleared events.
*/ */
static eventmask_t WaitAny(eventmask_t ewmask); static eventmask_t waitAny(eventmask_t ewmask);
/** /**
* @brief Waits for all the specified event flags then clears them. * @brief Waits for all the specified event flags then clears them.
@ -590,7 +723,7 @@ namespace chibios_rt {
* wait for * wait for
* @return The mask of the served and cleared events. * @return The mask of the served and cleared events.
*/ */
static eventmask_t WaitAll(eventmask_t ewmask); static eventmask_t waitAll(eventmask_t ewmask);
#if CH_USE_EVENTS_TIMEOUT #if CH_USE_EVENTS_TIMEOUT
/** /**
@ -611,7 +744,7 @@ namespace chibios_rt {
* event. * event.
* @retval 0 if the specified timeout expired. * @retval 0 if the specified timeout expired.
*/ */
static eventmask_t WaitOneTimeout(eventmask_t ewmask, systime_t time); static eventmask_t waitOneTimeout(eventmask_t ewmask, systime_t time);
/** /**
* @brief Waits for any of the specified events. * @brief Waits for any of the specified events.
@ -626,7 +759,7 @@ namespace chibios_rt {
* @return The mask of the served and cleared events. * @return The mask of the served and cleared events.
* @retval 0 if the specified timeout expired. * @retval 0 if the specified timeout expired.
*/ */
static eventmask_t WaitAnyTimeout(eventmask_t ewmask, systime_t time); static eventmask_t waitAnyTimeout(eventmask_t ewmask, systime_t time);
/** /**
* @brief Waits for all the specified event flags then clears them. * @brief Waits for all the specified event flags then clears them.
@ -640,7 +773,7 @@ namespace chibios_rt {
* @return The mask of the served and cleared events. * @return The mask of the served and cleared events.
* @retval 0 if the specified timeout expired. * @retval 0 if the specified timeout expired.
*/ */
static eventmask_t WaitAllTimeout(eventmask_t ewmask, systime_t time); static eventmask_t waitAllTimeout(eventmask_t ewmask, systime_t time);
#endif /* CH_USE_EVENTS_TIMEOUT */ #endif /* CH_USE_EVENTS_TIMEOUT */
}; };