summaryrefslogtreecommitdiffstats
path: root/unix/tclUnixThrd.c
diff options
context:
space:
mode:
authorhobbs <hobbs@noemail.net>2002-02-08 09:33:02 (GMT)
committerhobbs <hobbs@noemail.net>2002-02-08 09:33:02 (GMT)
commitf2cd5579a84160faf2402f50767c63e96343d113 (patch)
treeddc852096661b311770cc5de932600eeb110f05f /unix/tclUnixThrd.c
parent26f44ce50a1e99ec5912128536e1698d7b2257ab (diff)
downloadtcl-f2cd5579a84160faf2402f50767c63e96343d113.zip
tcl-f2cd5579a84160faf2402f50767c63e96343d113.tar.gz
tcl-f2cd5579a84160faf2402f50767c63e96343d113.tar.bz2
* unix/tclUnixPort.h:
* unix/tclUnixThrd.c: added thread-safe versions of readdir, localtime, gmtime and inet_ntoa for threaded build. (jgdavidson) FossilOrigin-Name: 66e9f4d6b4ef7c1907dce967a7da98539d8b762b
Diffstat (limited to 'unix/tclUnixThrd.c')
-rw-r--r--unix/tclUnixThrd.c71
1 files changed, 70 insertions, 1 deletions
diff --git a/unix/tclUnixThrd.c b/unix/tclUnixThrd.c
index ccffe3a..5086b2d 100644
--- a/unix/tclUnixThrd.c
+++ b/unix/tclUnixThrd.c
@@ -19,6 +19,18 @@
#include "tclPort.h"
#include "pthread.h"
+typedef struct ThreadSpecificData {
+ char nabuf[16];
+ struct tm gtbuf;
+ struct tm ltbuf;
+ struct {
+ struct dirent ent;
+ char name[PATH_MAX+1];
+ } rdbuf;
+} ThreadSpecificData;
+
+static Tcl_ThreadDataKey dataKey;
+
/*
* masterLock is used to serialize creation of mutexes, condition
* variables, and thread local storage.
@@ -760,8 +772,65 @@ TclpFinalizeCondition(condPtr)
*condPtr = NULL;
}
}
+
+/*
+ *----------------------------------------------------------------------
+ *
+ * TclpReaddir, TclpLocaltime, TclpGmtime, TclpInetNtoa --
+ *
+ * These procedures replace core C versions to be used in a
+ * threaded environment.
+ *
+ * Results:
+ * See documentation of C functions.
+ *
+ * Side effects:
+ * See documentation of C functions.
+ *
+ *----------------------------------------------------------------------
+ */
+struct dirent *
+TclpReaddir(DIR * dir)
+{
+ ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&dataKey);
+ struct dirent *ent;
+ ent = &tsdPtr->rdbuf.ent;
+ if (readdir_r(dir, ent, &ent) != 0) {
+ ent = NULL;
+ }
+ return ent;
+}
-#endif /* TCL_THREADS */
+struct tm *
+TclpLocaltime(time_t * clock)
+{
+ ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&dataKey);
+
+ return localtime_r(clock, &tsdPtr->ltbuf);
+}
+
+struct tm *
+TclpGmtime(time_t * clock)
+{
+ ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&dataKey);
+ return gmtime_r(clock, &tsdPtr->gtbuf);
+}
+
+char *
+TclpInetNtoa(struct in_addr addr)
+{
+ ThreadSpecificData *tsdPtr = TCL_TSD_INIT(&dataKey);
+ union {
+ unsigned long l;
+ unsigned char b[4];
+ } u;
+
+ u.l = (unsigned long) addr.s_addr;
+ sprintf(tsdPtr->nabuf, "%u.%u.%u.%u", u.b[0], u.b[1], u.b[2], u.b[3]);
+ return tsdPtr->nabuf;
+}
+
+#endif /* TCL_THREADS */