summaryrefslogtreecommitdiff
path: root/thirdparty/icu4c/common/ucln_imp.h
blob: 63a54c86f62414b7f837b59e95819398d72b28fc (plain)
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
132
133
134
135
136
137
138
139
140
141
142
143
144
145
146
147
148
149
150
151
152
153
154
155
156
157
158
159
160
161
162
163
164
165
166
167
168
169
170
171
172
173
174
175
176
177
178
179
180
181
182
// © 2016 and later: Unicode, Inc. and others.
// License & terms of use: http://www.unicode.org/copyright.html
/*
******************************************************************************
*
* Copyright (C) 2009-2011, International Business Machines
*                Corporation and others. All Rights Reserved.
*
******************************************************************************
*   file name:  ucln_imp.h
*   encoding:   UTF-8
*   tab size:   8 (not used)
*   indentation:4
*
*   This file contains the platform specific implementation of per-library cleanup.
*
*/


#ifndef __UCLN_IMP_H__
#define __UCLN_IMP_H__

#include "ucln.h"
#include <stdlib.h>

/**
 * Auto cleanup of ICU libraries
 * There are several methods in per library cleanup of icu libraries:
 * 1) Compiler/Platform based cleanup:
 *   a) Windows MSVC uses DllMain()
 *   b) GCC uses destructor function attribute
 *   c) Sun Studio, AIX VA, and HP-UX aCC uses a linker option to set the exit function
 * 2) Using atexit()
 * 3) Implementing own automatic cleanup functions
 *
 * For option 1, ensure that UCLN_NO_AUTO_CLEANUP is set to 0 by using --enable-auto-cleanup
 * configure option or by otherwise setting UCLN_NO_AUTO_CLEANUP to 0
 * For option 2, follow option 1 and also define UCLN_AUTO_ATEXIT
 * For option 3, follow option 1 and also define UCLN_AUTO_LOCAL (see below for more information)
 */

#if !UCLN_NO_AUTO_CLEANUP

/*
 * The following declarations are for when UCLN_AUTO_LOCAL or UCLN_AUTO_ATEXIT
 * are defined. They are commented out because they are static and will be defined
 * later. The information is still here to provide some guidance for the developer
 * who chooses to use UCLN_AUTO_LOCAL.
 */
/**
 * Give the library an opportunity to register an automatic cleanup.
 * This may be called more than once.
 */
/*static void ucln_registerAutomaticCleanup();*/
/**
 * Unregister an automatic cleanup, if possible. Called from cleanup.
 */
/*static void ucln_unRegisterAutomaticCleanup();*/

#ifdef UCLN_TYPE_IS_COMMON
#   define UCLN_CLEAN_ME_UP u_cleanup()
#else
#   define UCLN_CLEAN_ME_UP ucln_cleanupOne(UCLN_TYPE)
#endif

/* ------------ automatic cleanup: registration. Choose ONE ------- */
#if defined(UCLN_AUTO_LOCAL)
/* To use:
 *  1. define UCLN_AUTO_LOCAL,
 *  2. create ucln_local_hook.c containing implementations of
 *           static void ucln_registerAutomaticCleanup()
 *           static void ucln_unRegisterAutomaticCleanup()
 */
#include "ucln_local_hook.c"

#elif defined(UCLN_AUTO_ATEXIT)
/*
 * Use the ANSI C 'atexit' function. Note that this mechanism does not
 * guarantee the order of cleanup relative to other users of ICU!
 */
static UBool gAutoCleanRegistered = false;

static void ucln_atexit_handler()
{
    UCLN_CLEAN_ME_UP;
}

static void ucln_registerAutomaticCleanup()
{
    if(!gAutoCleanRegistered) {
        gAutoCleanRegistered = true;
        atexit(&ucln_atexit_handler);
    }
}

static void ucln_unRegisterAutomaticCleanup () {
}
/* ------------end of automatic cleanup: registration. ------- */

#elif defined (UCLN_FINI)
/**
 * If UCLN_FINI is defined, it is the (versioned, etc) name of a cleanup
 * entrypoint. Add a stub to call ucln_cleanupOne
 * Used on AIX, Solaris, and HP-UX
 */
U_CAPI void U_EXPORT2 UCLN_FINI (void);

U_CAPI void U_EXPORT2 UCLN_FINI ()
{
    /* This function must be defined, if UCLN_FINI is defined, else link error. */
     UCLN_CLEAN_ME_UP;
}

/* Windows: DllMain */
#elif U_PLATFORM_HAS_WIN32_API
/* 
 * ICU's own DllMain.
 */

/* these are from putil.c */
/* READ READ READ READ!    Are you getting compilation errors from windows.h?
          Any source file which includes this (ucln_imp.h) header MUST 
          be defined with language extensions ON. */
#ifndef WIN32_LEAN_AND_MEAN
#   define WIN32_LEAN_AND_MEAN
#endif
#   define VC_EXTRALEAN
#   define NOUSER
#   define NOSERVICE
#   define NOIME
#   define NOMCX
#   include <windows.h>
/*
 * This is a stub DllMain function with icu specific process handling code.
 */
BOOL WINAPI DllMain(HINSTANCE hinstDLL, DWORD fdwReason, LPVOID lpvReserved)
{
    BOOL status = true;

    switch(fdwReason) {
        case DLL_PROCESS_ATTACH:
             /* ICU does not trap process attach, but must pass these through properly. */
            /* ICU specific process attach could go here */
            break;

        case DLL_PROCESS_DETACH:
            /* Here is the one we actually care about. */

            UCLN_CLEAN_ME_UP;

            break;

        case DLL_THREAD_ATTACH:
            /* ICU does not trap thread attach, but must pass these through properly. */
            /* ICU specific thread attach could go here */
            break;

        case DLL_THREAD_DETACH:
            /* ICU does not trap thread detach, but must pass these through properly. */
            /* ICU specific thread detach could go here */
            break;

    }
    return status;
}

#elif defined(__GNUC__)
/* GCC - use __attribute((destructor)) */
static void ucln_destructor()   __attribute__((destructor)) ;

static void ucln_destructor() 
{
    UCLN_CLEAN_ME_UP;
}

#endif

#endif /* UCLN_NO_AUTO_CLEANUP */

#else
#error This file can only be included once.
#endif