X-Git-Url: http://review.tizen.org/git/?a=blobdiff_plain;f=dbus%2Fdbus-sysdeps-util-win.c;h=4678b11ee1a355b65675fa37a32d2c5caceb993e;hb=61d97215c317a4154df47fbfb882aab60b92fbab;hp=b9ebc82a56ded4be186b57d38f1a3cc1639731d0;hpb=9601b11eebf3659141dc4b44d5068a30a5a66789;p=platform%2Fupstream%2Fdbus.git diff --git a/dbus/dbus-sysdeps-util-win.c b/dbus/dbus-sysdeps-util-win.c index b9ebc82..4678b11 100644 --- a/dbus/dbus-sysdeps-util-win.c +++ b/dbus/dbus-sysdeps-util-win.c @@ -22,6 +22,8 @@ * */ +#include + #define STRSAFE_NO_DEPRECATE #include "dbus-sysdeps.h" @@ -32,23 +34,27 @@ #include "dbus-sysdeps-win.h" #include "dbus-sockets-win.h" #include "dbus-memory.h" - -#include -#include -#include -#include +#include "dbus-pipe.h" #include #include -#include +#if HAVE_ERRNO_H #include +#endif #include // WSA error codes +#ifndef DBUS_WINCE +#include +#include +#include +#endif + + /** * Does the chdir, fork, setsid, etc. to become a daemon process. * * @param pidfile #NULL, or pidfile to create - * @param print_pid_fd file descriptor to print daemon's pid to, or -1 for none + * @param print_pid_pipe file descriptor to print daemon's pid to, or -1 for none * @param error return location for errors * @param keep_umask #TRUE to keep the original umask * @returns #FALSE on failure @@ -59,7 +65,9 @@ _dbus_become_daemon (const DBusString *pidfile, DBusError *error, dbus_bool_t keep_umask) { - return TRUE; + dbus_set_error (error, DBUS_ERROR_NOT_SUPPORTED, + "Cannot daemonize on Windows"); + return FALSE; } /** @@ -76,44 +84,70 @@ _dbus_write_pid_file (const DBusString *filename, DBusError *error) { const char *cfilename; - int fd; - FILE *f; + HANDLE hnd; + char pidstr[20]; + int total; + int bytes_to_write; + + _DBUS_ASSERT_ERROR_IS_CLEAR (error); cfilename = _dbus_string_get_const_data (filename); - - fd = _open (cfilename, O_WRONLY|O_CREAT|O_EXCL|O_BINARY, 0644); - - if (fd < 0) + + hnd = CreateFileA (cfilename, GENERIC_WRITE, + FILE_SHARE_READ | FILE_SHARE_WRITE, + NULL, CREATE_NEW, FILE_ATTRIBUTE_NORMAL, + INVALID_HANDLE_VALUE); + if (hnd == INVALID_HANDLE_VALUE) { - dbus_set_error (error, _dbus_error_from_errno (errno), - "Failed to open \"%s\": %s", cfilename, - strerror (errno)); + char *emsg = _dbus_win_error_string (GetLastError ()); + dbus_set_error (error, _dbus_win_error_from_last_error (), + "Could not create PID file %s: %s", + cfilename, emsg); + _dbus_win_free_error_string (emsg); return FALSE; } - if ((f = fdopen (fd, "w")) == NULL) + if (snprintf (pidstr, sizeof (pidstr), "%lu\n", pid) < 0) { - dbus_set_error (error, _dbus_error_from_errno (errno), - "Failed to fdopen fd %d: %s", fd, strerror (errno)); - _close (fd); + dbus_set_error (error, _dbus_error_from_system_errno (), + "Failed to format PID for \"%s\": %s", cfilename, + _dbus_strerror_from_errno ()); + CloseHandle (hnd); return FALSE; } - if (fprintf (f, "%lu\n", pid) < 0) + total = 0; + bytes_to_write = strlen (pidstr);; + + while (total < bytes_to_write) { - dbus_set_error (error, _dbus_error_from_errno (errno), - "Failed to write to \"%s\": %s", cfilename, - strerror (errno)); + DWORD bytes_written; + BOOL res; - fclose (f); - return FALSE; + res = WriteFile (hnd, pidstr + total, bytes_to_write - total, + &bytes_written, NULL); + + if (res == 0 || bytes_written <= 0) + { + char *emsg = _dbus_win_error_string (GetLastError ()); + dbus_set_error (error, _dbus_win_error_from_last_error (), + "Could not write to %s: %s", cfilename, emsg); + _dbus_win_free_error_string (emsg); + CloseHandle (hnd); + return FALSE; + } + + total += bytes_written; } - if (fclose (f) == EOF) + if (CloseHandle (hnd) == 0) { - dbus_set_error (error, _dbus_error_from_errno (errno), - "Failed to close \"%s\": %s", cfilename, - strerror (errno)); + char *emsg = _dbus_win_error_string (GetLastError ()); + dbus_set_error (error, _dbus_win_error_from_last_error (), + "Could not close file %s: %s", + cfilename, emsg); + _dbus_win_free_error_string (emsg); + return FALSE; } @@ -159,7 +193,7 @@ _dbus_write_pid_to_file_and_pipe (const DBusString *pidfile, DBusString pid; int bytes; - _dbus_verbose ("writing our pid to pipe %d\n", print_pid_pipe->fd_or_handle); + _dbus_verbose ("writing our pid to pipe %d\n", print_pid_pipe->fd); if (!_dbus_string_init (&pid)) { @@ -225,35 +259,63 @@ _dbus_change_to_daemon_user (const char *user, } void -_dbus_init_system_log (void) +_dbus_request_file_descriptor_limit (unsigned int limit) +{ +} + +void +_dbus_init_system_log (dbus_bool_t is_daemon) { - // FIXME! + /* OutputDebugStringA doesn't need any special initialization, do nothing */ } /** - * Log an informative message. Intended for use primarily by - * the system bus. + * Log a message to the system log file (e.g. syslog on Unix). * + * @param severity a severity value * @param msg a printf-style format string - * @param args arguments for the format string */ void -_dbus_log_info (const char *msg, va_list args) +_dbus_system_log (DBusSystemLogSeverity severity, const char *msg, ...) { - // FIXME! + va_list args; + + va_start (args, msg); + + _dbus_system_logv (severity, msg, args); + + va_end (args); } /** - * Log a security-related message. Intended for use primarily by - * the system bus. + * Log a message to the system log file (e.g. syslog on Unix). * + * @param severity a severity value * @param msg a printf-style format string * @param args arguments for the format string + * + * If the FATAL severity is given, this function will terminate the program + * with an error code. */ void -_dbus_log_security (const char *msg, va_list args) +_dbus_system_logv (DBusSystemLogSeverity severity, const char *msg, va_list args) { - // FIXME! + char *s = ""; + char buf[1024]; + + switch(severity) + { + case DBUS_SYSTEM_LOG_INFO: s = "info"; break; + case DBUS_SYSTEM_LOG_SECURITY: s = "security"; break; + case DBUS_SYSTEM_LOG_FATAL: s = "fatal"; break; + } + + sprintf(buf,"%s%s",s,msg); + vsprintf(buf,buf,args); + OutputDebugStringA(buf); + + if (severity == DBUS_SYSTEM_LOG_FATAL) + exit (1); } /** Installs a signal handler @@ -281,22 +343,16 @@ _dbus_stat(const DBusString *filename, DBusStat *statbuf, DBusError *error) { -#ifdef DBUS_WINCE - return TRUE; - //TODO -#else const char *filename_c; WIN32_FILE_ATTRIBUTE_DATA wfad; char *lastdot; DWORD rc; - PSID owner_sid, group_sid; - PSECURITY_DESCRIPTOR sd; _DBUS_ASSERT_ERROR_IS_CLEAR (error); filename_c = _dbus_string_get_const_data (filename); - if (!GetFileAttributesEx (filename_c, GetFileExInfoStandard, &wfad)) + if (!GetFileAttributesExA (filename_c, GetFileExInfoStandard, &wfad)) { _dbus_win_set_error_from_win_error (error, GetLastError ()); return FALSE; @@ -320,28 +376,36 @@ _dbus_stat(const DBusString *filename, statbuf->nlink = 1; - sd = NULL; - rc = GetNamedSecurityInfo ((char *) filename_c, SE_FILE_OBJECT, - OWNER_SECURITY_INFORMATION | - GROUP_SECURITY_INFORMATION, - &owner_sid, &group_sid, - NULL, NULL, - &sd); - if (rc != ERROR_SUCCESS) - { - _dbus_win_set_error_from_win_error (error, rc); - if (sd != NULL) - LocalFree (sd); - return FALSE; - } - #ifdef ENABLE_UID_TO_SID - /* FIXME */ - statbuf->uid = _dbus_win_sid_to_uid_t (owner_sid); - statbuf->gid = _dbus_win_sid_to_uid_t (group_sid); -#endif + { + PSID owner_sid, group_sid; + PSECURITY_DESCRIPTOR sd; + + sd = NULL; + rc = GetNamedSecurityInfo ((char *) filename_c, SE_FILE_OBJECT, + OWNER_SECURITY_INFORMATION | + GROUP_SECURITY_INFORMATION, + &owner_sid, &group_sid, + NULL, NULL, + &sd); + if (rc != ERROR_SUCCESS) + { + _dbus_win_set_error_from_win_error (error, rc); + if (sd != NULL) + LocalFree (sd); + return FALSE; + } + + /* FIXME */ + statbuf->uid = _dbus_win_sid_to_uid_t (owner_sid); + statbuf->gid = _dbus_win_sid_to_uid_t (group_sid); - LocalFree (sd); + LocalFree (sd); + } +#else + statbuf->uid = DBUS_UID_UNSET; + statbuf->gid = DBUS_GID_UNSET; +#endif statbuf->size = ((dbus_int64_t) wfad.nFileSizeHigh << 32) + wfad.nFileSizeLow; @@ -358,27 +422,9 @@ _dbus_stat(const DBusString *filename, wfad.ftCreationTime.dwLowDateTime) / 10000000 - DBUS_INT64_CONSTANT (116444736000000000); return TRUE; -#endif //DBUS_WINCE } -#ifdef HAVE_DIRENT_H - -// mingw ships with dirent.h -#include -#define _dbus_opendir opendir -#define _dbus_readdir readdir -#define _dbus_closedir closedir - -#else - -#ifdef HAVE_IO_H -#include // win32 file functions -#endif - -#include -#include - /* This file is part of the KDE project Copyright (C) 2000 Werner Almesberger @@ -418,10 +464,10 @@ struct dirent /* typedef DIR - not the same as Unix */ typedef struct { - long handle; /* _findfirst/_findnext handle */ - short offset; /* offset into directory */ + HANDLE handle; /* FindFirst/FindNext handle */ + short offset; /* offset into directory */ short finished; /* 1 if there are not more files */ - struct _finddata_t fileinfo; /* from _findfirst/_findnext */ + WIN32_FIND_DATAA fileinfo; /* from FindFirst/FindNext */ char *dir; /* the dir we are reading */ struct dirent dent; /* the dirent to return */ } @@ -437,6 +483,8 @@ DIR; * The dirent struct is compatible with Unix, except that d_ino is * always 1 and d_off is made up as we go along. * +* Error codes are not available with errno but GetLastError. +* * The DIR typedef is not compatible with Unix. **********************************************************************/ @@ -444,7 +492,7 @@ static DIR * _dbus_opendir(const char *dir) { DIR *dp; char *filespec; - long handle; + HANDLE handle; int index; filespec = malloc(strlen(dir) + 2 + 1); @@ -459,9 +507,10 @@ static DIR * _dbus_opendir(const char *dir) dp->finished = 0; dp->dir = strdup(dir); - if ((handle = _findfirst(filespec, &(dp->fileinfo))) < 0) + handle = FindFirstFileA(filespec, &(dp->fileinfo)); + if (handle == INVALID_HANDLE_VALUE) { - if (errno == ENOENT) + if (GetLastError() == ERROR_NO_MORE_FILES) dp->finished = 1; else return NULL; @@ -474,35 +523,40 @@ static DIR * _dbus_opendir(const char *dir) } static struct dirent * _dbus_readdir(DIR *dp) - { - if (!dp || dp->finished) - return NULL; - - if (dp->offset != 0) - { - if (_findnext(dp->handle, &(dp->fileinfo)) < 0) - { - dp->finished = 1; - errno = 0; - return NULL; - } - } - dp->offset++; +{ + int saved_err = GetLastError(); - strncpy(dp->dent.d_name, dp->fileinfo.name, _MAX_FNAME); - dp->dent.d_ino = 1; - dp->dent.d_reclen = strlen(dp->dent.d_name); - dp->dent.d_off = dp->offset; + if (!dp || dp->finished) + return NULL; - return &(dp->dent); - } + if (dp->offset != 0) + { + if (FindNextFileA(dp->handle, &(dp->fileinfo)) == 0) + { + if (GetLastError() == ERROR_NO_MORE_FILES) + { + SetLastError(saved_err); + dp->finished = 1; + } + return NULL; + } + } + dp->offset++; + + strncpy(dp->dent.d_name, dp->fileinfo.cFileName, _MAX_FNAME); + dp->dent.d_ino = 1; + dp->dent.d_reclen = strlen(dp->dent.d_name); + dp->dent.d_off = dp->offset; + + return &(dp->dent); +} static int _dbus_closedir(DIR *dp) { if (!dp) return 0; - _findclose(dp->handle); + FindClose(dp->handle); if (dp->dir) free(dp->dir); if (dp) @@ -511,7 +565,6 @@ static int _dbus_closedir(DIR *dp) return 0; } -#endif //#ifdef HAVE_DIRENT_H /** * Internals of directory iterator @@ -544,10 +597,11 @@ _dbus_directory_open (const DBusString *filename, d = _dbus_opendir (filename_c); if (d == NULL) { - dbus_set_error (error, _dbus_error_from_errno (errno), + char *emsg = _dbus_win_error_string (GetLastError ()); + dbus_set_error (error, _dbus_win_error_from_last_error (), "Failed to read directory \"%s\": %s", - filename_c, - _dbus_strerror (errno)); + filename_c, emsg); + _dbus_win_free_error_string (emsg); return NULL; } iter = dbus_new0 (DBusDirIter, 1); @@ -587,14 +641,17 @@ _dbus_directory_get_next_file (DBusDirIter *iter, _DBUS_ASSERT_ERROR_IS_CLEAR (error); again: - errno = 0; + SetLastError (0); ent = _dbus_readdir (iter->d); if (ent == NULL) { - if (errno != 0) - dbus_set_error (error, - _dbus_error_from_errno (errno), - "%s", _dbus_strerror (errno)); + if (GetLastError() != 0) + { + char *emsg = _dbus_win_error_string (GetLastError ()); + dbus_set_error (error, _dbus_win_error_from_last_error (), + "Failed to get next in directory: %s", emsg); + _dbus_win_free_error_string (emsg); + } return FALSE; } else if (ent->d_name[0] == '.' && @@ -625,23 +682,6 @@ _dbus_directory_close (DBusDirIter *iter) dbus_free (iter); } -/** - * Checks whether the filename is an absolute path - * - * @param filename the filename - * @returns #TRUE if an absolute path - */ -dbus_bool_t -_dbus_path_is_absolute (const DBusString *filename) -{ - if (_dbus_string_get_length (filename) > 0) - return _dbus_string_get_byte (filename, 1) == ':' - || _dbus_string_get_byte (filename, 0) == '\\' - || _dbus_string_get_byte (filename, 0) == '/'; - else - return FALSE; -} - /** @} */ /* End of DBusInternalsUtils functions */ /** @@ -1490,3 +1530,207 @@ _dbus_command_for_pid (unsigned long pid, // FIXME return FALSE; } + +/* + * replaces the term DBUS_PREFIX in configure_time_path by the + * current dbus installation directory. On unix this function is a noop + * + * @param configure_time_path + * @return real path + */ +const char * +_dbus_replace_install_prefix (const char *configure_time_path) +{ +#ifndef DBUS_PREFIX + return configure_time_path; +#else + static char retval[1000]; + static char runtime_prefix[1000]; + int len = 1000; + int i; + + if (!configure_time_path) + return NULL; + + if ((!_dbus_get_install_root(runtime_prefix, len) || + strncmp (configure_time_path, DBUS_PREFIX "/", + strlen (DBUS_PREFIX) + 1))) { + strcat (retval, configure_time_path); + return retval; + } + + strcpy (retval, runtime_prefix); + strcat (retval, configure_time_path + strlen (DBUS_PREFIX) + 1); + + /* Somehow, in some situations, backslashes get collapsed in the string. + * Since windows C library accepts both forward and backslashes as + * path separators, convert all backslashes to forward slashes. + */ + + for(i = 0; retval[i] != '\0'; i++) { + if(retval[i] == '\\') + retval[i] = '/'; + } + return retval; +#endif +} + +/** + * return the relocated DATADIR + * + * @returns relocated DATADIR static string + */ + +static const char * +_dbus_windows_get_datadir (void) +{ + return _dbus_replace_install_prefix(DBUS_DATADIR); +} + +#undef DBUS_DATADIR +#define DBUS_DATADIR _dbus_windows_get_datadir () + + +#define DBUS_STANDARD_SESSION_SERVICEDIR "/dbus-1/services" +#define DBUS_STANDARD_SYSTEM_SERVICEDIR "/dbus-1/system-services" + +/** + * Returns the standard directories for a session bus to look for service + * activation files + * + * On Windows this should be data directories: + * + * %CommonProgramFiles%/dbus + * + * and + * + * relocated DBUS_DATADIR + * + * @param dirs the directory list we are returning + * @returns #FALSE on OOM + */ + +dbus_bool_t +_dbus_get_standard_session_servicedirs (DBusList **dirs) +{ + const char *common_progs; + DBusString servicedir_path; + + if (!_dbus_string_init (&servicedir_path)) + return FALSE; + +#ifdef DBUS_WINCE + { + /* On Windows CE, we adjust datadir dynamically to installation location. */ + const char *data_dir = _dbus_getenv ("DBUS_DATADIR"); + + if (data_dir != NULL) + { + if (!_dbus_string_append (&servicedir_path, data_dir)) + goto oom; + + if (!_dbus_string_append (&servicedir_path, _DBUS_PATH_SEPARATOR)) + goto oom; + } + } +#else +/* + the code for accessing services requires absolute base pathes + in case DBUS_DATADIR is relative make it absolute +*/ +#ifdef DBUS_WIN + { + DBusString p; + + _dbus_string_init_const (&p, DBUS_DATADIR); + + if (!_dbus_path_is_absolute (&p)) + { + char install_root[1000]; + if (_dbus_get_install_root (install_root, sizeof(install_root))) + if (!_dbus_string_append (&servicedir_path, install_root)) + goto oom; + } + } +#endif + if (!_dbus_string_append (&servicedir_path, DBUS_DATADIR)) + goto oom; + + if (!_dbus_string_append (&servicedir_path, _DBUS_PATH_SEPARATOR)) + goto oom; +#endif + + common_progs = _dbus_getenv ("CommonProgramFiles"); + + if (common_progs != NULL) + { + if (!_dbus_string_append (&servicedir_path, common_progs)) + goto oom; + + if (!_dbus_string_append (&servicedir_path, _DBUS_PATH_SEPARATOR)) + goto oom; + } + + if (!_dbus_split_paths_and_append (&servicedir_path, + DBUS_STANDARD_SESSION_SERVICEDIR, + dirs)) + goto oom; + + _dbus_string_free (&servicedir_path); + return TRUE; + + oom: + _dbus_string_free (&servicedir_path); + return FALSE; +} + +/** + * Returns the standard directories for a system bus to look for service + * activation files + * + * On UNIX this should be the standard xdg freedesktop.org data directories: + * + * XDG_DATA_DIRS=${XDG_DATA_DIRS-/usr/local/share:/usr/share} + * + * and + * + * DBUS_DATADIR + * + * On Windows there is no system bus and this function can return nothing. + * + * @param dirs the directory list we are returning + * @returns #FALSE on OOM + */ + +dbus_bool_t +_dbus_get_standard_system_servicedirs (DBusList **dirs) +{ + *dirs = NULL; + return TRUE; +} + +/** + * Append the absolute path of the system.conf file + * (there is no system bus on Windows so this can just + * return FALSE and print a warning or something) + * + * @param str the string to append to + * @returns #FALSE if no memory + */ +dbus_bool_t +_dbus_append_system_config_file (DBusString *str) +{ + return _dbus_get_config_file_name(str, "system.conf"); +} + +/** + * Append the absolute path of the session.conf file. + * + * @param str the string to append to + * @returns #FALSE if no memory + */ +dbus_bool_t +_dbus_append_session_config_file (DBusString *str) +{ + return _dbus_get_config_file_name(str, "session.conf"); +}