D-Bus 1.4.14
|
00001 /* -*- mode: C; c-file-style: "gnu"; indent-tabs-mode: nil; -*- */ 00002 /* dbus-sysdeps.c Wrappers around system/libc features shared between UNIX and Windows (internal to D-Bus implementation) 00003 * 00004 * Copyright (C) 2002, 2003, 2006 Red Hat, Inc. 00005 * Copyright (C) 2003 CodeFactory AB 00006 * 00007 * Licensed under the Academic Free License version 2.1 00008 * 00009 * This program is free software; you can redistribute it and/or modify 00010 * it under the terms of the GNU General Public License as published by 00011 * the Free Software Foundation; either version 2 of the License, or 00012 * (at your option) any later version. 00013 * 00014 * This program is distributed in the hope that it will be useful, 00015 * but WITHOUT ANY WARRANTY; without even the implied warranty of 00016 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the 00017 * GNU General Public License for more details. 00018 * 00019 * You should have received a copy of the GNU General Public License 00020 * along with this program; if not, write to the Free Software 00021 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA 00022 * 00023 */ 00024 00025 #include <config.h> 00026 #include "dbus-internals.h" 00027 #include "dbus-sysdeps.h" 00028 #include "dbus-threads.h" 00029 #include "dbus-protocol.h" 00030 #include "dbus-string.h" 00031 #include "dbus-list.h" 00032 00033 /* NOTE: If you include any unix/windows-specific headers here, you are probably doing something 00034 * wrong and should be putting some code in dbus-sysdeps-unix.c or dbus-sysdeps-win.c. 00035 * 00036 * These are the standard ANSI C headers... 00037 */ 00038 #if HAVE_LOCALE_H 00039 #include <locale.h> 00040 #endif 00041 #include <stdlib.h> 00042 #include <string.h> 00043 #include <stdio.h> 00044 00045 #ifdef HAVE_ERRNO_H 00046 #include <errno.h> 00047 #endif 00048 00049 _DBUS_DEFINE_GLOBAL_LOCK (win_fds); 00050 _DBUS_DEFINE_GLOBAL_LOCK (sid_atom_cache); 00051 _DBUS_DEFINE_GLOBAL_LOCK (system_users); 00052 00053 #ifdef DBUS_WIN 00054 #include <stdlib.h> 00055 #elif (defined __APPLE__) 00056 # include <crt_externs.h> 00057 # define environ (*_NSGetEnviron()) 00058 #else 00059 extern char **environ; 00060 #endif 00061 00079 void 00080 _dbus_abort (void) 00081 { 00082 const char *s; 00083 00084 _dbus_print_backtrace (); 00085 00086 s = _dbus_getenv ("DBUS_BLOCK_ON_ABORT"); 00087 if (s && *s) 00088 { 00089 /* don't use _dbus_warn here since it can _dbus_abort() */ 00090 fprintf (stderr, " Process %lu sleeping for gdb attach\n", _dbus_pid_for_log ()); 00091 _dbus_sleep_milliseconds (1000 * 180); 00092 } 00093 00094 abort (); 00095 _dbus_exit (1); /* in case someone manages to ignore SIGABRT ? */ 00096 } 00097 00111 dbus_bool_t 00112 _dbus_setenv (const char *varname, 00113 const char *value) 00114 { 00115 _dbus_assert (varname != NULL); 00116 00117 if (value == NULL) 00118 { 00119 #ifdef HAVE_UNSETENV 00120 unsetenv (varname); 00121 return TRUE; 00122 #else 00123 char *putenv_value; 00124 size_t len; 00125 00126 len = strlen (varname); 00127 00128 /* Use system malloc to avoid memleaks that dbus_malloc 00129 * will get upset about. 00130 */ 00131 00132 putenv_value = malloc (len + 2); 00133 if (putenv_value == NULL) 00134 return FALSE; 00135 00136 strcpy (putenv_value, varname); 00137 #if defined(DBUS_WIN) 00138 strcat (putenv_value, "="); 00139 #endif 00140 00141 return (putenv (putenv_value) == 0); 00142 #endif 00143 } 00144 else 00145 { 00146 #ifdef HAVE_SETENV 00147 return (setenv (varname, value, TRUE) == 0); 00148 #else 00149 char *putenv_value; 00150 size_t len; 00151 size_t varname_len; 00152 size_t value_len; 00153 00154 varname_len = strlen (varname); 00155 value_len = strlen (value); 00156 00157 len = varname_len + value_len + 1 /* '=' */ ; 00158 00159 /* Use system malloc to avoid memleaks that dbus_malloc 00160 * will get upset about. 00161 */ 00162 00163 putenv_value = malloc (len + 1); 00164 if (putenv_value == NULL) 00165 return FALSE; 00166 00167 strcpy (putenv_value, varname); 00168 strcpy (putenv_value + varname_len, "="); 00169 strcpy (putenv_value + varname_len + 1, value); 00170 00171 return (putenv (putenv_value) == 0); 00172 #endif 00173 } 00174 } 00175 00182 const char* 00183 _dbus_getenv (const char *varname) 00184 { 00185 /* Don't respect any environment variables if the current process is 00186 * setuid. This is the equivalent of glibc's __secure_getenv(). 00187 */ 00188 if (_dbus_check_setuid ()) 00189 return NULL; 00190 return getenv (varname); 00191 } 00192 00198 dbus_bool_t 00199 _dbus_clearenv (void) 00200 { 00201 dbus_bool_t rc = TRUE; 00202 00203 #ifdef HAVE_CLEARENV 00204 if (clearenv () != 0) 00205 rc = FALSE; 00206 #else 00207 00208 if (environ != NULL) 00209 environ[0] = NULL; 00210 #endif 00211 00212 return rc; 00213 } 00214 00221 char ** 00222 _dbus_get_environment (void) 00223 { 00224 int i, length; 00225 char **environment; 00226 00227 _dbus_assert (environ != NULL); 00228 00229 for (length = 0; environ[length] != NULL; length++); 00230 00231 /* Add one for NULL */ 00232 length++; 00233 00234 environment = dbus_new0 (char *, length); 00235 00236 if (environment == NULL) 00237 return NULL; 00238 00239 for (i = 0; environ[i] != NULL; i++) 00240 { 00241 environment[i] = _dbus_strdup (environ[i]); 00242 00243 if (environment[i] == NULL) 00244 break; 00245 } 00246 00247 if (environ[i] != NULL) 00248 { 00249 dbus_free_string_array (environment); 00250 environment = NULL; 00251 } 00252 00253 return environment; 00254 } 00255 00264 dbus_bool_t 00265 _dbus_split_paths_and_append (DBusString *dirs, 00266 const char *suffix, 00267 DBusList **dir_list) 00268 { 00269 int start; 00270 int i; 00271 int len; 00272 char *cpath; 00273 DBusString file_suffix; 00274 00275 start = 0; 00276 i = 0; 00277 00278 _dbus_string_init_const (&file_suffix, suffix); 00279 00280 len = _dbus_string_get_length (dirs); 00281 00282 while (_dbus_string_find (dirs, start, _DBUS_PATH_SEPARATOR, &i)) 00283 { 00284 DBusString path; 00285 00286 if (!_dbus_string_init (&path)) 00287 goto oom; 00288 00289 if (!_dbus_string_copy_len (dirs, 00290 start, 00291 i - start, 00292 &path, 00293 0)) 00294 { 00295 _dbus_string_free (&path); 00296 goto oom; 00297 } 00298 00299 _dbus_string_chop_white (&path); 00300 00301 /* check for an empty path */ 00302 if (_dbus_string_get_length (&path) == 0) 00303 goto next; 00304 00305 if (!_dbus_concat_dir_and_file (&path, 00306 &file_suffix)) 00307 { 00308 _dbus_string_free (&path); 00309 goto oom; 00310 } 00311 00312 if (!_dbus_string_copy_data(&path, &cpath)) 00313 { 00314 _dbus_string_free (&path); 00315 goto oom; 00316 } 00317 00318 if (!_dbus_list_append (dir_list, cpath)) 00319 { 00320 _dbus_string_free (&path); 00321 dbus_free (cpath); 00322 goto oom; 00323 } 00324 00325 next: 00326 _dbus_string_free (&path); 00327 start = i + 1; 00328 } 00329 00330 if (start != len) 00331 { 00332 DBusString path; 00333 00334 if (!_dbus_string_init (&path)) 00335 goto oom; 00336 00337 if (!_dbus_string_copy_len (dirs, 00338 start, 00339 len - start, 00340 &path, 00341 0)) 00342 { 00343 _dbus_string_free (&path); 00344 goto oom; 00345 } 00346 00347 if (!_dbus_concat_dir_and_file (&path, 00348 &file_suffix)) 00349 { 00350 _dbus_string_free (&path); 00351 goto oom; 00352 } 00353 00354 if (!_dbus_string_copy_data(&path, &cpath)) 00355 { 00356 _dbus_string_free (&path); 00357 goto oom; 00358 } 00359 00360 if (!_dbus_list_append (dir_list, cpath)) 00361 { 00362 _dbus_string_free (&path); 00363 dbus_free (cpath); 00364 goto oom; 00365 } 00366 00367 _dbus_string_free (&path); 00368 } 00369 00370 return TRUE; 00371 00372 oom: 00373 _dbus_list_foreach (dir_list, (DBusForeachFunction)dbus_free, NULL); 00374 _dbus_list_clear (dir_list); 00375 return FALSE; 00376 } 00377 00392 dbus_bool_t 00393 _dbus_string_append_int (DBusString *str, 00394 long value) 00395 { 00396 /* this calculation is from comp.lang.c faq */ 00397 #define MAX_LONG_LEN ((sizeof (long) * 8 + 2) / 3 + 1) /* +1 for '-' */ 00398 int orig_len; 00399 int i; 00400 char *buf; 00401 00402 orig_len = _dbus_string_get_length (str); 00403 00404 if (!_dbus_string_lengthen (str, MAX_LONG_LEN)) 00405 return FALSE; 00406 00407 buf = _dbus_string_get_data_len (str, orig_len, MAX_LONG_LEN); 00408 00409 snprintf (buf, MAX_LONG_LEN, "%ld", value); 00410 00411 i = 0; 00412 while (*buf) 00413 { 00414 ++buf; 00415 ++i; 00416 } 00417 00418 _dbus_string_shorten (str, MAX_LONG_LEN - i); 00419 00420 return TRUE; 00421 } 00422 00430 dbus_bool_t 00431 _dbus_string_append_uint (DBusString *str, 00432 unsigned long value) 00433 { 00434 /* this is wrong, but definitely on the high side. */ 00435 #define MAX_ULONG_LEN (MAX_LONG_LEN * 2) 00436 int orig_len; 00437 int i; 00438 char *buf; 00439 00440 orig_len = _dbus_string_get_length (str); 00441 00442 if (!_dbus_string_lengthen (str, MAX_ULONG_LEN)) 00443 return FALSE; 00444 00445 buf = _dbus_string_get_data_len (str, orig_len, MAX_ULONG_LEN); 00446 00447 snprintf (buf, MAX_ULONG_LEN, "%lu", value); 00448 00449 i = 0; 00450 while (*buf) 00451 { 00452 ++buf; 00453 ++i; 00454 } 00455 00456 _dbus_string_shorten (str, MAX_ULONG_LEN - i); 00457 00458 return TRUE; 00459 } 00460 00461 #ifdef DBUS_BUILD_TESTS 00462 00469 dbus_bool_t 00470 _dbus_string_append_double (DBusString *str, 00471 double value) 00472 { 00473 #define MAX_DOUBLE_LEN 64 /* this is completely made up :-/ */ 00474 int orig_len; 00475 char *buf; 00476 int i; 00477 00478 orig_len = _dbus_string_get_length (str); 00479 00480 if (!_dbus_string_lengthen (str, MAX_DOUBLE_LEN)) 00481 return FALSE; 00482 00483 buf = _dbus_string_get_data_len (str, orig_len, MAX_DOUBLE_LEN); 00484 00485 snprintf (buf, MAX_LONG_LEN, "%g", value); 00486 00487 i = 0; 00488 while (*buf) 00489 { 00490 ++buf; 00491 ++i; 00492 } 00493 00494 _dbus_string_shorten (str, MAX_DOUBLE_LEN - i); 00495 00496 return TRUE; 00497 } 00498 #endif /* DBUS_BUILD_TESTS */ 00499 00512 dbus_bool_t 00513 _dbus_string_parse_int (const DBusString *str, 00514 int start, 00515 long *value_return, 00516 int *end_return) 00517 { 00518 long v; 00519 const char *p; 00520 char *end; 00521 00522 p = _dbus_string_get_const_data_len (str, start, 00523 _dbus_string_get_length (str) - start); 00524 00525 end = NULL; 00526 _dbus_set_errno_to_zero (); 00527 v = strtol (p, &end, 0); 00528 if (end == NULL || end == p || errno != 0) 00529 return FALSE; 00530 00531 if (value_return) 00532 *value_return = v; 00533 if (end_return) 00534 *end_return = start + (end - p); 00535 00536 return TRUE; 00537 } 00538 00551 dbus_bool_t 00552 _dbus_string_parse_uint (const DBusString *str, 00553 int start, 00554 unsigned long *value_return, 00555 int *end_return) 00556 { 00557 unsigned long v; 00558 const char *p; 00559 char *end; 00560 00561 p = _dbus_string_get_const_data_len (str, start, 00562 _dbus_string_get_length (str) - start); 00563 00564 end = NULL; 00565 _dbus_set_errno_to_zero (); 00566 v = strtoul (p, &end, 0); 00567 if (end == NULL || end == p || errno != 0) 00568 return FALSE; 00569 00570 if (value_return) 00571 *value_return = v; 00572 if (end_return) 00573 *end_return = start + (end - p); 00574 00575 return TRUE; 00576 } 00577 00578 #ifdef DBUS_BUILD_TESTS 00579 static dbus_bool_t 00580 ascii_isspace (char c) 00581 { 00582 return (c == ' ' || 00583 c == '\f' || 00584 c == '\n' || 00585 c == '\r' || 00586 c == '\t' || 00587 c == '\v'); 00588 } 00589 #endif /* DBUS_BUILD_TESTS */ 00590 00591 #ifdef DBUS_BUILD_TESTS 00592 static dbus_bool_t 00593 ascii_isdigit (char c) 00594 { 00595 return c >= '0' && c <= '9'; 00596 } 00597 #endif /* DBUS_BUILD_TESTS */ 00598 00599 #ifdef DBUS_BUILD_TESTS 00600 static dbus_bool_t 00601 ascii_isxdigit (char c) 00602 { 00603 return (ascii_isdigit (c) || 00604 (c >= 'a' && c <= 'f') || 00605 (c >= 'A' && c <= 'F')); 00606 } 00607 #endif /* DBUS_BUILD_TESTS */ 00608 00609 #ifdef DBUS_BUILD_TESTS 00610 /* Calls strtod in a locale-independent fashion, by looking at 00611 * the locale data and patching the decimal comma to a point. 00612 * 00613 * Relicensed from glib. 00614 */ 00615 static double 00616 ascii_strtod (const char *nptr, 00617 char **endptr) 00618 { 00619 /* FIXME: The Win32 C library's strtod() doesn't handle hex. 00620 * Presumably many Unixes don't either. 00621 */ 00622 00623 char *fail_pos; 00624 double val; 00625 struct lconv *locale_data; 00626 const char *decimal_point; 00627 int decimal_point_len; 00628 const char *p, *decimal_point_pos; 00629 const char *end = NULL; /* Silence gcc */ 00630 00631 fail_pos = NULL; 00632 00633 #if HAVE_LOCALECONV 00634 locale_data = localeconv (); 00635 decimal_point = locale_data->decimal_point; 00636 #else 00637 decimal_point = "."; 00638 #endif 00639 00640 decimal_point_len = strlen (decimal_point); 00641 _dbus_assert (decimal_point_len != 0); 00642 00643 decimal_point_pos = NULL; 00644 if (decimal_point[0] != '.' || 00645 decimal_point[1] != 0) 00646 { 00647 p = nptr; 00648 /* Skip leading space */ 00649 while (ascii_isspace (*p)) 00650 p++; 00651 00652 /* Skip leading optional sign */ 00653 if (*p == '+' || *p == '-') 00654 p++; 00655 00656 if (p[0] == '0' && 00657 (p[1] == 'x' || p[1] == 'X')) 00658 { 00659 p += 2; 00660 /* HEX - find the (optional) decimal point */ 00661 00662 while (ascii_isxdigit (*p)) 00663 p++; 00664 00665 if (*p == '.') 00666 { 00667 decimal_point_pos = p++; 00668 00669 while (ascii_isxdigit (*p)) 00670 p++; 00671 00672 if (*p == 'p' || *p == 'P') 00673 p++; 00674 if (*p == '+' || *p == '-') 00675 p++; 00676 while (ascii_isdigit (*p)) 00677 p++; 00678 end = p; 00679 } 00680 } 00681 else 00682 { 00683 while (ascii_isdigit (*p)) 00684 p++; 00685 00686 if (*p == '.') 00687 { 00688 decimal_point_pos = p++; 00689 00690 while (ascii_isdigit (*p)) 00691 p++; 00692 00693 if (*p == 'e' || *p == 'E') 00694 p++; 00695 if (*p == '+' || *p == '-') 00696 p++; 00697 while (ascii_isdigit (*p)) 00698 p++; 00699 end = p; 00700 } 00701 } 00702 /* For the other cases, we need not convert the decimal point */ 00703 } 00704 00705 /* Set errno to zero, so that we can distinguish zero results 00706 and underflows */ 00707 _dbus_set_errno_to_zero (); 00708 00709 if (decimal_point_pos) 00710 { 00711 char *copy, *c; 00712 00713 /* We need to convert the '.' to the locale specific decimal point */ 00714 copy = dbus_malloc (end - nptr + 1 + decimal_point_len); 00715 00716 c = copy; 00717 memcpy (c, nptr, decimal_point_pos - nptr); 00718 c += decimal_point_pos - nptr; 00719 memcpy (c, decimal_point, decimal_point_len); 00720 c += decimal_point_len; 00721 memcpy (c, decimal_point_pos + 1, end - (decimal_point_pos + 1)); 00722 c += end - (decimal_point_pos + 1); 00723 *c = 0; 00724 00725 val = strtod (copy, &fail_pos); 00726 00727 if (fail_pos) 00728 { 00729 if (fail_pos > decimal_point_pos) 00730 fail_pos = (char *)nptr + (fail_pos - copy) - (decimal_point_len - 1); 00731 else 00732 fail_pos = (char *)nptr + (fail_pos - copy); 00733 } 00734 00735 dbus_free (copy); 00736 00737 } 00738 else 00739 val = strtod (nptr, &fail_pos); 00740 00741 if (endptr) 00742 *endptr = fail_pos; 00743 00744 return val; 00745 } 00746 #endif /* DBUS_BUILD_TESTS */ 00747 00748 #ifdef DBUS_BUILD_TESTS 00749 00761 dbus_bool_t 00762 _dbus_string_parse_double (const DBusString *str, 00763 int start, 00764 double *value_return, 00765 int *end_return) 00766 { 00767 double v; 00768 const char *p; 00769 char *end; 00770 00771 p = _dbus_string_get_const_data_len (str, start, 00772 _dbus_string_get_length (str) - start); 00773 00774 /* parsing hex works on linux but isn't portable, so intercept it 00775 * here to get uniform behavior. 00776 */ 00777 if (p[0] == '0' && (p[1] == 'x' || p[1] == 'X')) 00778 return FALSE; 00779 00780 end = NULL; 00781 _dbus_set_errno_to_zero (); 00782 v = ascii_strtod (p, &end); 00783 if (end == NULL || end == p || errno != 0) 00784 return FALSE; 00785 00786 if (value_return) 00787 *value_return = v; 00788 if (end_return) 00789 *end_return = start + (end - p); 00790 00791 return TRUE; 00792 } 00793 #endif /* DBUS_BUILD_TESTS */ 00794 /* DBusString group */ 00796 00802 void 00803 _dbus_generate_pseudorandom_bytes_buffer (char *buffer, 00804 int n_bytes) 00805 { 00806 long tv_usec; 00807 int i; 00808 00809 /* fall back to pseudorandom */ 00810 _dbus_verbose ("Falling back to pseudorandom for %d bytes\n", 00811 n_bytes); 00812 00813 _dbus_get_current_time (NULL, &tv_usec); 00814 srand (tv_usec); 00815 00816 i = 0; 00817 while (i < n_bytes) 00818 { 00819 double r; 00820 unsigned int b; 00821 00822 r = rand (); 00823 b = (r / (double) RAND_MAX) * 255.0; 00824 00825 buffer[i] = b; 00826 00827 ++i; 00828 } 00829 } 00830 00837 void 00838 _dbus_generate_random_bytes_buffer (char *buffer, 00839 int n_bytes) 00840 { 00841 DBusString str; 00842 00843 if (!_dbus_string_init (&str)) 00844 { 00845 _dbus_generate_pseudorandom_bytes_buffer (buffer, n_bytes); 00846 return; 00847 } 00848 00849 if (!_dbus_generate_random_bytes (&str, n_bytes)) 00850 { 00851 _dbus_string_free (&str); 00852 _dbus_generate_pseudorandom_bytes_buffer (buffer, n_bytes); 00853 return; 00854 } 00855 00856 _dbus_string_copy_to_buffer (&str, buffer, n_bytes); 00857 00858 _dbus_string_free (&str); 00859 } 00860 00869 dbus_bool_t 00870 _dbus_generate_random_ascii (DBusString *str, 00871 int n_bytes) 00872 { 00873 static const char letters[] = 00874 "ABCDEFGHIJKLMNOPQRSTUVWXYZ0123456789abcdefghijklmnopqrstuvwxyz"; 00875 int i; 00876 int len; 00877 00878 if (!_dbus_generate_random_bytes (str, n_bytes)) 00879 return FALSE; 00880 00881 len = _dbus_string_get_length (str); 00882 i = len - n_bytes; 00883 while (i < len) 00884 { 00885 _dbus_string_set_byte (str, i, 00886 letters[_dbus_string_get_byte (str, i) % 00887 (sizeof (letters) - 1)]); 00888 00889 ++i; 00890 } 00891 00892 _dbus_assert (_dbus_string_validate_ascii (str, len - n_bytes, 00893 n_bytes)); 00894 00895 return TRUE; 00896 } 00897 00908 const char* 00909 _dbus_error_from_errno (int error_number) 00910 { 00911 switch (error_number) 00912 { 00913 case 0: 00914 return DBUS_ERROR_FAILED; 00915 00916 #ifdef EPROTONOSUPPORT 00917 case EPROTONOSUPPORT: 00918 return DBUS_ERROR_NOT_SUPPORTED; 00919 #endif 00920 #ifdef WSAEPROTONOSUPPORT 00921 case WSAEPROTONOSUPPORT: 00922 return DBUS_ERROR_NOT_SUPPORTED; 00923 #endif 00924 #ifdef EAFNOSUPPORT 00925 case EAFNOSUPPORT: 00926 return DBUS_ERROR_NOT_SUPPORTED; 00927 #endif 00928 #ifdef WSAEAFNOSUPPORT 00929 case WSAEAFNOSUPPORT: 00930 return DBUS_ERROR_NOT_SUPPORTED; 00931 #endif 00932 #ifdef ENFILE 00933 case ENFILE: 00934 return DBUS_ERROR_LIMITS_EXCEEDED; /* kernel out of memory */ 00935 #endif 00936 #ifdef EMFILE 00937 case EMFILE: 00938 return DBUS_ERROR_LIMITS_EXCEEDED; 00939 #endif 00940 #ifdef EACCES 00941 case EACCES: 00942 return DBUS_ERROR_ACCESS_DENIED; 00943 #endif 00944 #ifdef EPERM 00945 case EPERM: 00946 return DBUS_ERROR_ACCESS_DENIED; 00947 #endif 00948 #ifdef ENOBUFS 00949 case ENOBUFS: 00950 return DBUS_ERROR_NO_MEMORY; 00951 #endif 00952 #ifdef ENOMEM 00953 case ENOMEM: 00954 return DBUS_ERROR_NO_MEMORY; 00955 #endif 00956 #ifdef ECONNREFUSED 00957 case ECONNREFUSED: 00958 return DBUS_ERROR_NO_SERVER; 00959 #endif 00960 #ifdef WSAECONNREFUSED 00961 case WSAECONNREFUSED: 00962 return DBUS_ERROR_NO_SERVER; 00963 #endif 00964 #ifdef ETIMEDOUT 00965 case ETIMEDOUT: 00966 return DBUS_ERROR_TIMEOUT; 00967 #endif 00968 #ifdef WSAETIMEDOUT 00969 case WSAETIMEDOUT: 00970 return DBUS_ERROR_TIMEOUT; 00971 #endif 00972 #ifdef ENETUNREACH 00973 case ENETUNREACH: 00974 return DBUS_ERROR_NO_NETWORK; 00975 #endif 00976 #ifdef WSAENETUNREACH 00977 case WSAENETUNREACH: 00978 return DBUS_ERROR_NO_NETWORK; 00979 #endif 00980 #ifdef EADDRINUSE 00981 case EADDRINUSE: 00982 return DBUS_ERROR_ADDRESS_IN_USE; 00983 #endif 00984 #ifdef WSAEADDRINUSE 00985 case WSAEADDRINUSE: 00986 return DBUS_ERROR_ADDRESS_IN_USE; 00987 #endif 00988 #ifdef EEXIST 00989 case EEXIST: 00990 return DBUS_ERROR_FILE_EXISTS; 00991 #endif 00992 #ifdef ENOENT 00993 case ENOENT: 00994 return DBUS_ERROR_FILE_NOT_FOUND; 00995 #endif 00996 } 00997 00998 return DBUS_ERROR_FAILED; 00999 } 01000 01006 const char* 01007 _dbus_error_from_system_errno (void) 01008 { 01009 return _dbus_error_from_errno (errno); 01010 } 01011 01015 void 01016 _dbus_set_errno_to_zero (void) 01017 { 01018 #ifdef DBUS_WINCE 01019 SetLastError (0); 01020 #else 01021 errno = 0; 01022 #endif 01023 } 01024 01029 dbus_bool_t 01030 _dbus_get_is_errno_nonzero (void) 01031 { 01032 return errno != 0; 01033 } 01034 01039 dbus_bool_t 01040 _dbus_get_is_errno_enomem (void) 01041 { 01042 return errno == ENOMEM; 01043 } 01044 01049 dbus_bool_t 01050 _dbus_get_is_errno_eintr (void) 01051 { 01052 return errno == EINTR; 01053 } 01054 01059 dbus_bool_t 01060 _dbus_get_is_errno_epipe (void) 01061 { 01062 return errno == EPIPE; 01063 } 01064 01069 const char* 01070 _dbus_strerror_from_errno (void) 01071 { 01072 return _dbus_strerror (errno); 01073 } 01074 01077 /* tests in dbus-sysdeps-util.c */