\input manualMacros.tex
\manBegin
\manPageInfo{RCI Reference Manual}{}{}
\manTitle{rciSharedMemory}{3}
\manSection{NAME}
{\tt \manName{rciSharedMemory}}, 
{\tt \manName{rciGlobalMemory}}, 
{\tt \manName{rciLocalMemory}},
{\tt \manName{rciSharedData}}
 -- RCI routines for setting up shared memory.
\manSection{USAGE}
\cverbatim
#include <rci.h>

void *rciSharedMemory (label, size, hostTd)
   const char *label;
   int size;
   RCI_DESC *hostTd;

void *rciGlobalMemory (label, size, unused, pool)
   const char *label;
   int size;
   unsigned long unused;
   int pool;

void *rciLocalMemory (label, size, hostTd)
   const char *label;
   int size;
   RCI_DESC *hostTd;

rciSharedData (addr, size, hostTd, accessMask)
   void *addr;
   int size;
   RCI_DESC *hostTd;
   unsigned long accessMask; @endcverbatim
\manSection{ARGUMENTS}
\manItem{{\tt label} --}
Name of the memory section; can be given as {\tt NULL}.
\manItem{{\tt size} --}
Size of the shared memory area, in bytes.
\manItem{{\tt hostTd} --}
Descriptor pointer for the task which will {\it host} the shared memory;
(i.e., the shared memory will be allocated from a pool 
that is quickly accessible to that task).
\manItem{{\tt pool} --}
Integer specifying where the memory should be allocated from. In the
present system, all shared memory sections are allocated from one
of the system's CPUs, hence pool should be a CPU number.
\manItem{{\tt addr} --}
Address of an existing area of memory to be mapped.
\manItem{{\tt unused} --}
Argument is not currently used.
\manItem{{\tt accessMask} --}
Bitmask describingn the tasks on which CPUs the memory will be mapped to.
The bitmask for any given task may be obtained from its task descriptor
using {\tt TASKMASK(td)}.
\manSection{RESTRICTIONS}
These routines must be called from the planning level.
\manSection{DESCRIPTION}
{\tt rciSharedMemory()} allocates a shared memory section of {\tt size} bytes,
zeros it, 
and returns a pointer to it.  ({\tt size} is rounded up to the nearest page
boundary.)
The section is private to the
planning task and the indicated control task. If {\tt label} is
not {\tt NULL}, the control task can
later obtain a pointer to the section by calling 
{\tt getSharedMemory()} with the label name. Alternatively, 
a pointer to the section can be obtained by calling
{\tt findSharedMemory()} with the value returned
by {\tt rciSharedMemory()} as a key.

{\tt rciGlobalMemory()} allocates a shared memory section of {\tt size} bytes
from the indicated {\tt pool} (which is nominally a CPU number), zeros it,
and returns a pointer to it.  (Again, {\tt size} is rounded up to the nearest
page boundary.)
The section is accessible to all tasks.
If {\tt label} is 
not {\tt NULL}, tasks can
later obtain a pointer to the section by calling 
{\tt getGlobalMemory()} with the label name. Alternatively, 
a pointer to the section can be obtained by calling
{\tt findGlobalMemory()} with the value returned
by {\tt rciGlobalMemory()} as a key.

{\tt rciLocalMemory()} allocates a memory section of {\tt size} bytes
of data private to
the task specified by {\tt td}, and returns a pointer to it
whose value is valid for the control task.
If {\tt label} is 
not {\tt NULL}, the task can
later obtain a pointer to the section by calling 
{\tt getLocalMemory()} with the label name. 

\manInset{\bf NOTE: Unlike the other routines, 
{\tt rciLocalMemory()} does not (at the time of this writing) zero its
allocated memory.}

{\tt rciSharedData()} sets up a shared section from within
the compile-time data region. This can be
used to create shared compiled variables.
The memory section described by {\tt addr} and {\tt size} must be part
of the program data segment, and specifically that part of the data segment
which has been marked for access by the {\it control} level (see
{\tt rcc(1)}). Both {\tt addr} and {\tt size} must
be page-aligned. Mapping will be set up among all tasks which are
indicated by the {\tt accessMask}.

\manInset{\bf IMPORTANT: Because the sharing
of the data segment is done on a per CPU basis, all tasks which are resident
on the CPUs covered by {\tt accessMask} will be mapped, whether they are
explicitly described by {\tt accessMask} or not.}

Shared memory sections cannot presently be deleted individually.
They are removed {\it en masse}, along with all the control tasks,
by the function {\tt rciClose()}.

\manSection{DIAGNOSTICS}

In the event of error, {\tt rciSharedMemory()}, {\tt rciGlobalMemory()},
and {\tt rciLocalMemory()}
return {\tt NULL}, while {\tt rciSharedData()} returns {\tt -1}.
Error information is reported on the {\it error\-Stack}(q.v.).

Returned error codes, accessible with {\tt getErrorCode()}, are:

\manItem{{\tt EDescriptor} --}
Invalid task descriptor.
\manItem{{\tt ENoPageAlign} --}
Argument to {\tt rciSharedData()} is not page aligned.
\manItem{{\tt ERange} --}
Section specified to {\tt rciSharedData()} does not lie in the {\it control
data} area, or overlaps an existing section.
\manItem{{\tt EMemory} --} 
Out of memory.
\manItem{{\tt EInternal} --}
Unexpected internal failure.

These routines will abort the program if called from the control level.
\manSection{CAVEATS}
Remember that {\tt rciSharedData()} will set up a shared region among
{\it all} tasks resident on the CPUs which host the tasks specified by {\tt
accessMask}.

There is no way
to delete a shared memory area once it has been created, except
through {\tt rciClose()}.
\manSection{SEE ALSO}
\raggedright
{\tt getSharedMemory(3)}, {\tt rciCreate(3)}, {\tt rciStart(3)},
{\tt errorStack(3)}.
\manEnd
\end
