aboutsummaryrefslogtreecommitdiff
path: root/pthreads/manual/pthread_key_create.html
diff options
context:
space:
mode:
Diffstat (limited to 'pthreads/manual/pthread_key_create.html')
-rw-r--r--pthreads/manual/pthread_key_create.html211
1 files changed, 211 insertions, 0 deletions
diff --git a/pthreads/manual/pthread_key_create.html b/pthreads/manual/pthread_key_create.html
new file mode 100644
index 000000000..5ecca6995
--- /dev/null
+++ b/pthreads/manual/pthread_key_create.html
@@ -0,0 +1,211 @@
+<!DOCTYPE HTML PUBLIC "-//W3C//DTD HTML 4.0 Transitional//EN">
+<HTML>
+<HEAD>
+ <META HTTP-EQUIV="CONTENT-TYPE" CONTENT="text/html; charset=utf-8">
+ <TITLE>PTHREAD_SPECIFIC(3) manual page</TITLE>
+ <META NAME="GENERATOR" CONTENT="OpenOffice.org 1.1.3 (Linux)">
+ <META NAME="CREATED" CONTENT="20050504;18425400">
+ <META NAME="CHANGED" CONTENT="20050509;18220200">
+ <!-- manual page source format generated by PolyglotMan v3.2, -->
+ <!-- available at http://polyglotman.sourceforge.net/ -->
+</HEAD>
+<BODY LANG="en-GB" BGCOLOR="#ffffff" DIR="LTR">
+<H4>POSIX Threads for Windows – REFERENCE - <A HREF="http://sources.redhat.com/pthreads-win32">Pthreads-w32</A></H4>
+<P><A HREF="index.html">Reference Index</A></P>
+<P><A HREF="#toc">Table of Contents</A></P>
+<H2><A HREF="#toc0" NAME="sect0">Name</A></H2>
+<P>pthread_key_create, pthread_key_delete, pthread_setspecific,
+pthread_getspecific - management of thread-specific data
+</P>
+<H2><A HREF="#toc1" NAME="sect1">Synopsis</A></H2>
+<P><B>#include &lt;pthread.h&gt;</B>
+</P>
+<P><B>int pthread_key_create(pthread_key_t *</B><I>key</I><B>, void
+(*</B><I>destr_function</I><B>) (void *));</B>
+</P>
+<P><B>int pthread_key_delete(pthread_key_t </B><I>key</I><B>);</B>
+</P>
+<P><B>int pthread_setspecific(pthread_key_t </B><I>key</I><B>, const
+void *</B><I>pointer</I><B>);</B>
+</P>
+<P><B>void * pthread_getspecific(pthread_key_t </B><I>key</I><B>);</B>
+</P>
+<H2><A HREF="#toc2" NAME="sect2">Description</A></H2>
+<P>Programs often need global or static variables that have different
+values in different threads. Since threads share one memory space,
+this cannot be achieved with regular variables. Thread-specific data
+is the POSIX threads answer to this need.
+</P>
+<P>Each thread possesses a private memory block, the thread-specific
+data area, or TSD area for short. This area is indexed by TSD keys.
+The TSD area associates values of type <B>void *</B> to TSD keys. TSD
+keys are common to all threads, but the value associated with a given
+TSD key can be different in each thread.
+</P>
+<P>For concreteness, the TSD areas can be viewed as arrays of <B>void
+*</B> pointers, TSD keys as integer indices into these arrays, and
+the value of a TSD key as the value of the corresponding array
+element in the calling thread.
+</P>
+<P>When a thread is created, its TSD area initially associates <B>NULL</B>
+with all keys.
+</P>
+<P><B>pthread_key_create</B> allocates a new TSD key. The key is
+stored in the location pointed to by <I>key</I>. There is a limit of
+<B>PTHREAD_KEYS_MAX</B> on the number of keys allocated at a given
+time. The value initially associated with the returned key is <B>NULL</B>
+in all currently executing threads.
+</P>
+<P>The <I>destr_function</I> argument, if not <B>NULL</B>, specifies
+a destructor function associated with the key. When a thread
+terminates via <B>pthread_exit</B> or by cancellation, <I>destr_function</I>
+is called with arguments the value associated with the key in that
+thread. The <I>destr_function</I> is not called if that value is <B>NULL</B><SPAN STYLE="font-weight: medium">
+or the key has been deleted</SPAN>. The order in which destructor
+functions are called at thread termination time is unspecified.
+</P>
+<P>Before the destructor function is called, the <B>NULL</B> value is
+associated with the key in the current thread. A destructor function
+might, however, re-associate non- <B>NULL</B> values to that key or
+some other key. To deal with this, if after all the destructors have
+been called for all non- <B>NULL</B> values, there are still some
+non- <B>NULL</B> values with associated destructors, then the process
+is repeated.</P>
+<P><B>pthread_key_delete</B> deallocates a TSD key. It does not check
+whether non- <B>NULL</B> values are associated with that key in the
+currently executing threads, nor call the destructor function
+associated with the key.
+</P>
+<P><B>pthread_setspecific</B> changes the value associated with <I>key</I>
+in the calling thread, storing the given <I>pointer</I> instead.
+</P>
+<P><B>pthread_getspecific</B> returns the value currently associated
+with <I>key</I> in the calling thread.
+</P>
+<P>The routines <B>pthread_setspecific</B>, <B>pthread_getspecific</B>,
+and <B>pthread_key_delete</B> can be called from <I>destr_function</I>
+targeting any valid key including the key on which <I>destr_function</I>
+is currently operating. If <B>pthread_getspecific</B> is called on
+the key whose thread specific data is being destroyed, the value NULL
+is returned, unless <B>pthread_setspecific</B> was called previously
+on that key from within <I>destr_function</I> to set the value to
+non-NULL. For some implementations the effect of calling
+<B>pthread_setspecific</B> from within <I>destr_function</I> can be
+either memory leakage or infinite loops if <I>destr_function</I> has
+already been called at least <B>PTHREAD_DESTRUCTOR_ITERATIONS</B>
+times.</P>
+<P STYLE="font-weight: medium"><B>Pthreads-w32</B> stops running key
+<I>destr_function</I> routines after <B>PTHREAD_DESTRUCTOR_ITERATIONS</B>
+iterations, even if some non- <B>NULL</B> values with associated
+descriptors remain. If memory is allocated and associated with a key
+from within <I>destr_function</I>, that memory may not be reclaimed
+because that key's <I>destr_function</I>, may not run again.</P>
+<H2><A HREF="#toc3" NAME="sect3">Return Value</A></H2>
+<P><B>pthread_key_create</B>, <B>pthread_key_delete</B>, and
+<B>pthread_setspecific</B> return 0 on success and a non-zero error
+code on failure. If successful, <B>pthread_key_create</B> stores the
+newly allocated key in the location pointed to by its <I>key</I>
+argument.
+</P>
+<P><B>pthread_getspecific</B> returns the value associated with <I>key</I>
+on success, and <B>NULL</B> on error.
+</P>
+<H2><A HREF="#toc4" NAME="sect4">Errors</A></H2>
+<P><B>pthread_key_create</B> returns the following error code on
+error:
+</P>
+<DL>
+ <DL>
+ <DT STYLE="margin-right: 1cm; margin-bottom: 0.5cm"><B>EAGAIN</B>
+ </DT></DL>
+</DL>
+<BLOCKQUOTE STYLE="margin-left: 5cm">
+<B>PTHREAD_KEYS_MAX</B> keys are already allocated
+</BLOCKQUOTE>
+<DL>
+ <DL>
+ <DT STYLE="margin-right: 1cm; margin-bottom: 0.5cm"><B>ENOMEM</B>
+ </DT></DL>
+</DL>
+<BLOCKQUOTE STYLE="margin-left: 5cm">
+Insufficient memory to allocate the key.
+</BLOCKQUOTE>
+<P><B>pthread_key_delete</B> and <B>pthread_setspecific</B> return
+the following error code on error:
+</P>
+<DL>
+ <DL>
+ <DT STYLE="margin-right: 1cm; margin-bottom: 0.5cm"><B>EINVAL</B>
+ </DT><DD STYLE="margin-right: 1cm; margin-bottom: 0.5cm">
+ <I>key</I> is not a valid, allocated TSD key
+ </DD></DL>
+</DL>
+<P>
+<B>pthread_getspecific</B> returns <B>NULL</B> if <I>key</I> is not a
+valid, allocated TSD key.
+</P>
+<H2><A HREF="#toc5" NAME="sect5">Author</A></H2>
+<P>Xavier Leroy &lt;Xavier.Leroy@inria.fr&gt;
+</P>
+<P>Modified by Ross Johnson for use with <A HREF="http://sources.redhat.com/pthreads-win32">Pthreads-w32</A>.</P>
+<H2><A HREF="#toc6" NAME="sect6">See Also</A></H2>
+<P><A HREF="pthread_create.html">pthread_create(3)</A> ,
+<A HREF="pthread_exit.html">pthread_exit(3)</A> ,
+<A HREF="pthread_cancel.html">pthread_testcancel(3)</A> .
+</P>
+<H2><A HREF="#toc7" NAME="sect7">Example</A></H2>
+<P>The following code fragment allocates a thread-specific array of
+100 characters, with automatic reclamation at thread exit:
+</P>
+<BLOCKQUOTE><BR><BR>
+</BLOCKQUOTE>
+<PRE STYLE="margin-left: 1cm; margin-right: 1cm">/* Key for the thread-specific buffer */
+static pthread_key_t buffer_key;
+/* Once-only initialisation of the key */
+static pthread_once_t buffer_key_once = PTHREAD_ONCE_INIT;
+/* Allocate the thread-specific buffer */
+void buffer_alloc(void)
+{
+ pthread_once(&amp;buffer_key_once, buffer_key_alloc);
+ pthread_setspecific(buffer_key, malloc(100));
+}
+/* Return the thread-specific buffer */
+char * get_buffer(void)
+{
+ return (char *) pthread_getspecific(buffer_key);
+}
+/* Allocate the key */
+static void buffer_key_alloc()
+{
+ pthread_key_create(&amp;buffer_key, buffer_destroy);
+}
+/* Free the thread-specific buffer */
+static void buffer_destroy(void * buf)
+{
+ free(buf);
+}</PRE>
+<HR>
+<BLOCKQUOTE STYLE="margin-left: 0cm; margin-right: 0cm"><A NAME="toc"></A>
+<B>Table of Contents</B></BLOCKQUOTE>
+<UL>
+ <LI><BLOCKQUOTE STYLE="margin-bottom: 0cm"><A HREF="#sect0" NAME="toc0">Name</A>
+ </BLOCKQUOTE>
+ <LI><BLOCKQUOTE STYLE="margin-bottom: 0cm"><A HREF="#sect1" NAME="toc1">Synopsis</A>
+ </BLOCKQUOTE>
+ <LI><BLOCKQUOTE STYLE="margin-bottom: 0cm"><A HREF="#sect2" NAME="toc2">Description</A>
+ </BLOCKQUOTE>
+ <LI><BLOCKQUOTE STYLE="margin-bottom: 0cm"><A HREF="#sect3" NAME="toc3">Return
+ Value</A>
+ </BLOCKQUOTE>
+ <LI><BLOCKQUOTE STYLE="margin-bottom: 0cm"><A HREF="#sect4" NAME="toc4">Errors</A>
+ </BLOCKQUOTE>
+ <LI><BLOCKQUOTE STYLE="margin-bottom: 0cm"><A HREF="#sect5" NAME="toc5">Author</A>
+ </BLOCKQUOTE>
+ <LI><BLOCKQUOTE STYLE="margin-bottom: 0cm"><A HREF="#sect6" NAME="toc6">See
+ Also</A>
+ </BLOCKQUOTE>
+ <LI><BLOCKQUOTE><A HREF="#sect7" NAME="toc7">Example</A>
+ </BLOCKQUOTE>
+</UL>
+</BODY>
+</HTML> \ No newline at end of file