diff options
| author | gdisirio <gdisirio@35acf78f-673a-0410-8e92-d51de3d6d3f4> | 2010-02-02 20:20:12 +0000 | 
|---|---|---|
| committer | gdisirio <gdisirio@35acf78f-673a-0410-8e92-d51de3d6d3f4> | 2010-02-02 20:20:12 +0000 | 
| commit | e515bcf581c92643c21eb6ed53ba0d0b1604fe4b (patch) | |
| tree | efae1098d4db1532fcf51f1387add77747ffc061 | |
| parent | ce91c3f44a3f0b9cacd07972a052c7360fb24053 (diff) | |
| download | ChibiOS-e515bcf581c92643c21eb6ed53ba0d0b1604fe4b.tar.gz ChibiOS-e515bcf581c92643c21eb6ed53ba0d0b1604fe4b.tar.bz2 ChibiOS-e515bcf581c92643c21eb6ed53ba0d0b1604fe4b.zip | |
Implemented registry subsystem (still in progress).
git-svn-id: svn://svn.code.sf.net/p/chibios/svn/trunk@1558 35acf78f-673a-0410-8e92-d51de3d6d3f4
| -rw-r--r-- | demos/ARMCM3-STM32F103-GCC/chconf.h | 10 | ||||
| -rw-r--r-- | os/kernel/include/ch.h | 1 | ||||
| -rw-r--r-- | os/kernel/include/scheduler.h | 16 | ||||
| -rw-r--r-- | os/kernel/include/threads.h | 18 | ||||
| -rw-r--r-- | os/kernel/kernel.mk | 1 | ||||
| -rw-r--r-- | os/kernel/src/chschd.c | 8 | ||||
| -rw-r--r-- | os/kernel/src/chthreads.c | 222 | ||||
| -rw-r--r-- | os/kernel/templates/chconf.h | 10 | ||||
| -rw-r--r-- | os/ports/GCC/ARMCM3/chcore.c | 8 | ||||
| -rw-r--r-- | readme.txt | 11 | 
10 files changed, 186 insertions, 119 deletions
| diff --git a/demos/ARMCM3-STM32F103-GCC/chconf.h b/demos/ARMCM3-STM32F103-GCC/chconf.h index 3b29983cb..d0d7e7d41 100644 --- a/demos/ARMCM3-STM32F103-GCC/chconf.h +++ b/demos/ARMCM3-STM32F103-GCC/chconf.h @@ -124,6 +124,16 @@  /*===========================================================================*/
  /**
 + * @brief Threads registry APIs.
 + * @details If enabled then the registry APIs are included in the kernel.
 + *
 + * @note The default is @p TRUE.
 + */
 +#if !defined(CH_USE_REGISTRY) || defined(__DOXYGEN__)
 +#define CH_USE_REGISTRY                 TRUE
 +#endif
 +
 +/**
   * @brief Threads synchronization APIs.
   * @details If enabled then the @p chThdWait() function is included in
   *          the kernel.
 diff --git a/os/kernel/include/ch.h b/os/kernel/include/ch.h index 683c69cc6..109040262 100644 --- a/os/kernel/include/ch.h +++ b/os/kernel/include/ch.h @@ -79,6 +79,7 @@  #include "heap.h"
  #include "mempools.h"
  #include "threads.h"
 +#include "registry.h"
  #include "inline.h"
  #include "queues.h"
  #include "streams.h"
 diff --git a/os/kernel/include/scheduler.h b/os/kernel/include/scheduler.h index 539c678fa..9d8af9ecc 100644 --- a/os/kernel/include/scheduler.h +++ b/os/kernel/include/scheduler.h @@ -64,19 +64,27 @@   * @extends ThreadsQueue   */  typedef struct { -  ThreadsQueue          r_queue;        /**< Threads queue.*/ +  ThreadsQueue          r_queue;        /**< Threads queue.                 */    tprio_t               r_prio;         /**< This field must be initialized to -                                             zero.*/ +                                             zero.                          */ +  struct context        p_ctx;          /**< Not used, present because +                                             offsets.                       */ +#if CH_USE_REGISTRY +  Thread                *p_newer;       /**< Newer registry element.        */ +  Thread                *p_older;       /**< Older registry element.        */ +#endif    /* End of the fields shared with the Thread structure.*/  #if CH_TIME_QUANTUM > 0 -  cnt_t                 r_preempt;      /**< Round robin counter.*/ +  cnt_t                 r_preempt;      /**< Round robin counter.           */  #endif  #ifndef CH_CURRP_REGISTER_CACHE -  Thread                *r_current;     /**< The currently running thread.*/ +  Thread                *r_current;     /**< The currently running thread.  */  #endif  } ReadyList; +#if !defined(__DOXYGEN__)  extern ReadyList rlist; +#endif  #ifdef CH_CURRP_REGISTER_CACHE  register Thread *currp asm(CH_CURRP_REGISTER_CACHE); diff --git a/os/kernel/include/threads.h b/os/kernel/include/threads.h index a9209e6ea..24b79a3cd 100644 --- a/os/kernel/include/threads.h +++ b/os/kernel/include/threads.h @@ -53,13 +53,17 @@ struct Thread {                                               queue.                         */    /* End of the fields shared with the ThreadsQueue structure. */    tprio_t               p_prio;         /**< Thread priority.               */ +  struct context        p_ctx;          /**< Processor context.             */ +#if CH_USE_REGISTRY +  Thread                *p_newer;       /**< Newer registry element.        */ +  Thread                *p_older;       /**< Older registry element.        */ +#endif    /* End of the fields shared with the ReadyList structure. */  #if CH_USE_DYNAMIC    trefs_t               p_refs;         /**< References to this thread.     */  #endif    tstate_t              p_state;        /**< Current thread state.          */    tmode_t               p_flags;        /**< Various thread flags.          */ -  struct context        p_ctx;          /**< Processor context.             */  #if CH_USE_NESTED_LOCKS    cnt_t                 p_locks;        /**< Number of nested locks.        */  #endif @@ -181,13 +185,19 @@ extern "C" {  }  #endif -/** Returns the pointer to the @p Thread currently in execution.*/ +/** + * Returns a pointer to the current @p Thread. + */  #define chThdSelf() currp -/** Returns the current thread priority.*/ +/** + * Returns the current thread priority. + */  #define chThdGetPriority() (currp->p_prio) -/** Returns the pointer to the @p Thread local storage area, if any.*/ +/** + * Returns the pointer to the @p Thread local storage area, if any. + */  #define chThdLS() (void *)(currp + 1)  /** diff --git a/os/kernel/kernel.mk b/os/kernel/kernel.mk index 47c8bb1d4..b97b0e5dc 100644 --- a/os/kernel/kernel.mk +++ b/os/kernel/kernel.mk @@ -6,6 +6,7 @@ KERNSRC = ${CHIBIOS}/os/kernel/src/chsys.c \            ${CHIBIOS}/os/kernel/src/chvt.c \
            ${CHIBIOS}/os/kernel/src/chschd.c \
            ${CHIBIOS}/os/kernel/src/chthreads.c \
 +          ${CHIBIOS}/os/kernel/src/chregistry.c \
            ${CHIBIOS}/os/kernel/src/chsem.c \
            ${CHIBIOS}/os/kernel/src/chmtx.c \
            ${CHIBIOS}/os/kernel/src/chcond.c \
 diff --git a/os/kernel/src/chschd.c b/os/kernel/src/chschd.c index f7be9c6a8..5b4d18133 100644 --- a/os/kernel/src/chschd.c +++ b/os/kernel/src/chschd.c @@ -26,9 +26,10 @@  #include "ch.h" -/** @cond never */ +/** + * @brief Ready list header. + */  ReadyList rlist; -/** @endcond */  /**   * @brief Scheduler initialization. @@ -42,6 +43,9 @@ void scheduler_init(void) {  #if CH_TIME_QUANTUM > 0    rlist.r_preempt = CH_TIME_QUANTUM;  #endif +#if CH_USE_REGISTRY +  rlist.p_newer = rlist.p_older = (Thread *)&rlist; +#endif  }  /** diff --git a/os/kernel/src/chthreads.c b/os/kernel/src/chthreads.c index 26183706a..95b1e68bf 100644 --- a/os/kernel/src/chthreads.c +++ b/os/kernel/src/chthreads.c @@ -27,13 +27,21 @@  #include "ch.h"  /** - * @brief Initializes a thread structure. + * @brief   Initializes a thread structure. + * + * @param[in] tp    pointer to the thread + * @param[in] prio  the priority level for the new thread + * + * @return  The same thread pointer passed as parameter.   */  Thread *init_thread(Thread *tp, tprio_t prio) {    tp->p_flags = THD_MEM_MODE_STATIC;    tp->p_prio = prio;    tp->p_state = THD_STATE_SUSPENDED; +#if CH_USE_REGISTRY +  REG_INSERT(tp); +#endif  #if CH_USE_DYNAMIC    tp->p_refs = 1;  #endif @@ -69,22 +77,23 @@ static void memfill(uint8_t *startp, uint8_t *endp, uint8_t v) {  #endif  /** - * @brief Initializes a new thread. + * @brief   Initializes a new thread.   * @details The new thread is initialized but not inserted in the ready list,   *          the initial state is @p THD_STATE_SUSPENDED. + * @note    A thread can terminate by calling @p chThdExit() or by simply + *          returning from its main function. + * @note    This function can be invoked from within an interrupt handler + *          even if it is not an I-Class API because it does not touch + *          any critical kernel data structure.   * - * @param[out] wsp pointer to a working area dedicated to the thread stack - * @param[in] size size of the working area - * @param[in] prio the priority level for the new thread - * @param[in] pf the thread function - * @param[in] arg an argument passed to the thread function. It can be @p NULL. - * @return The pointer to the @p Thread structure allocated for the - *         thread into the working space area. - * @note A thread can terminate by calling @p chThdExit() or by simply - *       returning from its main function. - * @note This function can be invoked from within an interrupt handler even if - *       it is not an I-Class API because it does not touch any critical kernel - *       data structure. + * @param[out] wsp  pointer to a working area dedicated to the thread stack + * @param[in] size  size of the working area + * @param[in] prio  the priority level for the new thread + * @param[in] pf    the thread function + * @param[in] arg   an argument passed to the thread function. It can be + *                  @p NULL. + * @return  The pointer to the @p Thread structure allocated for the + *          thread into the working space area.   */  Thread *chThdInit(void *wsp, size_t size, tprio_t prio, tfunc_t pf, void *arg) {    /* Thread structure is layed out in the lower part of the thread workspace */ @@ -103,18 +112,18 @@ Thread *chThdInit(void *wsp, size_t size, tprio_t prio, tfunc_t pf, void *arg) {  }  /** - * @brief Creates a new thread into a static memory area. + * @brief   Creates a new thread into a static memory area. + * @note    A thread can terminate by calling @p chThdExit() or by simply + *          returning from its main function.   * - * @param[out] wsp pointer to a working area dedicated to the thread - *                       stack - * @param[in] size size of the working area - * @param[in] prio the priority level for the new thread - * @param[in] pf the thread function - * @param[in] arg an argument passed to the thread function. It can be @p NULL. - * @return The pointer to the @p Thread structure allocated for the - *         thread into the working space area. - * @note A thread can terminate by calling @p chThdExit() or by simply - *       returning from its main function. + * @param[out] wsp  pointer to a working area dedicated to the thread stack + * @param[in] size  size of the working area + * @param[in] prio  the priority level for the new thread + * @param[in] pf    the thread function + * @param[in] arg   an argument passed to the thread function. It can be + *                  @p NULL. + * @return  The pointer to the @p Thread structure allocated for the + *          thread into the working space area.   */  Thread *chThdCreateStatic(void *wsp, size_t size,                            tprio_t prio, tfunc_t pf, void *arg) { @@ -124,24 +133,25 @@ Thread *chThdCreateStatic(void *wsp, size_t size,  #if CH_USE_DYNAMIC && CH_USE_HEAP  /** - * @brief Creates a new thread allocating the memory from the heap. + * @brief   Creates a new thread allocating the memory from the heap. + * @note    A thread can terminate by calling @p chThdExit() or by simply + *          returning from its main function. + * @note    The memory allocated for the thread is not released when the thread + *          terminates but when a @p chThdWait() is performed. + * @note    The function is available only if the @p CH_USE_DYNAMIC, + *          @p CH_USE_HEAP and @p CH_USE_WAITEXIT options are enabled + *          in @p chconf.h.   * - * @param[in] heapp heap from which allocate the memory or NULL for the + * @param[in] heapp heap from which allocate the memory or @p NULL for the   *                  default heap - * @param[in] size size of the working area to be allocated - * @param[in] prio the priority level for the new thread - * @param[in] pf the thread function - * @param[in] arg an argument passed to the thread function. It can be @p NULL. - * @return The pointer to the @p Thread structure allocated for the - *         thread into the working space area. - * @retval NULL if the memory cannot be allocated. - * @note A thread can terminate by calling @p chThdExit() or by simply - *       returning from its main function. - * @note The memory allocated for the thread is not released when the thread - *       terminates but when a @p chThdWait() is performed. - * @note The function is available only if the @p CH_USE_DYNAMIC, - *       @p CH_USE_HEAP and @p CH_USE_WAITEXIT options are enabled - *       in @p chconf.h. + * @param[in] size  size of the working area to be allocated + * @param[in] prio  the priority level for the new thread + * @param[in] pf    the thread function + * @param[in] arg   an argument passed to the thread function. It can be + *                  @p NULL. + * @return  The pointer to the @p Thread structure allocated for the + *          thread into the working space area. + * @retval  NULL if the memory cannot be allocated.   */  Thread *chThdCreateFromHeap(MemoryHeap *heapp, size_t size,                              tprio_t prio, tfunc_t pf, void *arg) { @@ -159,24 +169,25 @@ Thread *chThdCreateFromHeap(MemoryHeap *heapp, size_t size,  #if CH_USE_DYNAMIC && CH_USE_MEMPOOLS  /** - * @brief Creates a new thread allocating the memory from the specified Memory - *        Pool. + * @brief   Creates a new thread allocating the memory from the specified + *          Memory Pool. + * @note    A thread can terminate by calling @p chThdExit() or by simply + *          returning from its main function. + * @note    The memory allocated for the thread is not released when the thread + *          terminates but when a @p chThdWait() is performed. + * @note    The function is available only if the @p CH_USE_DYNAMIC, + *          @p CH_USE_MEMPOOLS and @p CH_USE_WAITEXIT options are enabled + *          in @p chconf.h.   * - * @param[in] mp the memory pool - * @param[in] prio the priority level for the new thread - * @param[in] pf the thread function - * @param[in] arg an argument passed to the thread function. It can be @p NULL. - * @return The pointer to the @p Thread structure allocated for the - *         thread into the working space area or @p NULL if the memory cannot - *         be allocated. - * @retval NULL if the memory pool is empty. - * @note A thread can terminate by calling @p chThdExit() or by simply - *       returning from its main function. - * @note The memory allocated for the thread is not released when the thread - *       terminates but when a @p chThdWait() is performed. - * @note The function is available only if the @p CH_USE_DYNAMIC, - *       @p CH_USE_MEMPOOLS and @p CH_USE_WAITEXIT options are enabled - *       in @p chconf.h. + * @param[in] mp    pointer to the memory pool object + * @param[in] prio  the priority level for the new thread + * @param[in] pf    the thread function + * @param[in] arg   an argument passed to the thread function. It can be + *                  @p NULL. + * @return  The pointer to the @p Thread structure allocated for the + *          thread into the working space area or @p NULL if the memory cannot + *          be allocated. + * @retval  NULL if the memory pool is empty.   */  Thread *chThdCreateFromMemoryPool(MemoryPool *mp, tprio_t prio,                                    tfunc_t pf, void *arg) { @@ -196,14 +207,14 @@ Thread *chThdCreateFromMemoryPool(MemoryPool *mp, tprio_t prio,  #endif /* CH_USE_DYNAMIC && CH_USE_MEMPOOLS */  /** - * @brief Changes the running thread priority level then reschedules if - *        necessary. + * @brief   Changes the running thread priority level then reschedules if + *          necessary. + * @note    The function returns the real thread priority regardless of the + *          current priority that could be higher than the real priority + *          because the priority inheritance mechanism.   *   * @param[in] newprio the new priority level of the running thread - * @return The old priority level. - * @note The function returns the real thread priority regardless of the - *       current priority that could be higher than the real priority because - *       the priority inheritance mechanism. + * @return  The old priority level.   */  tprio_t chThdSetPriority(tprio_t newprio) {    tprio_t oldprio; @@ -227,12 +238,11 @@ tprio_t chThdSetPriority(tprio_t newprio) {  }  /** - * @brief Resumes a suspended thread. + * @brief   Resumes a suspended thread. + * @note    Use this function to resume threads created with @p chThdInit().   * - * @param[in] tp the pointer to the thread - * @return The pointer to the thread. - * @note This call is supposed to resume threads created with @p chThdInit(). - *       It should not be used on threads suspended using @p chThdSuspend(). + * @param[in] tp    pointer to the thread + * @return  The pointer to the thread.   */  Thread *chThdResume(Thread *tp) { @@ -246,12 +256,12 @@ Thread *chThdResume(Thread *tp) {  }  /** - * @brief Requests a thread termination. + * @brief   Requests a thread termination. + * @note    The thread is not terminated but a termination request is added to + *          its @p p_flags field. The thread can read this status by + *          invoking @p chThdShouldTerminate() and then terminate cleanly.   * - * @param[in] tp the pointer to the thread - * @note The thread is not termitated but a termination request is added to - *       its @p p_flags field. The thread can read this status by - *       invoking @p chThdShouldTerminate() and then terminate cleanly. + * @param[in] tp    pointer to the thread   */  void chThdTerminate(Thread *tp) { @@ -261,16 +271,16 @@ void chThdTerminate(Thread *tp) {  }  /** - * @brief Suspends the invoking thread for the specified time. + * @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. - *                 . + * @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. + *                  .   */  void chThdSleep(systime_t time) { @@ -282,10 +292,10 @@ void chThdSleep(systime_t time) {  }  /** - * @brief Suspends the invoking thread until the system time arrives to the - *        specified value. + * @brief   Suspends the invoking thread until the system time arrives to the + *          specified value.   * - * @param[in] time the absolute system time + * @param[in] time  absolute system time   */  void chThdSleepUntil(systime_t time) { @@ -296,7 +306,7 @@ void chThdSleepUntil(systime_t time) {  }  /** - * @brief Yields the time slot. + * @brief   Yields the time slot.   * @details Yields the CPU control to the next thread in the ready list with   *          equal priority, if any.   */ @@ -308,11 +318,11 @@ void chThdYield(void) {  }  /** - * @brief Terminates the current thread by specifying an exit status code. + * @brief   Terminates the current thread by specifying an exit status code.   * - * @param[in] msg the thread exit code. The code can be retrieved by using - *                @p chThdWait(). - * @return The same thread pointer passed as parameter. + * @param[in] msg   thread exit code. The code can be retrieved by using + *                  @p chThdWait(). + * @return  The same thread pointer passed as parameter.   */  void chThdExit(msg_t msg) {    Thread *tp = currp; @@ -324,10 +334,19 @@ void chThdExit(msg_t msg) {    while (notempty(&tp->p_waiting))      chSchReadyI(list_remove(&tp->p_waiting));  #endif +#if CH_USE_REGISTRY +  REG_REMOVE(tp); +#endif    chSchGoSleepS(THD_STATE_FINAL);  }  #if CH_USE_DYNAMIC || defined(__DOXYGEN__) +/** + * @brief   Adds a reference to a thread object. + * + * @param[in] tp    pointer to the thread + * @return  The same thread pointer passed as parameter. + */  Thread *chThdAddRef(Thread *tp) {    chSysLock(); @@ -343,8 +362,8 @@ Thread *chThdAddRef(Thread *tp) {   *          to the proper allocator.   * @note    Static threads are not affected.   * - * @param[in] tp the thread pointer - * @return The same thread pointer passed as parameter. + * @param[in] tp    pointer to the thread + * @return  The same thread pointer passed as parameter.   */  Thread *chThdRelease(Thread *tp) {    trefs_t refs; @@ -393,14 +412,15 @@ Thread *chThdRelease(Thread *tp) {   *            then the working area is returned to the owning memory pool.   *          .   *          Please read the @ref article_lifecycle article for more details. - * @param[in] tp the thread pointer - * @return The exit code from the terminated thread - * @note After invoking @p chThdWait() the thread pointer becomes invalid and - *       must not be used as parameter for further system calls. - * @note The function is available only if the @p CH_USE_WAITEXIT - *       option is enabled in @p chconf.h. - * @note If @p CH_USE_DYNAMIC is not specified this function just waits for - *       the thread termination, no memory allocators are involved. + * @note    After invoking @p chThdWait() the thread pointer becomes invalid + *          and must not be used as parameter for further system calls. + * @note    The function is available only if the @p CH_USE_WAITEXIT + *          option is enabled in @p chconf.h. + * @note    If @p CH_USE_DYNAMIC is not specified this function just waits for + *          the thread termination, no memory allocators are involved. + * + * @param[in] tp    pointer to the thread + * @return  The exit code from the terminated thread   */  msg_t chThdWait(Thread *tp) {    msg_t msg; diff --git a/os/kernel/templates/chconf.h b/os/kernel/templates/chconf.h index 7fc7ea82b..4cb12bd74 100644 --- a/os/kernel/templates/chconf.h +++ b/os/kernel/templates/chconf.h @@ -126,6 +126,16 @@  /*===========================================================================*/
  /**
 + * @brief Threads registry APIs.
 + * @details If enabled then the registry APIs are included in the kernel.
 + *
 + * @note The default is @p TRUE.
 + */
 +#if !defined(CH_USE_REGISTRY) || defined(__DOXYGEN__)
 +#define CH_USE_REGISTRY                 TRUE
 +#endif
 +
 +/**
   * @brief Threads synchronization APIs.
   * @details If enabled then the @p chThdWait() function is included in
   *          the kernel.
 diff --git a/os/ports/GCC/ARMCM3/chcore.c b/os/ports/GCC/ARMCM3/chcore.c index 80354f863..bcd726a7b 100644 --- a/os/ports/GCC/ARMCM3/chcore.c +++ b/os/ports/GCC/ARMCM3/chcore.c @@ -87,8 +87,8 @@ void SVCallVector(Thread *otp, Thread *ntp) {    asm volatile ("mrs     r3, BASEPRI                            \n\t" \
                  "mrs     r12, PSP                               \n\t" \
                  "stmdb   r12!, {r3-r6,r8-r11, lr}               \n\t" \
 -                "str     r12, [r0, #16]                         \n\t" \
 -                "ldr     r12, [r1, #16]                         \n\t" \
 +                "str     r12, [r0, #12]                         \n\t" \
 +                "ldr     r12, [r1, #12]                         \n\t" \
                  "ldmia   r12!, {r3-r6,r8-r11, lr}               \n\t" \
                  "msr     PSP, r12                               \n\t" \
                  "msr     BASEPRI, r3                            \n\t" \
 @@ -97,8 +97,8 @@ void SVCallVector(Thread *otp, Thread *ntp) {    asm volatile ("mrs     r3, BASEPRI                            \n\t" \
                  "mrs     r12, PSP                               \n\t" \
                  "stmdb   r12!, {r3-r11, lr}                     \n\t" \
 -                "str     r12, [r0, #16]                         \n\t" \
 -                "ldr     r12, [r1, #16]                         \n\t" \
 +                "str     r12, [r0, #12]                         \n\t" \
 +                "ldr     r12, [r1, #12]                         \n\t" \
                  "ldmia   r12!, {r3-r11, lr}                     \n\t" \
                  "msr     PSP, r12                               \n\t" \
                  "msr     BASEPRI, r3                            \n\t" \
 diff --git a/readme.txt b/readme.txt index d97427fa0..724a57f20 100644 --- a/readme.txt +++ b/readme.txt @@ -52,14 +52,17 @@  *****************************************************************************
  *** 1.5.1 ***
 +- FIX: Fixed wrong notes on function chThdResume() (bug 2943160).
  - NEW: Implemented the concept of thread references, this mechanism ensures
    that a dynamic thread's memory is not freed while some other thread still
    owns a pointer to the thread. Static threads are not affected by the new
    mechanism. Two new APIs have been added: chThdAddRef() and chThdRelease().
 -- NEW: Not more than one thread can be waiting in chThdWait(), this
 -  capability was already present in beta versions before 0.8.0 but removed
 -  because at the time there was not the references mechanism in place.
 -
 +- NEW: Not more than one thread can be waiting in chThdWait() as long they
 +  own a reference.
 +- NEW: Implemented a new threads registry subsystem, the registry allows to
 +  enumerate the active threads at runtime. The registry is meant as both
 +  a runtime API and a support for debuggers.
 +  
  *** 1.5.0 ***
  - FIX: Fixed missing dependencies check for CH_USE_DYNAMIC (bug 2942757)
    (backported in 1.4.1).
 | 
