00001
00002
00003 #include "ace/ACE.h"
00004 #include "ace/OS_NS_string.h"
00005 #include "ace/OS_NS_stdio.h"
00006 #include "ace/OS_NS_stdlib.h"
00007
00008 ACE_RCSID (ace,
00009 OS_NS_string,
00010 "$Id: OS_NS_string.cpp 88331 2009-12-24 09:54:25Z johnnyw $")
00011
00012 #if !defined (ACE_HAS_INLINED_OSCALLS)
00013 # include "ace/OS_NS_string.inl"
00014 #endif
00015
00016 ACE_BEGIN_VERSIONED_NAMESPACE_DECL
00017
00018 #if defined (ACE_LACKS_MEMCHR)
00019 const void *
00020 ACE_OS::memchr_emulation (const void *s, int c, size_t len)
00021 {
00022 const unsigned char *t = (const unsigned char *) s;
00023 const unsigned char *e = (const unsigned char *) s + len;
00024
00025 while (t < e)
00026 if (((int) *t) == c)
00027 return t;
00028 else
00029 ++t;
00030
00031 return 0;
00032 }
00033 #endif
00034
00035 #if (defined (ACE_LACKS_STRDUP) && !defined (ACE_STRDUP_EQUIVALENT)) \
00036 || defined (ACE_HAS_STRDUP_EMULATION)
00037 char *
00038 ACE_OS::strdup_emulation (const char *s)
00039 {
00040 char *t = (char *) ACE_OS::malloc (ACE_OS::strlen (s) + 1);
00041 if (t == 0)
00042 return 0;
00043
00044 return ACE_OS::strcpy (t, s);
00045 }
00046 #endif
00047
00048 #if defined (ACE_HAS_WCHAR)
00049 #if (defined (ACE_LACKS_WCSDUP) && !defined (ACE_WCSDUP_EQUIVALENT)) \
00050 || defined (ACE_HAS_WCSDUP_EMULATION)
00051 wchar_t *
00052 ACE_OS::strdup_emulation (const wchar_t *s)
00053 {
00054 wchar_t *buffer =
00055 (wchar_t *) ACE_OS::malloc ((ACE_OS::strlen (s) + 1)
00056 * sizeof (wchar_t));
00057 if (buffer == 0)
00058 return 0;
00059
00060 return ACE_OS::strcpy (buffer, s);
00061 }
00062 #endif
00063 #endif
00064
00065 char *
00066 ACE_OS::strecpy (char *s, const char *t)
00067 {
00068 register char *dscan = s;
00069 register const char *sscan = t;
00070
00071 while ((*dscan++ = *sscan++) != '\0')
00072 continue;
00073
00074 return dscan;
00075 }
00076
00077 #if defined (ACE_HAS_WCHAR)
00078 wchar_t *
00079 ACE_OS::strecpy (wchar_t *s, const wchar_t *t)
00080 {
00081 register wchar_t *dscan = s;
00082 register const wchar_t *sscan = t;
00083
00084 while ((*dscan++ = *sscan++) != ACE_TEXT_WIDE ('\0'))
00085 continue;
00086
00087 return dscan;
00088 }
00089 #endif
00090
00091 char *
00092 ACE_OS::strerror (int errnum)
00093 {
00094 static char ret_errortext[128];
00095
00096 if (ACE::is_sock_error (errnum))
00097 {
00098 const ACE_TCHAR *errortext = ACE::sock_error (errnum);
00099 ACE_OS::strncpy (ret_errortext,
00100 ACE_TEXT_ALWAYS_CHAR (errortext),
00101 sizeof (ret_errortext));
00102 return ret_errortext;
00103 }
00104 #if defined (ACE_LACKS_STRERROR)
00105 errno = EINVAL;
00106 return ACE_OS::strerror_emulation (errnum);
00107 #else
00108
00109
00110
00111
00112
00113 ACE_Errno_Guard g (errno);
00114 errno = 0;
00115 char *errmsg = 0;
00116
00117 #if defined (ACE_HAS_TR24731_2005_CRT)
00118 errmsg = ret_errortext;
00119 ACE_SECURECRTCALL (strerror_s (ret_errortext, sizeof(ret_errortext), errnum),
00120 char *, 0, errmsg);
00121 if (errnum < 0 || errnum >= _sys_nerr)
00122 g = EINVAL;
00123
00124 return errmsg;
00125 #elif defined (ACE_WIN32)
00126 if (errnum < 0 || errnum >= _sys_nerr)
00127 errno = EINVAL;
00128 #endif
00129 errmsg = ::strerror (errnum);
00130
00131 if (errno == EINVAL || errmsg == 0 || errmsg[0] == 0)
00132 {
00133 ACE_OS::sprintf (ret_errortext, "Unknown error %d", errnum);
00134 errmsg = ret_errortext;
00135 g = EINVAL;
00136 }
00137 return errmsg;
00138 #endif
00139 }
00140
00141 #if defined (ACE_LACKS_STRERROR)
00142
00143
00144
00145 char *
00146 ACE_OS::strerror_emulation (int)
00147 {
00148 return const_cast <char*> ("Unknown Error");
00149 }
00150 #endif
00151
00152
00153 char *
00154 ACE_OS::strsignal (int signum)
00155 {
00156 static char signal_text[128];
00157 #if defined (ACE_HAS_STRSIGNAL)
00158 char *ret_val = 0;
00159
00160 # if defined (ACE_NEEDS_STRSIGNAL_RANGE_CHECK)
00161 if (signum < 0 || signum >= ACE_NSIG)
00162 ret_val = 0;
00163 else
00164 # endif
00165 ret_val = ACE_STD_NAMESPACE::strsignal (signum);
00166
00167 if (ret_val <= reinterpret_cast<char *> (0))
00168 {
00169 ACE_OS::sprintf (signal_text, "Unknown signal: %d", signum);
00170 ret_val = signal_text;
00171 }
00172 return ret_val;
00173 #else
00174 if (signum < 0 || signum >= ACE_NSIG)
00175 {
00176 ACE_OS::sprintf (signal_text, "Unknown signal: %d", signum);
00177 return signal_text;
00178 }
00179 # if defined (ACE_SYS_SIGLIST)
00180 return ACE_SYS_SIGLIST[signum];
00181 # else
00182 ACE_OS::sprintf (signal_text, "Signal: %d", signum);
00183 return signal_text;
00184 # endif
00185 #endif
00186 }
00187
00188 const char *
00189 ACE_OS::strnchr (const char *s, int c, size_t len)
00190 {
00191 for (size_t i = 0; i < len; ++i)
00192 if (s[i] == c)
00193 return s + i;
00194
00195 return 0;
00196 }
00197
00198 const ACE_WCHAR_T *
00199 ACE_OS::strnchr (const ACE_WCHAR_T *s, ACE_WCHAR_T c, size_t len)
00200 {
00201 for (size_t i = 0; i < len; ++i)
00202 {
00203 if (s[i] == c)
00204 {
00205 return s + i;
00206 }
00207 }
00208
00209 return 0;
00210 }
00211
00212 const char *
00213 ACE_OS::strnstr (const char *s1, const char *s2, size_t len2)
00214 {
00215
00216 size_t const len1 = ACE_OS::strlen (s1);
00217
00218
00219 if (len2 > len1)
00220 return 0;
00221
00222
00223 size_t const len = len1 - len2;
00224
00225 for (size_t i = 0; i <= len; i++)
00226 {
00227 if (ACE_OS::memcmp (s1 + i, s2, len2) == 0)
00228 {
00229
00230 return s1 + i;
00231 }
00232 }
00233
00234 return 0;
00235 }
00236
00237 const ACE_WCHAR_T *
00238 ACE_OS::strnstr (const ACE_WCHAR_T *s1, const ACE_WCHAR_T *s2, size_t len2)
00239 {
00240
00241 size_t const len1 = ACE_OS::strlen (s1);
00242
00243
00244 if (len2 > len1)
00245 return 0;
00246
00247
00248 size_t const len = len1 - len2;
00249
00250 for (size_t i = 0; i <= len; i++)
00251 {
00252 if (ACE_OS::memcmp (s1 + i, s2, len2 * sizeof (ACE_WCHAR_T)) == 0)
00253 {
00254
00255 return s1 + i;
00256 }
00257 }
00258
00259 return 0;
00260 }
00261
00262 #if defined (ACE_HAS_MEMCPY_LOOP_UNROLL)
00263 void *
00264 ACE_OS::fast_memcpy (void *t, const void *s, size_t len)
00265 {
00266 unsigned char* to = static_cast<unsigned char*> (t) ;
00267 const unsigned char* from = static_cast<const unsigned char*> (s) ;
00268
00269 switch (len)
00270 {
00271 case 16: to[15] = from[15];
00272 case 15: to[14] = from[14];
00273 case 14: to[13] = from[13];
00274 case 13: to[12] = from[12];
00275 case 12: to[11] = from[11];
00276 case 11: to[10] = from[10];
00277 case 10: to[9] = from[9];
00278 case 9: to[8] = from[8];
00279 case 8: to[7] = from[7];
00280 case 7: to[6] = from[6];
00281 case 6: to[5] = from[5];
00282 case 5: to[4] = from[4];
00283 case 4: to[3] = from[3];
00284 case 3: to[2] = from[2];
00285 case 2: to[1] = from[1];
00286 case 1: to[0] = from[0];
00287 case 0: return t;
00288 default: return ::memcpy (t, s, len);
00289 }
00290 }
00291 #endif
00292
00293 #if defined (ACE_LACKS_STRRCHR)
00294 char *
00295 ACE_OS::strrchr_emulation (char *s, int c)
00296 {
00297 char *p = s + ACE_OS::strlen (s);
00298
00299 while (*p != c)
00300 if (p == s)
00301 return 0;
00302 else
00303 --p;
00304
00305 return p;
00306 }
00307
00308 const char *
00309 ACE_OS::strrchr_emulation (const char *s, int c)
00310 {
00311 const char *p = s + ACE_OS::strlen (s);
00312
00313 while (*p != c)
00314 if (p == s)
00315 return 0;
00316 else
00317 --p;
00318
00319 return p;
00320 }
00321 #endif
00322
00323 char *
00324 ACE_OS::strsncpy (char *dst, const char *src, size_t maxlen)
00325 {
00326 register char *rdst = dst;
00327 register const char *rsrc = src;
00328 register size_t rmaxlen = maxlen;
00329
00330 if (rmaxlen > 0)
00331 {
00332 if (rdst!=rsrc)
00333 {
00334 *rdst = '\0';
00335 if (rsrc != 0)
00336 {
00337 ACE_OS::strncat (rdst, rsrc, --rmaxlen);
00338 }
00339 }
00340 else
00341 {
00342 rdst += (rmaxlen - 1);
00343 *rdst = '\0';
00344 }
00345 }
00346 return dst;
00347 }
00348
00349 ACE_WCHAR_T *
00350 ACE_OS::strsncpy (ACE_WCHAR_T *dst, const ACE_WCHAR_T *src, size_t maxlen)
00351 {
00352 register ACE_WCHAR_T *rdst = dst;
00353 register const ACE_WCHAR_T *rsrc = src;
00354 register size_t rmaxlen = maxlen;
00355
00356 if (rmaxlen > 0)
00357 {
00358 if (rdst!= rsrc)
00359 {
00360 *rdst = ACE_TEXT_WIDE ('\0');
00361 if (rsrc != 0)
00362 {
00363 ACE_OS::strncat (rdst, rsrc, --rmaxlen);
00364 }
00365 }
00366 else
00367 {
00368 rdst += (rmaxlen - 1);
00369 *rdst = ACE_TEXT_WIDE ('\0');
00370 }
00371 }
00372 return dst;
00373 }
00374
00375 #if (!defined (ACE_HAS_REENTRANT_FUNCTIONS) || defined (ACE_LACKS_STRTOK_R)) \
00376 && !defined (ACE_HAS_TR24731_2005_CRT)
00377 char *
00378 ACE_OS::strtok_r_emulation (char *s, const char *tokens, char **lasts)
00379 {
00380 if (s == 0)
00381 s = *lasts;
00382 else
00383 *lasts = s;
00384 if (*s == 0)
00385 return 0;
00386 size_t const l_org = ACE_OS::strlen (s);
00387 s = ::strtok (s, tokens);
00388 if (s == 0)
00389 return 0;
00390 size_t const l_sub = ACE_OS::strlen (s);
00391 if (s + l_sub < *lasts + l_org)
00392 *lasts = s + l_sub + 1;
00393 else
00394 *lasts = s + l_sub;
00395 return s ;
00396 }
00397 #endif
00398
00399 # if defined (ACE_HAS_WCHAR) && defined (ACE_LACKS_WCSTOK)
00400 wchar_t*
00401 ACE_OS::strtok_r_emulation (ACE_WCHAR_T *s,
00402 const ACE_WCHAR_T *tokens,
00403 ACE_WCHAR_T **lasts)
00404 {
00405 ACE_WCHAR_T* sbegin = s ? s : *lasts;
00406 sbegin += ACE_OS::strspn(sbegin, tokens);
00407 if (*sbegin == 0)
00408 {
00409 static ACE_WCHAR_T empty[1] = { 0 };
00410 *lasts = empty;
00411 return 0;
00412 }
00413 ACE_WCHAR_T*send = sbegin + ACE_OS::strcspn(sbegin, tokens);
00414 if (*send != 0)
00415 *send++ = 0;
00416 *lasts = send;
00417 return sbegin;
00418 }
00419 # endif
00420
00421 ACE_END_VERSIONED_NAMESPACE_DECL