00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038
00039
00040
00041
00042
00043
00044
00045
00046
00047
00048
00049
00050
00051
00052
00053
00054
00055
00056
00057
00058
00059
00060
00061
00062
00063 #include <locale.h>
00064 #include <errno.h>
00065
00066 #include "gwlib.h"
00067
00068
00069
00070
00071
00072 #undef localtime
00073 #undef gmtime
00074 #undef rand
00075 #undef gethostbyname
00076 #undef mktime
00077 #undef strftime
00078
00079
00080 enum {
00081 RAND,
00082 GETHOSTBYNAME,
00083 GWTIME,
00084 NUM_LOCKS
00085 };
00086
00087
00088 static Mutex locks[NUM_LOCKS];
00089
00090
00091 static void lock(int which)
00092 {
00093 mutex_lock(&locks[which]);
00094 }
00095
00096
00097 static void unlock(int which)
00098 {
00099 mutex_unlock(&locks[which]);
00100 }
00101
00102
00103 void gwlib_protected_init(void)
00104 {
00105 int i;
00106
00107 for (i = 0; i < NUM_LOCKS; ++i)
00108 mutex_init_static(&locks[i]);
00109 }
00110
00111
00112 void gwlib_protected_shutdown(void)
00113 {
00114 int i;
00115
00116 for (i = 0; i < NUM_LOCKS; ++i)
00117 mutex_destroy(&locks[i]);
00118 }
00119
00120
00121 struct tm gw_localtime(time_t t)
00122 {
00123 struct tm tm;
00124
00125 #ifndef HAVE_LOCALTIME_R
00126 lock(GWTIME);
00127 tm = *localtime(&t);
00128 unlock(GWTIME);
00129 #else
00130 localtime_r(&t, &tm);
00131 #endif
00132
00133 return tm;
00134 }
00135
00136
00137 struct tm gw_gmtime(time_t t)
00138 {
00139 struct tm tm;
00140
00141 #ifndef HAVE_GMTIME_R
00142 lock(GWTIME);
00143 tm = *gmtime(&t);
00144 unlock(GWTIME);
00145 #else
00146 gmtime_r(&t, &tm);
00147 #endif
00148
00149 return tm;
00150 }
00151
00152
00153 time_t gw_mktime(struct tm *tm)
00154 {
00155 time_t t;
00156 lock(GWTIME);
00157 t = mktime(tm);
00158 unlock(GWTIME);
00159
00160 return t;
00161 }
00162
00163
00164 size_t gw_strftime(char *s, size_t max, const char *format, const struct tm *tm)
00165 {
00166 size_t ret;
00167 lock(GWTIME);
00168 ret = strftime(s, max, format, tm);
00169 unlock(GWTIME);
00170 return ret;
00171 }
00172
00173
00174 int gw_rand(void)
00175 {
00176 int ret;
00177
00178 lock(RAND);
00179 ret = rand();
00180 unlock(RAND);
00181 return ret;
00182 }
00183
00184 #if HAVE_FUNC_GETHOSTBYNAME_R_6
00185
00186 int gw_gethostbyname(struct hostent *ent, const char *name, char **buff)
00187 {
00188 struct hostent *tmphp, hp;
00189 int herr, res;
00190 size_t bufflen;
00191
00192 tmphp = NULL;
00193
00194 bufflen = 1024;
00195 *buff = (char*) gw_malloc(bufflen);
00196 while ((res=gethostbyname_r(name, &hp,*buff, bufflen, &tmphp, &herr)) == ERANGE) {
00197
00198 bufflen *= 2;
00199 *buff = (char*) gw_realloc(*buff, bufflen);
00200 }
00201
00202 if (res != 0 || tmphp == NULL) {
00203 error(herr, "Error while gw_gethostbyname occurs.");
00204 gw_free(*buff);
00205 *buff = NULL;
00206 res = -1;
00207 }
00208 else {
00209 *ent = hp;
00210 }
00211
00212 return res;
00213 }
00214 #elif HAVE_FUNC_GETHOSTBYNAME_R_5
00215
00216 int gw_gethostbyname(struct hostent *ent, const char *name, char **buff)
00217 {
00218 int herr = 0;
00219 size_t bufflen = 1024;
00220 int res = 0;
00221 struct hostent *tmphp = NULL;
00222
00223 *buff = gw_malloc(bufflen);
00224 while ((tmphp = gethostbyname_r(name, ent, *buff, bufflen, &herr)) == NULL && (errno == ERANGE)) {
00225
00226 bufflen *= 2;
00227 *buff = (char *) gw_realloc(*buff, bufflen);
00228 }
00229
00230 if (tmphp == NULL) {
00231 error(herr, "Error while gw_gethostbyname occurs.");
00232 gw_free(*buff);
00233 *buff = NULL;
00234 res = -1;
00235 }
00236
00237 return res;
00238 }
00239
00240
00241 #else
00242
00243
00244
00245
00246
00247
00248 int gw_gethostbyname(struct hostent *ent, const char *name, char **buff)
00249 {
00250 int len, i;
00251 struct hostent *p;
00252
00253
00254
00255
00256
00257 size_t bufflen = 9000;
00258 char *bufptr, *str;
00259
00260 lock(GETHOSTBYNAME);
00261
00262 p = gethostbyname(name);
00263 if (p == NULL) {
00264 unlock(GETHOSTBYNAME);
00265 *buff = NULL;
00266 return -1;
00267 }
00268
00269 *ent = *p;
00270
00271 bufptr = *buff = gw_malloc(bufflen);
00272 ent->h_name = bufptr;
00273
00274 len = strlen(p->h_name) + 1;
00275 strncpy(bufptr, p->h_name, len);
00276 bufptr += len;
00277
00278
00279 #define MEMALIGN(x) ((x)+(8-(((unsigned long)(x))&0x7)))
00280
00281
00282 bufptr = MEMALIGN(bufptr);
00283
00284 ent->h_aliases = (char**)bufptr;
00285
00286
00287 for (i = 0; p->h_aliases[i] != NULL; ++i)
00288 ;
00289
00290
00291 bufptr += (i + 1) * sizeof(char*);
00292
00293
00294 for(i = 0; (str = p->h_aliases[i]); i++) {
00295 len = strlen(str) + 1;
00296 strncpy(bufptr, str, len);
00297 ent->h_aliases[i] = bufptr;
00298 bufptr += len;
00299 }
00300
00301 ent->h_aliases[i] = NULL;
00302
00303 ent->h_addrtype = p->h_addrtype;
00304 ent->h_length = p->h_length;
00305
00306
00307 bufptr = MEMALIGN(bufptr);
00308
00309 ent->h_addr_list = (char**)bufptr;
00310
00311
00312 for (i = 0; p->h_addr_list[i] != NULL; ++i)
00313 ;
00314
00315
00316 bufptr += (i + 1) * sizeof(char*);
00317
00318 i = 0;
00319 len = p->h_length;
00320 str = p->h_addr_list[i];
00321 while (str != NULL) {
00322 memcpy(bufptr, str, len);
00323 ent->h_addr_list[i] = bufptr;
00324 bufptr += len;
00325 str = p->h_addr_list[++i];
00326 }
00327 ent->h_addr_list[i] = NULL;
00328
00329 #undef MEMALIGN
00330
00331 unlock(GETHOSTBYNAME);
00332
00333 return 0;
00334 }
00335 #endif
00336
See file LICENSE for details about the license agreement for using,
modifying, copying or deriving work from this software.