diff options
author | Gregory Nutt <gnutt@nuttx.org> | 2014-08-22 12:32:34 -0600 |
---|---|---|
committer | Gregory Nutt <gnutt@nuttx.org> | 2014-08-22 12:32:34 -0600 |
commit | 440d27c51fed1c66e883a6d0584599e2d0569a94 (patch) | |
tree | 8d392b85ac509e0c0e26d1c4c1a8338417771381 /nuttx | |
parent | 3ee26908593dc30b07686f8cb3f8e23fa8ad12d5 (diff) | |
download | nuttx-440d27c51fed1c66e883a6d0584599e2d0569a94.tar.gz nuttx-440d27c51fed1c66e883a6d0584599e2d0569a94.tar.bz2 nuttx-440d27c51fed1c66e883a6d0584599e2d0569a94.zip |
An address environment is the property of a task group, not of a thread
Diffstat (limited to 'nuttx')
-rw-r--r-- | nuttx/Documentation/NuttXBinfmt.html | 4 | ||||
-rw-r--r-- | nuttx/Documentation/NuttxPortingGuide.html | 131 | ||||
-rw-r--r-- | nuttx/arch/z80/include/z180/arch.h | 3 | ||||
-rw-r--r-- | nuttx/arch/z80/include/z180/irq.h | 6 | ||||
-rw-r--r-- | nuttx/arch/z80/src/z180/z180_mmu.c | 209 | ||||
-rw-r--r-- | nuttx/binfmt/binfmt_execmodule.c | 6 | ||||
-rw-r--r-- | nuttx/include/nuttx/arch.h | 122 | ||||
-rw-r--r-- | nuttx/include/nuttx/binfmt/binfmt.h | 2 | ||||
-rw-r--r-- | nuttx/include/nuttx/binfmt/elf.h | 4 | ||||
-rw-r--r-- | nuttx/include/nuttx/binfmt/nxflat.h | 6 | ||||
-rw-r--r-- | nuttx/include/nuttx/sched.h | 52 | ||||
-rw-r--r-- | nuttx/sched/pthread/pthread_create.c | 21 | ||||
-rw-r--r-- | nuttx/sched/sched/sched_releasetcb.c | 4 |
13 files changed, 271 insertions, 299 deletions
diff --git a/nuttx/Documentation/NuttXBinfmt.html b/nuttx/Documentation/NuttXBinfmt.html index 2f4f6e425..0df3b6475 100644 --- a/nuttx/Documentation/NuttXBinfmt.html +++ b/nuttx/Documentation/NuttXBinfmt.html @@ -8,7 +8,7 @@ <tr align="center" bgcolor="#e4e4e4"> <td> <h1><big><font color="#3c34ec"><i>NuttX Binary Loader</i></font></big></h1> - <p>Last Updated: January 16, 2013</p> + <p>Last Updated: August 22, 2014</p> </td> </tr> </table> @@ -170,7 +170,7 @@ struct binary_s */ #ifdef CONFIG_ADDRENV - task_addrenv_t addrenv; /* Task address environment */ + group_addrenv_t addrenv; /* Task group address environment */ #endif size_t mapsize; /* Size of the mapped address region (needed for munmap) */ diff --git a/nuttx/Documentation/NuttxPortingGuide.html b/nuttx/Documentation/NuttxPortingGuide.html index 011048d2a..88c7bb2e1 100644 --- a/nuttx/Documentation/NuttxPortingGuide.html +++ b/nuttx/Documentation/NuttxPortingGuide.html @@ -12,7 +12,7 @@ <h1><big><font color="#3c34ec"> <i>NuttX RTOS Porting Guide</i> </font></big></h1> - <p>Last Updated: August 21, 2014</p> + <p>Last Updated: August 22, 2014</p> </td> </tr> </table> @@ -107,13 +107,13 @@ <a href="#addrenv">4.4 Address Environments</a> <ul> <a href="#up_addrenv_create">4.4.1 <code>up_addrenv_create()</code></a></br> - <a href="#up_addrenv_vaddr">4.4.2 <code>up_addrenv_vaddr()</code></a></br> - <a href="#up_addrenv_select">4.4.3 <code>up_addrenv_select()</code></a></br> - <a href="#up_addrenv_restore">4.4.4 <code>up_addrenv_restore()</code></a></br> - <a href="#up_addrenv_destroy">4.4.5 <code>up_addrenv_destroy()</code></a></br> + <a href="#up_addrenv_destroy">4.4.2 <code>up_addrenv_destroy()</code></a></br> + <a href="#up_addrenv_vaddr">4.4.3 <code>up_addrenv_vaddr()</code></a></br> + <a href="#up_addrenv_select">4.4.4 <code>up_addrenv_select()</code></a></br> + <a href="#up_addrenv_restore">4.4.5 <code>up_addrenv_restore()</code></a></br> <a href="#up_addrenv_assign">4.4.6 <code>up_addrenv_assign()</code></a></br> - <a href="#up_addrenv_share">4.4.7 <code>up_addrenv_share()</code></a></br> - <a href="#up_addrenv_release">4.4.8 <code>up_addrenv_release()</code></a> + <a href="#up_addrenv_attach">4.4.7 <code>up_addrenv_attach()</code></a></br> + <a href="#up_addrenv_detach">4.4.8 <code>up_addrenv_detach()</code></a> </ul> <a href="#exports">4.5 APIs Exported by NuttX to Architecture-Specific Logic</a> <ul> @@ -2625,7 +2625,7 @@ int up_alarm_cancel(FAR struct timespec *ts); May be called from interrupt level handling or from the normal tasking level. iterrupts may need to be disabled internally to assure non-reentrancy. </ul> -<h5><a name="upalarmstart">4.3.4.4.5 <code>up_alarm_start()</code></a></h5> +<h5><a name="upalarmstart">4.3.4.4.4 <code>up_alarm_start()</code></a></h5> <p><b>Function Prototype</b>:<p> <ul><pre> #include <nuttx/arch.h> @@ -2930,8 +2930,7 @@ VxWorks provides the following comparable interface: <p> <b>Binary Loader Support</b>. These are low-level interfaces used in <code>binfmt/</code> to instantiate tasks with address environments. - These interfaces all operate on type <code>task_addrenv_t</code> which is an abstract representation of a asks's address environment and must be defined in arch/arch.h if <code>CONFIG_ADDRENV</code> is defined. - These low-level interfaces include: + These interfaces all operate on type <code>group_addrenv_t</code> which is an abstract representation of a task group's address environment and the type must be defined in<code>arch/arch.h</code> if <code>CONFIG_ADDRENV</code> is defined. These low-level interfaces include: </p> <ul> <li> @@ -2939,24 +2938,24 @@ VxWorks provides the following comparable interface: Create an address environment. </li> <li> - <a href="#up_addrenv_vaddr">4.4.2 <code>up_addrenv_vaddr()</code></a>: + <a href="#up_addrenv_destroy">4.4.2 <code>up_addrenv_destroy()</code></a>: + Destroy an address environment. + </li> + <li> + <a href="#up_addrenv_vaddr">4.4.3 <code>up_addrenv_vaddr()</code></a>: Returns the virtual base address of the address environment. </li> <li> - <a href="#up_addrenv_select">4.4.3 <code>up_addrenv_select()</code></a>: + <a href="#up_addrenv_select">4.4.4 <code>up_addrenv_select()</code></a>: Instantiate an address environment. </li> <li> - <a href="#up_addrenv_restore">4.4.4 <code>up_addrenv_restore()</code></a>: + <a href="#up_addrenv_restore">4.4.5 <code>up_addrenv_restore()</code></a>: Restore an address environment. </li> <li> - <a href="#up_addrenv_destroy">4.4.5 <code>up_addrenv_destroy()</code></a>: - Destroy an address environment. - </li> - <li> <a href="#up_addrenv_assign">4.4.6 <code>up_addrenv_assign()</code></a>: - Assign an address environment to a TCB. + Assign an address environment to a thread. </li> </ul> </li> @@ -2964,31 +2963,30 @@ VxWorks provides the following comparable interface: <p> <b>Tasking Support</b>. Other interfaces must be provided to support higher-level interfaces used by the NuttX tasking logic. - These interfaces are* used by the functions in <code>sched/</code> and all operate on the TCB which as been assigned an address environment by <code>up_addrenv_assign()</code>. + These interfaces are* used by the functions in <code>sched/</code> and all operate on the task group which as been assigned an address environment by <code>up_addrenv_assign()</code>. </p> <ul> <li> - <a href="#up_addrenv_share">4.4.7 <code>up_addrenv_share()</code></a>: - Clone the address environment assigned to one TCB to another. + <a href="#up_addrenv_attach">4.4.7 <code>up_addrenv_attach()</code></a>: + Clone the group address environment assigned to a new thread. This operation is done when a pthread is created that share's the same address environment. </li> <li> - <a href="#up_addrenv_release">4.4.8 <code>up_addrenv_release()</code></a>: - Release the TCB's reference to an address environment when a task/thread exits. + <a href="#up_addrenv_detach">4.4.8 <code>up_addrenv_detach()</code></a>: + Release the thread's reference to a group address environment when a task/thread exits. </li> </ul> </li> </ol> - <h3><a name="up_addrenv_create">4.4.1 <code>up_addrenv_create()</code></a></h3> <p><b>Function Prototype</b>:</p> <ul> - <code>int up_addrenv_create(size_t envsize, FAR task_addrenv_t *addrenv);</code> + <code>int up_addrenv_create(size_t envsize, FAR group_addrenv_t *addrenv);</code> </ul> <p><b>Description</b>:</p> <ul> - This function is called from the binary loader logic when a new task is created in order to instantiate an address environment for the task. + This function is called when a new task is created in order to instantiate an address environment for the new task group. <code>up_addrenv_create()</code> is essentially the allocator of the physical memory for the new task. </ul> <p><b>Input Parameters</b>:</p> @@ -3001,81 +2999,81 @@ VxWorks provides the following comparable interface: Zero (<code>OK</code>) on success; a negated <code>errno</code> value on failure. </ul> -<h3><a name="up_addrenv_vaddr">4.4.2 <code>up_addrenv_vaddr()</code></a></h3> +<h3><a name="up_addrenv_destroy">4.4.2 <code>up_addrenv_destroy()</code></a></h3> <p><b>Function Prototype</b>:<p> <ul> - <code>int up_addrenv_vaddr(FAR task_addrenv_t addrenv, FAR void **vaddr);</code> + <code>int up_addrenv_destroy(group_addrenv_t addrenv);</code> </ul> <p><b>Description</b>:</p> <ul> - Return the virtual address associated with the newly create address environment. - This function is used by the binary loaders in order get an address that can be used to initialize the new task. + This function is called when a final thread leaves the task group and the task group is destroyed. This function then destroys the defunct address environment, releasing the underlying physical memory allocated by <code>up_addrenv_create()</code>. </ul> <p><b>Input Parameters</b>:</p> <ul> <li><code>addrenv</code>: The representation of the task address environment previously returned by up_addrenv_create.</li> - <li><code>vaddr</code>: The location to return the virtual address.</li> </ul> <p><b>Returned Value</b>:</p> <ul> Zero (<code>OK</code>) on success; a negated <code>errno</code> value on failure. </ul> -<h3><a name="up_addrenv_select">4.4.3 <code>up_addrenv_select()</code></a></h3> +<h3><a name="up_addrenv_vaddr">4.4.3 <code>up_addrenv_vaddr()</code></a></h3> <p><b>Function Prototype</b>:<p> <ul> - <code>int up_addrenv_select(task_addrenv_t addrenv, hw_addrenv_t *oldenv);</code> + <code>int up_addrenv_vaddr(FAR group_addrenv_t addrenv, FAR void **vaddr);</code> </ul> <p><b>Description</b>:</p> <ul> - After an address environment has been established for a task (via <code>up_addrenv_create())</code>, this function may be called to to instantiate that address environment in the virtual address space. - This might be necessary, for example, to load the code for the task from a file or to access address environment private data. + Return the virtual address associated with the newly create address environment. + This function is used by the binary loaders in order get an address that can be used to initialize the new task. </ul> <p><b>Input Parameters</b>:</p> <ul> <li><code>addrenv</code>: The representation of the task address environment previously returned by up_addrenv_create.</li> - <li><code>oldenv</code>: - The address environment that was in place before <code>up_addrenv_select()</code> was called. - This may be used with <code>up_addrenv_restore()</code> to restore the original address environment that was in place before <code>up_addrenv_select()</code> was called. - Note that this may be a task agnostic, hardware representation that is different from <code>task_addrenv_t</code>. - </li> + <li><code>vaddr</code>: The location to return the virtual address.</li> </ul> <p><b>Returned Value</b>:</p> <ul> Zero (<code>OK</code>) on success; a negated <code>errno</code> value on failure. </ul> -<h3><a name="up_addrenv_restore">4.4.4 <code>up_addrenv_restore()</code></a></h3> +<h3><a name="up_addrenv_select">4.4.4 <code>up_addrenv_select()</code></a></h3> <p><b>Function Prototype</b>:<p> <ul> - <code>int up_addrenv_restore(hw_addrenv_t oldenv);</code> + <code>int up_addrenv_select(group_addrenv_t addrenv, hw_addrenv_t *oldenv);</code> </ul> <p><b>Description</b>:</p> <ul> - After an address environment has been temporarily instantiated by <code>up_addrenv_select</code>, - this function may be called to to restore the original address environment. + After an address environment has been established for a task (via <code>up_addrenv_create())</code>, this function may be called to to instantiate that address environment in the virtual address space. + This might be necessary, for example, to load the code for the task from a file or to access address environment private data. </ul> <p><b>Input Parameters</b>:</p> <ul> - <li><code>oldenv</code>: The hardware representation of the address environment previously returned by <code>up_addrenv_select()</code>.</li> + <li><code>addrenv</code>: The representation of the task address environment previously returned by up_addrenv_create.</li> + <li><code>oldenv</code>: + The address environment that was in place before <code>up_addrenv_select()</code> was called. + This may be used with <code>up_addrenv_restore()</code> to restore the original address environment that was in place before <code>up_addrenv_select()</code> was called. + Note that this may be a task agnostic, hardware representation that is different from <code>group_addrenv_t</code>. + </li> </ul> <p><b>Returned Value</b>:</p> <ul> Zero (<code>OK</code>) on success; a negated <code>errno</code> value on failure. </ul> -<h3><a name="up_addrenv_destroy">4.4.5 <code>up_addrenv_destroy()</code></a></h3> +<h3><a name="up_addrenv_restore">4.4.5 <code>up_addrenv_restore()</code></a></h3> <p><b>Function Prototype</b>:<p> <ul> - <code>int up_addrenv_destroy(task_addrenv_t addrenv);</code> + <code>int up_addrenv_restore(hw_addrenv_t oldenv);</code> </ul> <p><b>Description</b>:</p> <ul> - Called from the binary loader loader during error handling to destroy the address environment previously created by <code>up_addrenv_create()</code>. + After an address environment has been temporarily instantiated by <code>up_addrenv_select</code>, + this function may be called to to restore the original address environment. </ul> <p><b>Input Parameters</b>:</p> <ul> - <li><code>addrenv</code>: The representation of the task address environment previously returned by up_addrenv_create.</li> + <li><code>oldenv</code>: The hardware representation of the address environment previously returned by <code>up_addrenv_select()</code>.</li> </ul> <p><b>Returned Value</b>:</p> <ul> @@ -3085,55 +3083,60 @@ VxWorks provides the following comparable interface: <h3><a name="up_addrenv_assign">4.4.6 <code>up_addrenv_assign()</code></a></h3> <p><b>Function Prototype</b>:<p> <ul> - <code>int up_addrenv_assign(task_addrenv_t addrenv, FAR struct tcb_s *tcb);</code> + <code>int up_addrenv_assign(group_addrenv_t addrenv, FAR struct task_group_s *group);</code> </ul> <p><b>Description</b>:</p> <ul> - Assign an address environment to a TCB. + Assign an address environment to a new task group. </ul> <p><b>Input Parameters</b>:</p> <ul> - <li><code>addrenv</code>: The representation of the task address environment previously returned by up_addrenv_create.</li> - <li><code>tcb</code>: The TCB of the task to receive the address environment.</li> + <li><code>addrenv</code>: The representation of the group address environment previously returned by <code>up_addrenv_create</code>.</li> + <li><code>group</code>: The new task group to receive the address environment.</li> </ul> <p><b>Returned Value</b>:</p> <ul> Zero (<code>OK</code>) on success; a negated <code>errno</code> value on failure. </ul> -<h3><a name="up_addrenv_share">4.4.7 <code>up_addrenv_share()</code></a></h3> +<h3><a name="up_addrenv_attach">4.4.7 <code>up_addrenv_attach()</code></a></h3> <p><b>Function Prototype</b>:<p> <ul> - <code>int up_addrenv_share(FAR const struct tcb_s *ptcb, FAR struct tcb_s *ctcb);</code> + <code>int up_addrenv_attach(FAR struct task_group_s *group, FAR struct tcb_s *tcb);</code> </ul> <p><b>Description</b>:</p> <ul> - This function is called from the core scheduler logic when a thread is created that needs to share the address environment of its parent task. - In this case, the parent's address environment needs to be "cloned" for the child thread. + <p> + This function is called from the core scheduler logic when a thread is created that needs to share the address environment of its task group. + In this case, the group's address environment may need to be "cloned" for the child thread. + </p> + <p> + NOTE: In most platforms, nothing will need to be done in this case. + Simply being a member of the group that has the address environment may be sufficient. + </p> </ul> <p><b>Input Parameters</b>:</p> <ul> - <li><code>ptcb</code>: The TCB of the parent task that has the address environment.</li> - <li><code>ctcb</code>: The TCB of the child thread needing the address environment.</li> + <li><code>group</code>: The task group to which the new thread belongs.</li> + <li><code>ctcb</code>: The TCB of the thread needing the address environment.</li> </ul> <p><b>Returned Value</b>:</p> <ul> Zero (<code>OK</code>) on success; a negated <code>errno</code> value on failure. </ul> -<h3><a name="up_addrenv_release">4.4.8 <code>up_addrenv_release()</code></a></h3> +<h3><a name="up_addrenv_detach">4.4.8 <code>up_addrenv_detach()</code></a></h3> <p><b>Function Prototype</b>:<p> <ul> - <code>int up_addrenv_release(FAR struct tcb_s *tcb);</code> + <code>int up_addrenv_detach(FAR struct task_group_s *group, FAR struct task_group_s *tcb);</code> </ul> <p><b>Description</b>:</p> <ul> - This function is called when a task or thread exits in order to release its reference to an address environment. - When there are no further references to an address environment, that address environment should - be destroyed. + This function is called when a task or thread exits in order to release its reference to an address environment. The address environment, however, should persist until up_addrenv_destroy() is called when the task group is itself destroyed. Any resources unique to this thread may be destroyed now. </ul> <p><b>Input Parameters</b>:</p> <ul> + <li><code>group</code>: The group to which the thread belonged.</li> <li><code>tcb</code>: The TCB of the task or thread whose the address environment will be released.</li> </ul> <p><b>Returned Value</b>:</p> diff --git a/nuttx/arch/z80/include/z180/arch.h b/nuttx/arch/z80/include/z180/arch.h index d7cf82a26..72306b930 100644 --- a/nuttx/arch/z80/include/z180/arch.h +++ b/nuttx/arch/z80/include/z180/arch.h @@ -1,6 +1,5 @@ /**************************************************************************** * arch/z80/arch.h - * arch/chip/arch.h * * Copyright (C) 2012 Gregory Nutt. All rights reserved. * Author: Gregory Nutt <gnutt@nuttx.org> @@ -73,7 +72,7 @@ typedef uint8_t hw_addrenv_t; */ struct z180_cbr_s; -typedef FAR struct z180_cbr_s *task_addrenv_t; +typedef FAR struct z180_cbr_s *group_addrenv_t; #endif /**************************************************************************** diff --git a/nuttx/arch/z80/include/z180/irq.h b/nuttx/arch/z80/include/z180/irq.h index 1d0c27cb4..ba809bad8 100644 --- a/nuttx/arch/z80/include/z180/irq.h +++ b/nuttx/arch/z80/include/z180/irq.h @@ -173,7 +173,7 @@ typedef uint16_t chipreg_t; struct z180_cbr_s { uint8_t cbr; /* The CBR value used by the thread */ - uint8_t crefs; /* The number of threads sharing this CBR value */ + uint8_t crefs; /* The number of task groups using this CBR value (0 or 1) */ uint8_t pages; /* The number of 4KB pages of physical memory in the allocation */ }; @@ -183,10 +183,6 @@ struct z180_cbr_s struct xcptcontext { - /* CBR allocation */ - - FAR struct z180_cbr_s *cbr; - /* Register save area */ chipreg_t regs[XCPTCONTEXT_REGS]; diff --git a/nuttx/arch/z80/src/z180/z180_mmu.c b/nuttx/arch/z80/src/z180/z180_mmu.c index 4306eaf5f..c54fda148 100644 --- a/nuttx/arch/z80/src/z180/z180_mmu.c +++ b/nuttx/arch/z80/src/z180/z180_mmu.c @@ -1,7 +1,7 @@ /**************************************************************************** * arch/z80/src/z180/z180_mmu.c * - * Copyright (C) 2012 Gregory Nutt. All rights reserved. + * Copyright (C) 2012, 2014 Gregory Nutt. All rights reserved. * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without @@ -180,36 +180,37 @@ return g_physhandle ? OK : -ENOMEM; * Address Environment Interfaces * * Low-level interfaces used in binfmt/ to instantiate tasks with address - * environments. These interfaces all operate on task_addrenv_t which is an - * abstract representation of the address environment and must be provided - * by arch/arch.h is CONFIG_ADDRENV is defined. + * environments. These interfaces all operate on type group_addrenv_t which + * is an abstract representation of a task group's address environment and + * must be defined in arch/arch.h if CONFIG_ADDRENV is defined. * * up_addrenv_create - Create an address environment + * up_addrenv_destroy - Destroy an address environment. * up_addrenv_vaddr - Returns the virtual base address of the address * environment * up_addrenv_select - Instantiate an address environment - * up_addrenv_destroy - Destroy an address environment. - * up_addrenv_assign - Assign an address environment to a TCB + * up_addrenv_restore - Restore an address environment + * up_addrenv_assign - Assign an address environment to a group * * Higher-level interfaces used by the tasking logic. These interfaces are - * used by the functions in sched/ and all operate on the TCB which as been - * assigned an address environment by up_addrenv_assign(). + * used by the functions in sched/ and all operate on the thread which whose + * group been assigned an address environment by up_addrenv_assign(). * - * up_addrenv_share - Clone the address environment assigned to one TCB + * up_addrenv_attach - Clone the address environment assigned to one TCB * to another. This operation is done when a pthread * is created that share's the same address * environment. - * up_addrenv_release - Release the TCBs reference to an address - * environment when a task/thread exists. + * up_addrenv_detach - Release the threads reference to an address + * environment when a task/thread exits. * ****************************************************************************/ /**************************************************************************** * Name: up_addrenv_create * * Description: - * This function is called from the binary loader logic when a new - * task is created in order to instantiate an address environment for the - * task. up_addrenv_create is essentially the allocator of the physical + * This function is called when a new task is created in order to + * instantiate an address environment for the new task group. + * up_addrenv_create() is essentially the allocator of the physical * memory for the new task. * * Input Parameters: @@ -223,7 +224,7 @@ return g_physhandle ? OK : -ENOMEM; * ****************************************************************************/ -int up_addrenv_create(size_t envsize, FAR task_addrenv_t *addrenv) +int up_addrenv_create(size_t envsize, FAR group_addrenv_t *addrenv) { FAR struct z180_cbr_s *cbr; irqstate_t flags; @@ -280,7 +281,7 @@ int up_addrenv_create(size_t envsize, FAR task_addrenv_t *addrenv) cbr->cbr = (uint8_t)alloc; cbr->pages = (uint8_t)npages; - *addrenv = (task_addrenv_t)cbr; + *addrenv = (group_addrenv_t)cbr; irqrestore(flags); return OK; @@ -294,6 +295,42 @@ errout_with_irq: } /**************************************************************************** + * Name: up_addrenv_destroy + * + * Description: + * This function is called when a final thread leaves the task group and + * the task group is destroyed. This function then destroys the defunct + * address environment, releasing the underlying physical memory. + * + * Input Parameters: + * addrenv - The address environment to be destroyed. + * + * Returned Value: + * Zero (OK) on success; a negated errno value on failure. + * + ****************************************************************************/ + +int up_addrenv_destroy(group_addrenv_t addrenv) +{ + FAR struct z180_cbr_s *cbr = (FAR struct z180_cbr_s *)addrenv; + + DEBUGASSERT(cbr); + + /* Free the physical address space backing up the mapping */ + +#ifdef CONFIG_GRAN_SINGLE + gran_free((FAR void *)cbr->cbr, cbr->pages); +#else + gran_free(g_physhandle, (FAR void *)cbr->cbr, cbr->pages); +#endif + + /* And make the CBR structure available for re-use */ + + z180_mmu_freecbr(cbr); + return OK; +} + +/**************************************************************************** * Name: up_addrenv_vaddr * * Description: @@ -311,7 +348,7 @@ errout_with_irq: * ****************************************************************************/ -int up_addrenv_vaddr(FAR task_addrenv_t addrenv, FAR void **vaddr) +int up_addrenv_vaddr(FAR group_addrenv_t addrenv, FAR void **vaddr) { return CONFIG_Z180_COMMON1AREA_VIRTBASE; } @@ -334,14 +371,14 @@ int up_addrenv_vaddr(FAR task_addrenv_t addrenv, FAR void **vaddr) * This may be used with up_addrenv_restore() to restore the original * address environment that was in place before up_addrenv_select() was * called. Note that this may be a task agnostic, hardware - * representation that is different from task_addrenv_t. + * representation that is different from group_addrenv_t. * * Returned Value: * Zero (OK) on success; a negated errno value on failure. * ****************************************************************************/ -int up_addrenv_select(task_addrenv_t addrenv, hw_addrenv_t *oldenv) +int up_addrenv_select(group_addrenv_t addrenv, hw_addrenv_t *oldenv) { FAR struct z180_cbr_s *cbr = (FAR struct z180_cbr_s *)addrenv; irqstate_t flags; @@ -384,126 +421,75 @@ int up_addrenv_restore(hw_addrenv_t oldenv) } /**************************************************************************** - * Name: up_addrenv_destroy - * - * Description: - * Called from the binary loader loader during error handling to destroy - * the address environment previously created by up_addrenv_create(). - * - * Input Parameters: - * addrenv - The representation of the task address environment previously - * returned by up_addrenv_create. - * - * Returned Value: - * Zero (OK) on success; a negated errno value on failure. - * - ****************************************************************************/ - -int up_addrenv_destroy(task_addrenv_t addrenv) -{ - FAR struct z180_cbr_s *cbr = (FAR struct z180_cbr_s *)addrenv; - - DEBUGASSERT(cbr); - - /* Free the physical address space backing up the mapping */ - -#ifdef CONFIG_GRAN_SINGLE - gran_free((FAR void *)cbr->cbr, cbr->pages); -#else - gran_free(g_physhandle, (FAR void *)cbr->cbr, cbr->pages); -#endif - - /* And make the CBR structure available for re-use */ - - z180_mmu_freecbr(cbr); - return OK; -} - -/**************************************************************************** * Name: up_addrenv_assign * * Description: - * Assign an address environment to a TCB. + * Assign an address environment to a task group. * * Input Parameters: * addrenv - The representation of the task address environment previously - * returned by up_addrenv_create. - * tcb - The TCB of the task to receive the address environment. + * returned by up_addrenv_create(). + * group - The task group to receive the address environment. * * Returned Value: * Zero (OK) on success; a negated errno value on failure. * ****************************************************************************/ -int up_addrenv_assign(task_addrenv_t addrenv, FAR struct tcb_s *tcb) +int up_addrenv_assign(group_addrenv_t addrenv, FAR struct task_group_s *group) { - FAR struct z180_cbr_s *cbr = (FAR struct z180_cbr_s *)addrenv; - /* Make sure that there is no address environment in place on this TCB */ - DEBUGASSERT(cbr && tcb->xcp.cbr == NULL); + DEBUGASSERT(addrenv && group->addrenv == NULL); - /* Save the CBR strucure in the TCB. This is an atomic operation so no + /* Save the CBR structure in the group. This is an atomic operation so no * special precautions should be needed. */ - tcb->xcp.cbr = cbr; + group->addrenv = addrenv; return OK; } /**************************************************************************** - * Name: up_addrenv_share + * Name: up_addrenv_attach * * Description: * This function is called from the core scheduler logic when a thread - * is created that needs to share the address ennvironment of its parent - * task. In this case, the parent's address environment needs to be - * "cloned" for the child. + * is created that needs to share the address environment of its task + * group. * * Input Parameters: - * ptcb - The TCB of the parent task that has the address environment. - * ctcb - The TCB of the child thread needing the address environment. + * group - The task group to which the new thread belongs. + * tcb - The tcb of the thread needing the address environment. * * Returned Value: * Zero (OK) on success; a negated errno value on failure. * ****************************************************************************/ -int up_addrenv_share(FAR const struct tcb_s *ptcb, FAR struct tcb_s *ctcb) +int up_addrenv_attach(FAR struct task_group_s *group, FAR struct tcb_s *tcb) { - irqstate_t flags; - - /* Make sure that the child has no address environment. It is okay if - * if the parent does not have one. - */ + /* There is nothing that needs to be done */ - DEBUGASSERT(ctcb->xcp.cbr == NULL); - - flags = irqsave(); - if (ptcb->xcp.cbr) - { - /* Clone the CBR by incrementing the reference counting and saving a - * copy in the child thread's TCB. - */ - - ptcb->xcp.cbr->crefs++; - ctcb->xcp.cbr = ptcb->xcp.cbr; - } - - irqrestore(flags); return OK; } /**************************************************************************** - * Name: up_addrenv_release + * Name: up_addrenv_detach * * Description: * This function is called when a task or thread exits in order to release - * its reference to an address environment. When there are no further - * references to an address environment, that address environment should - * be destroyed. + * its reference to an address environment. The address environment, + * however, should persist until up_addrenv_destroy() is called when the + * task group is itself destroyed. Any resources unique to this thread + * may be destroyed now. + * + * NOTE: In some platforms, nothing will need to be done in this case. + * Simply being a member of the group that has the address environment + * may be sufficient. * * Input Parameters: + * group - The group to which the thread belonged. * tcb - The TCB of the task or thread whose the address environment will * be released. * @@ -512,39 +498,10 @@ int up_addrenv_share(FAR const struct tcb_s *ptcb, FAR struct tcb_s *ctcb) * ****************************************************************************/ -int up_addrenv_release(FAR struct tcb_s *tcb) +int up_addrenv_detach(FAR struct task_group_s *group, + FAR struct task_group_s *tcb); { - FAR struct z180_cbr_s *cbr; - irqstate_t flags; - - /* Check if the task has an address environment. */ - - flags = irqsave(); - cbr = tcb->xcp.cbr; - if (cbr) - { - /* Nullify the reference to the CBR structure and decrement the number - * of references on the CBR. - */ - - tcb->xcp.cbr = NULL; - - /* If the reference count would decrement to zero, then free the CBR - * structure. - */ - - if (cbr->crefs <= 1) - { - up_addrenv_destroy(cbr); - } - else - { - /* Otherwise, just decrement the reference count */ - - cbr->crefs--; - } - } + /* There is nothing that needs to be done */ - irqrestore(flags); return OK; } diff --git a/nuttx/binfmt/binfmt_execmodule.c b/nuttx/binfmt/binfmt_execmodule.c index 13c692018..c765724bd 100644 --- a/nuttx/binfmt/binfmt_execmodule.c +++ b/nuttx/binfmt/binfmt_execmodule.c @@ -1,7 +1,7 @@ /**************************************************************************** * binfmt/binfmt_execmodule.c * - * Copyright (C) 2009, 2013 Gregory Nutt. All rights reserved. + * Copyright (C) 2009, 2013-2014 Gregory Nutt. All rights reserved. * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without @@ -205,10 +205,10 @@ int exec_module(FAR const struct binary_s *binp) up_initial_state(&tcb->cmn); #endif - /* Assign the address environment to the task */ + /* Assign the address environment to the new task group */ #ifdef CONFIG_ADDRENV - ret = up_addrenv_assign(binp->addrenv, &tcb->cmn); + ret = up_addrenv_assign(binp->addrenv, tcb->group); if (ret < 0) { err = -ret; diff --git a/nuttx/include/nuttx/arch.h b/nuttx/include/nuttx/arch.h index 4fb3a193a..b1e972be5 100644 --- a/nuttx/include/nuttx/arch.h +++ b/nuttx/include/nuttx/arch.h @@ -669,27 +669,27 @@ void up_allocate_kheap(FAR void **heap_start, size_t *heap_size); * Address Environment Interfaces * * Low-level interfaces used in binfmt/ to instantiate tasks with address - * environments. These interfaces all operate on type task_addrenv_t which - * is an abstract representation of a task's address environment and must be - * defined in arch/arch.h if CONFIG_ADDRENV is defined. + * environments. These interfaces all operate on type group_addrenv_t which + * is an abstract representation of a task group's address environment and + * must be defined in arch/arch.h if CONFIG_ADDRENV is defined. * * up_addrenv_create - Create an address environment + * up_addrenv_destroy - Destroy an address environment. * up_addrenv_vaddr - Returns the virtual base address of the address * environment * up_addrenv_select - Instantiate an address environment * up_addrenv_restore - Restore an address environment - * up_addrenv_destroy - Destroy an address environment. - * up_addrenv_assign - Assign an address environment to a TCB + * up_addrenv_assign - Assign an address environment to a group * * Higher-level interfaces used by the tasking logic. These interfaces are - * used by the functions in sched/ and all operate on the TCB which as been - * assigned an address environment by up_addrenv_assign(). + * used by the functions in sched/ and all operate on the thread which whose + * group been assigned an address environment by up_addrenv_assign(). * - * up_addrenv_share - Clone the address environment assigned to one TCB + * up_addrenv_attach - Clone the address environment assigned to one TCB * to another. This operation is done when a pthread * is created that share's the same address * environment. - * up_addrenv_release - Release the TCBs reference to an address + * up_addrenv_detach - Release the threads reference to an address * environment when a task/thread exits. * ****************************************************************************/ @@ -697,9 +697,9 @@ void up_allocate_kheap(FAR void **heap_start, size_t *heap_size); * Name: up_addrenv_create * * Description: - * This function is called from the binary loader logic when a new - * task is created in order to instantiate an address environment for the - * task. up_addrenv_create is essentially the allocator of the physical + * This function is called when a new task is created in order to + * instantiate an address environment for the new task group. + * up_addrenv_create() is essentially the allocator of the physical * memory for the new task. * * Input Parameters: @@ -714,7 +714,27 @@ void up_allocate_kheap(FAR void **heap_start, size_t *heap_size); ****************************************************************************/ #ifdef CONFIG_ADDRENV -int up_addrenv_create(size_t envsize, FAR task_addrenv_t *addrenv); +int up_addrenv_create(size_t envsize, FAR group_addrenv_t *addrenv); +#endif + +/**************************************************************************** + * Name: up_addrenv_destroy + * + * Description: + * This function is called when a final thread leaves the task group and + * the task group is destroyed. This function then destroys the defunct + * address environment, releasing the underlying physical memory. + * + * Input Parameters: + * addrenv - The address environment to be destroyed. + * + * Returned Value: + * Zero (OK) on success; a negated errno value on failure. + * + ****************************************************************************/ + +#ifdef CONFIG_ADDRENV +int up_addrenv_destroy(group_addrenv_t addrenv); #endif /**************************************************************************** @@ -736,17 +756,17 @@ int up_addrenv_create(size_t envsize, FAR task_addrenv_t *addrenv); ****************************************************************************/ #ifdef CONFIG_ADDRENV -int up_addrenv_vaddr(FAR task_addrenv_t addrenv, FAR void **vaddr); +int up_addrenv_vaddr(FAR group_addrenv_t addrenv, FAR void **vaddr); #endif /**************************************************************************** * Name: up_addrenv_select * * Description: - * After an address environment has been established for a task (via + * After an address environment has been established for a task group (via * up_addrenv_create(). This function may be called to to instantiate * that address environment in the virtual address space. this might be - * necessary, for example, to load the code for the task from a file or + * necessary, for example, to load the code for the task group from a file or * to access address environment private data. * * Input Parameters: @@ -757,7 +777,7 @@ int up_addrenv_vaddr(FAR task_addrenv_t addrenv, FAR void **vaddr); * This may be used with up_addrenv_restore() to restore the original * address environment that was in place before up_addrenv_select() was * called. Note that this may be a task agnostic, hardware - * representation that is different from task_addrenv_t. + * representation that is different from group_addrenv_t. * * Returned Value: * Zero (OK) on success; a negated errno value on failure. @@ -765,15 +785,15 @@ int up_addrenv_vaddr(FAR task_addrenv_t addrenv, FAR void **vaddr); ****************************************************************************/ #ifdef CONFIG_ADDRENV -int up_addrenv_select(task_addrenv_t addrenv, hw_addrenv_t *oldenv); +int up_addrenv_select(group_addrenv_t addrenv, hw_addrenv_t *oldenv); #endif /**************************************************************************** * Name: up_addrenv_restore * * Description: - * After an address environment has been temporarilty instantiated by - * up_addrenv_select, this function may be called to to restore the + * After an address environment has been temporarily instantiated by + * up_addrenv_select(), this function may be called to to restore the * original address environment. * * Input Parameters: @@ -790,35 +810,15 @@ int up_addrenv_restore(hw_addrenv_t oldenv); #endif /**************************************************************************** - * Name: up_addrenv_destroy - * - * Description: - * Called from the binary loader loader during error handling to destroy - * the address environment previously created by up_addrenv_create(). - * - * Input Parameters: - * addrenv - The representation of the task address environment previously - * returned by up_addrenv_create. - * - * Returned Value: - * Zero (OK) on success; a negated errno value on failure. - * - ****************************************************************************/ - -#ifdef CONFIG_ADDRENV -int up_addrenv_destroy(task_addrenv_t addrenv); -#endif - -/**************************************************************************** * Name: up_addrenv_assign * * Description: - * Assign an address environment to a TCB. + * Assign an address environment to a new task group. * * Input Parameters: * addrenv - The representation of the task address environment previously - * returned by up_addrenv_create. - * tcb - The TCB of the task to receive the address environment. + * returned by up_addrenv_create(). + * group - The new task group to receive the address environment. * * Returned Value: * Zero (OK) on success; a negated errno value on failure. @@ -826,21 +826,24 @@ int up_addrenv_destroy(task_addrenv_t addrenv); ****************************************************************************/ #ifdef CONFIG_ADDRENV -int up_addrenv_assign(task_addrenv_t addrenv, FAR struct tcb_s *tcb); +int up_addrenv_assign(group_addrenv_t addrenv, FAR struct task_group_s *group); #endif /**************************************************************************** - * Name: up_addrenv_share + * Name: up_addrenv_attach * * Description: * This function is called from the core scheduler logic when a thread - * is created that needs to share the address ennvironment of its parent - * task. In this case, the parent's address environment needs to be - * "cloned" for the child. + * is created that needs to share the address environment of its task + * group. + * + * NOTE: In some platforms, nothing will need to be done in this case. + * Simply being a member of the group that has the address environment + * may be sufficient. * * Input Parameters: - * ptcb - The TCB of the parent task that has the address environment. - * ctcb - The TCB of the child thread needing the address environment. + * group - The task group to which the new thread belongs. + * tcb - The TCB of the thread needing the address environment. * * Returned Value: * Zero (OK) on success; a negated errno value on failure. @@ -848,19 +851,25 @@ int up_addrenv_assign(task_addrenv_t addrenv, FAR struct tcb_s *tcb); ****************************************************************************/ #ifdef CONFIG_ADDRENV -int up_addrenv_share(FAR const struct tcb_s *ptcb, FAR struct tcb_s *ctcb); +int up_addrenv_attach(FAR struct task_group_s *group, FAR struct tcb_s *tcb); #endif /**************************************************************************** - * Name: up_addrenv_release + * Name: up_addrenv_detach * * Description: * This function is called when a task or thread exits in order to release - * its reference to an address environment. When there are no further - * references to an address environment, that address environment should - * be destroyed. + * its reference to an address environment. The address environment, + * however, should persist until up_addrenv_destroy() is called when the + * task group is itself destroyed. Any resources unique to this thread + * may be destroyed now. + * + * NOTE: In some platforms, nothing will need to be done in this case. + * Simply being a member of the group that has the address environment + * may be sufficient. * * Input Parameters: + * group - The group to which the thread belonged. * tcb - The TCB of the task or thread whose the address environment will * be released. * @@ -870,7 +879,8 @@ int up_addrenv_share(FAR const struct tcb_s *ptcb, FAR struct tcb_s *ctcb); ****************************************************************************/ #ifdef CONFIG_ADDRENV -int up_addrenv_release(FAR struct tcb_s *tcb); +int up_addrenv_detach(FAR struct task_group_s *group, + FAR struct task_group_s *tcb); #endif /**************************************************************************** diff --git a/nuttx/include/nuttx/binfmt/binfmt.h b/nuttx/include/nuttx/binfmt/binfmt.h index 4e5052a7f..e9bc03a78 100644 --- a/nuttx/include/nuttx/binfmt/binfmt.h +++ b/nuttx/include/nuttx/binfmt/binfmt.h @@ -125,7 +125,7 @@ struct binary_s */ #ifdef CONFIG_ADDRENV - task_addrenv_t addrenv; /* Task address environment */ + group_addrenv_t addrenv; /* Task group address environment */ #endif size_t mapsize; /* Size of the mapped address region (needed for munmap) */ diff --git a/nuttx/include/nuttx/binfmt/elf.h b/nuttx/include/nuttx/binfmt/elf.h index 7bfe0d9a3..9f058d6e1 100644 --- a/nuttx/include/nuttx/binfmt/elf.h +++ b/nuttx/include/nuttx/binfmt/elf.h @@ -131,8 +131,8 @@ struct elf_loadinfo_s */ #ifdef CONFIG_ADDRENV - task_addrenv_t addrenv; /* Task address environment */ - hw_addrenv_t oldenv; /* Saved hardware address environment */ + group_addrenv_t addrenv; /* Task group address environment */ + hw_addrenv_t oldenv; /* Saved hardware address environment */ #endif uint16_t symtabidx; /* Symbol table section index */ diff --git a/nuttx/include/nuttx/binfmt/nxflat.h b/nuttx/include/nuttx/binfmt/nxflat.h index c87235c68..c3a7ce29d 100644 --- a/nuttx/include/nuttx/binfmt/nxflat.h +++ b/nuttx/include/nuttx/binfmt/nxflat.h @@ -103,13 +103,13 @@ struct nxflat_loadinfo_s */ #ifdef CONFIG_ADDRENV - task_addrenv_t addrenv; /* Task address environment */ - hw_addrenv_t oldenv; /* Saved hardware address environment */ + group_addrenv_t addrenv; /* Task group address environment */ + hw_addrenv_t oldenv; /* Saved hardware address environment */ #endif /* File descriptors */ - int filfd; /* Descriptor for the file being loaded */ + int filfd; /* Descriptor for the file being loaded */ /* This is a copy of the NXFLAT header (still in network order) */ diff --git a/nuttx/include/nuttx/sched.h b/nuttx/include/nuttx/sched.h index f0e52de3f..5ef5337fc 100644 --- a/nuttx/include/nuttx/sched.h +++ b/nuttx/include/nuttx/sched.h @@ -1,7 +1,7 @@ /******************************************************************************** * include/nuttx/sched.h * - * Copyright (C) 2007-2013 Gregory Nutt. All rights reserved. + * Copyright (C) 2007-2014 Gregory Nutt. All rights reserved. * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without @@ -99,6 +99,8 @@ # define HAVE_TASK_GROUP 1 /* Sockets */ # elif !defined(CONFIG_DISABLE_MQUEUE) # define HAVE_TASK_GROUP 1 /* Message queues */ +# elif defined(CONFIG_ADDRENV) +# define HAVE_TASK_GROUP 1 /* Address environment */ # endif #endif @@ -264,25 +266,24 @@ struct dspace_s /* struct task_group_s ***********************************************************/ /* All threads created by pthread_create belong in the same task group (along with - * the thread of the original task). struct task_group_s is a shared, "breakaway" - * structure referenced by each TCB. + * the thread of the original task). struct task_group_s is a shared structure + * referenced by the TCB of each thread that is a member of the task group. * * This structure should contain *all* resources shared by tasks and threads that * belong to the same task group: * * Child exit status - * Environment varibles + * Environment variables * PIC data space and address environments * File descriptors * FILE streams * Sockets - * - * Currenty, however, this implementation only applies to child exit status. + * Address environments. * * Each instance of struct task_group_s is reference counted. Each instance is - * created with a reference count of one. The reference incremeneted when each + * created with a reference count of one. The reference incremented when each * thread joins the group and decremented when each thread exits, leaving the - * group. When the refernce count decrements to zero, the struc task_group_s + * group. When the reference count decrements to zero, the struct task_group_s * is free. */ @@ -313,9 +314,9 @@ struct task_group_s FAR pid_t *tg_members; /* Members of the group */ #endif - /* atexit/on_exit support ****************************************************/ - #if defined(CONFIG_SCHED_ATEXIT) && !defined(CONFIG_SCHED_ONEXIT) + /* atexit support ************************************************************/ + # if defined(CONFIG_SCHED_ATEXIT_MAX) && CONFIG_SCHED_ATEXIT_MAX > 1 atexitfunc_t tg_atexitfunc[CONFIG_SCHED_ATEXIT_MAX]; # else @@ -324,6 +325,8 @@ struct task_group_s #endif #ifdef CONFIG_SCHED_ONEXIT + /* on_exit support ***********************************************************/ + # if defined(CONFIG_SCHED_ONEXIT_MAX) && CONFIG_SCHED_ONEXIT_MAX > 1 onexitfunc_t tg_onexitfunc[CONFIG_SCHED_ONEXIT_MAX]; FAR void *tg_onexitarg[CONFIG_SCHED_ONEXIT_MAX]; @@ -333,23 +336,22 @@ struct task_group_s # endif #endif +#if defined(CONFIG_SCHED_HAVE_PARENT) && defined(CONFIG_SCHED_CHILD_STATUS) /* Child exit status **********************************************************/ -#if defined(CONFIG_SCHED_HAVE_PARENT) && defined(CONFIG_SCHED_CHILD_STATUS) FAR struct child_status_s *tg_children; /* Head of a list of child status */ #endif +#if defined(CONFIG_SCHED_WAITPID) && !defined(CONFIG_SCHED_HAVE_PARENT) /* waitpid support ************************************************************/ /* Simple mechanism used only when there is no support for SIGCHLD */ -#if defined(CONFIG_SCHED_WAITPID) && !defined(CONFIG_SCHED_HAVE_PARENT) sem_t tg_exitsem; /* Support for waitpid */ int *tg_statloc; /* Location to return exit status */ #endif - /* Pthreads *******************************************************************/ - #ifndef CONFIG_DISABLE_PTHREAD + /* Pthreads *******************************************************************/ /* Pthread join Info: */ sem_t tg_joinsem; /* Mutually exclusive access to join data */ FAR struct join_s *tg_joinhead; /* Head of a list of join data */ @@ -357,15 +359,15 @@ struct task_group_s uint8_t tg_nkeys; /* Number pthread keys allocated */ #endif +#ifndef CONFIG_DISABLE_SIGNALS /* POSIX Signal Control Fields ************************************************/ -#ifndef CONFIG_DISABLE_SIGNALS sq_queue_t sigpendingq; /* List of pending signals */ #endif +#ifndef CONFIG_DISABLE_ENVIRON /* Environment variables ******************************************************/ -#ifndef CONFIG_DISABLE_ENVIRON size_t tg_envsize; /* Size of environment string allocation */ FAR char *tg_envp; /* Allocated environment strings */ #endif @@ -376,19 +378,19 @@ struct task_group_s * life of the PIC data is managed. */ +#if CONFIG_NFILE_DESCRIPTORS > 0 /* File descriptors ***********************************************************/ -#if CONFIG_NFILE_DESCRIPTORS > 0 struct filelist tg_filelist; /* Maps file descriptor to file */ #endif +#if CONFIG_NFILE_STREAMS > 0 /* FILE streams ***************************************************************/ /* In a flat, single-heap build. The stream list is allocated with this * structure. But kernel mode with a kernel allocator, it must be separately * allocated using a user-space allocator. */ -#if CONFIG_NFILE_STREAMS > 0 #if defined(CONFIG_NUTTX_KERNEL) && defined(CONFIG_MM_KERNEL_HEAP) FAR struct streamlist *tg_streamlist; #else @@ -396,16 +398,24 @@ struct task_group_s #endif #endif +#if CONFIG_NSOCKET_DESCRIPTORS > 0 /* Sockets ********************************************************************/ -#if CONFIG_NSOCKET_DESCRIPTORS > 0 struct socketlist tg_socketlist; /* Maps socket descriptor to socket */ #endif - /* POSIX Named Message Queue Fields *******************************************/ #ifndef CONFIG_DISABLE_MQUEUE + /* POSIX Named Message Queue Fields *******************************************/ + sq_queue_t tg_msgdesq; /* List of opened message queues */ #endif + +#ifdef CONFIG_ADDRENV + /* POSIX Named Message Queue Fields *******************************************/ + /* POSIX Named Message Queue Fields *******************************************/ + + group_addrenv_t addrenv; /* Task group address environment */ +#endif }; #endif @@ -508,7 +518,7 @@ struct tcb_s int pterrno; /* Current per-thread errno */ /* State save areas ***********************************************************/ - /* The form and content of these fields are processor-specific. */ + /* The form and content of these fields are platform-specific. */ struct xcptcontext xcp; /* Interrupt register save area */ diff --git a/nuttx/sched/pthread/pthread_create.c b/nuttx/sched/pthread/pthread_create.c index 9ee5cc5d9..85ec3c5d8 100644 --- a/nuttx/sched/pthread/pthread_create.c +++ b/nuttx/sched/pthread/pthread_create.c @@ -1,7 +1,7 @@ /**************************************************************************** * sched/pthread/pthread_create.c * - * Copyright (C) 2007-2009, 2011, 2013 Gregory Nutt. All rights reserved. + * Copyright (C) 2007-2009, 2011, 2013-2014 Gregory Nutt. All rights reserved. * Author: Gregory Nutt <gnutt@nuttx.org> * * Redistribution and use in source and binary forms, with or without @@ -254,11 +254,11 @@ int pthread_create(FAR pthread_t *thread, FAR pthread_attr_t *attr, return ENOMEM; } +#ifdef HAVE_TASK_GROUP /* Bind the parent's group to the new TCB (we have not yet joined the * group). */ -#ifdef HAVE_TASK_GROUP ret = group_bind(ptcb); if (ret < 0) { @@ -267,14 +267,11 @@ int pthread_create(FAR pthread_t *thread, FAR pthread_attr_t *attr, } #endif - /* Share the address environment of the parent task. NOTE: Only tasks - * created throught the nuttx/binfmt loaders may have an address - * environment. - */ - #ifdef CONFIG_ADDRENV - ret = up_addrenv_share((FAR const struct tcb_s *)g_readytorun.head, - (FAR struct tcb_s *)ptcb); + /* Share the address environment of the parent task group. */ + + ret = up_addrenv_attach(ptcb->group, + (FAR const struct tcb_s *)g_readytorun.head); if (ret < 0) { errcode = -ret; @@ -323,9 +320,9 @@ int pthread_create(FAR pthread_t *thread, FAR pthread_attr_t *attr, priority = SCHED_FIFO; } +#if CONFIG_RR_INTERVAL > 0 /* Get the scheduler policy for this thread */ -#if CONFIG_RR_INTERVAL > 0 policy = sched_getscheduler(0); if (policy == ERROR) { @@ -358,9 +355,9 @@ int pthread_create(FAR pthread_t *thread, FAR pthread_attr_t *attr, pthread_argsetup(ptcb, arg); +#ifdef HAVE_TASK_GROUP /* Join the parent's task group */ -#ifdef HAVE_TASK_GROUP ret = group_join(ptcb); if (ret < 0) { @@ -373,11 +370,11 @@ int pthread_create(FAR pthread_t *thread, FAR pthread_attr_t *attr, ptcb->joininfo = (FAR void *)pjoin; +#if CONFIG_RR_INTERVAL > 0 /* If round robin scheduling is selected, set the appropriate flag * in the TCB. */ -#if CONFIG_RR_INTERVAL > 0 if (policy == SCHED_RR) { ptcb->cmn.flags |= TCB_FLAG_ROUND_ROBIN; diff --git a/nuttx/sched/sched/sched_releasetcb.c b/nuttx/sched/sched/sched_releasetcb.c index 7c7eeae3a..3899911f3 100644 --- a/nuttx/sched/sched/sched_releasetcb.c +++ b/nuttx/sched/sched/sched_releasetcb.c @@ -193,10 +193,10 @@ int sched_releasetcb(FAR struct tcb_s *tcb, uint8_t ttype) /* Release this thread's reference to the address environment */ #ifdef CONFIG_ADDRENV - ret = up_addrenv_release(tcb); + ret = up_addrenv_detach(tcp->group, tcb); #endif - /* Leave the group (if we did not already leady in task_exithook.c) */ + /* Leave the group (if we did not already leave in task_exithook.c) */ #ifdef HAVE_TASK_GROUP group_leave(tcb); |