Diff
Not logged in

Differences From Artifact [d697355cab]:

To Artifact [18eb60c992]:


1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
/* 
 * tclWinThread.c --
 *
 *	This file implements the Windows-specific thread operations.
 *
 * Copyright (c) 1998 by Sun Microsystems, Inc.
 * Copyright (c) 1999 by Scriptics Corporation
 *
 * See the file "license.terms" for information on usage and redistribution
 * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
 *
 * RCS: @(#) $Id: tclWinThrd.c,v 1.26.2.6 2005/05/11 16:58:53 dgp Exp $
 */

#include "tclWinInt.h"

#include <fcntl.h>
#include <io.h>
#include <sys/stat.h>











|







1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
/* 
 * tclWinThread.c --
 *
 *	This file implements the Windows-specific thread operations.
 *
 * Copyright (c) 1998 by Sun Microsystems, Inc.
 * Copyright (c) 1999 by Scriptics Corporation
 *
 * See the file "license.terms" for information on usage and redistribution
 * of this file, and for a DISCLAIMER OF ALL WARRANTIES.
 *
 * RCS: @(#) $Id: tclWinThrd.c,v 1.26.2.7 2005/06/02 04:18:04 dgp Exp $
 */

#include "tclWinInt.h"

#include <fcntl.h>
#include <io.h>
#include <sys/stat.h>
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
} WinCondition;

/*
 * Additions by AOL for specialized thread memory allocator.
 */
#ifdef USE_THREAD_ALLOC
static int once;
static DWORD key;

typedef struct allocMutex {
    Tcl_Mutex        tlock;
    CRITICAL_SECTION wlock;
} allocMutex;
#endif








|







113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
} WinCondition;

/*
 * Additions by AOL for specialized thread memory allocator.
 */
#ifdef USE_THREAD_ALLOC
static int once;
static DWORD tlsKey;

typedef struct allocMutex {
    Tcl_Mutex        tlock;
    CRITICAL_SECTION wlock;
} allocMutex;
#endif

696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
    BOOL success;

    if (*keyPtr != NULL) {
	indexPtr = *(DWORD **)keyPtr;
	result = (VOID *)TlsGetValue(*indexPtr);
	if (result != NULL) {
#if defined(USE_THREAD_ALLOC) && !defined(TCL_MEM_DEBUG)
        if (indexPtr == &key) {
            TclpFreeAllocCache(result);
            return;
        }
#endif
	    ckfree((char *)result);
	    success = TlsSetValue(*indexPtr, (void *)NULL);
            if (!success) {







|







696
697
698
699
700
701
702
703
704
705
706
707
708
709
710
    BOOL success;

    if (*keyPtr != NULL) {
	indexPtr = *(DWORD **)keyPtr;
	result = (VOID *)TlsGetValue(*indexPtr);
	if (result != NULL) {
#if defined(USE_THREAD_ALLOC) && !defined(TCL_MEM_DEBUG)
        if (indexPtr == &tlsKey) {
            TclpFreeAllocCache(result);
            return;
        }
#endif
	    ckfree((char *)result);
	    success = TlsSetValue(*indexPtr, (void *)NULL);
            if (!success) {
1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149

    if (!once) {
	/*
	 * We need to make sure that TclpFreeAllocCache is called
	 * on each thread that calls this, but only on threads that
	 * call this.
	 */
    	key = TlsAlloc();
	once = 1;
	if (key == TLS_OUT_OF_INDEXES) {
	    Tcl_Panic("could not allocate thread local storage");
	}
    }

    result = TlsGetValue(key);
    if ((result == NULL) && (GetLastError() != NO_ERROR)) {
        Tcl_Panic("TlsGetValue failed from TclpGetAllocCache!");
    }
    return result;
}

void
TclpSetAllocCache(void *ptr)
{
    BOOL success;
    success = TlsSetValue(key, ptr);
    if (!success) {
        Tcl_Panic("TlsSetValue failed from TclpSetAllocCache!");
    }
}

void
TclpFreeAllocCache(void *ptr)
{
    BOOL success;

    if (ptr != NULL) {
        /*
         * Called by us in TclpFinalizeThreadData when a thread exits
         * and destroys the tsd key which stores allocator caches.
         */
        TclFreeAllocCache(ptr);
        success = TlsSetValue(key, NULL);
        if (!success) {
            panic("TlsSetValue failed from TclpFreeAllocCache!");
        }
    } else if (once) { 
        /*
         * Called by us in TclFinalizeThreadAlloc() during
         * the library finalization initiated from Tcl_Finalize()
         */   
        success = TlsFree(key);
        if (!success) {
            Tcl_Panic("TlsFree failed from TclpFreeAllocCache!");
        }
        once = 0; /* reset for next time. */
    }

}

#endif /* USE_THREAD_ALLOC */
#endif /* TCL_THREADS */







|

|




|










|
















|








|










1088
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106
1107
1108
1109
1110
1111
1112
1113
1114
1115
1116
1117
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134
1135
1136
1137
1138
1139
1140
1141
1142
1143
1144
1145
1146
1147
1148
1149

    if (!once) {
	/*
	 * We need to make sure that TclpFreeAllocCache is called
	 * on each thread that calls this, but only on threads that
	 * call this.
	 */
	tlsKey = TlsAlloc();
	once = 1;
	if (tlsKey == TLS_OUT_OF_INDEXES) {
	    Tcl_Panic("could not allocate thread local storage");
	}
    }

    result = TlsGetValue(tlsKey);
    if ((result == NULL) && (GetLastError() != NO_ERROR)) {
        Tcl_Panic("TlsGetValue failed from TclpGetAllocCache!");
    }
    return result;
}

void
TclpSetAllocCache(void *ptr)
{
    BOOL success;
    success = TlsSetValue(tlsKey, ptr);
    if (!success) {
        Tcl_Panic("TlsSetValue failed from TclpSetAllocCache!");
    }
}

void
TclpFreeAllocCache(void *ptr)
{
    BOOL success;

    if (ptr != NULL) {
        /*
         * Called by us in TclpFinalizeThreadData when a thread exits
         * and destroys the tsd key which stores allocator caches.
         */
        TclFreeAllocCache(ptr);
        success = TlsSetValue(tlsKey, NULL);
        if (!success) {
            panic("TlsSetValue failed from TclpFreeAllocCache!");
        }
    } else if (once) { 
        /*
         * Called by us in TclFinalizeThreadAlloc() during
         * the library finalization initiated from Tcl_Finalize()
         */   
        success = TlsFree(tlsKey);
        if (!success) {
            Tcl_Panic("TlsFree failed from TclpFreeAllocCache!");
        }
        once = 0; /* reset for next time. */
    }

}

#endif /* USE_THREAD_ALLOC */
#endif /* TCL_THREADS */