/** ******************************************************************************* * @brief Get the executable path for a given pid. * * @param pid IN pid * @param lserror OUT set on error * * @retval executable path on success * @retval NULL on failure ******************************************************************************* */ static char* _LSTransportPidToExe(pid_t pid, LSError *lserror) { GError *error = NULL; char *ret = NULL; char *root = NULL; char *exe = NULL; char *proc_exe_path = g_strdup_printf("/proc/%d/exe", pid); char *proc_root_path = g_strdup_printf("/proc/%d/root",pid); if (!proc_exe_path || !proc_root_path) { _LSErrorSetOOM(lserror); goto cleanup; } exe = g_file_read_link(proc_exe_path, &error); if (!exe) { _LSErrorSetFromGError(lserror, error); goto cleanup; } root = g_file_read_link(proc_root_path, &error); if (!root) { _LSErrorSetFromGError(lserror, error); goto cleanup; } int rootlen = strlen(root); if ((rootlen > 1) && (strncmp(exe, root, rootlen) == 0)) { /* /proc/<pid>/root is not a link to "/" so subtract * it from the exe path (it's probably an app running in jail) */ ret = g_strdup(exe + rootlen); } else { ret = g_strdup(exe); } cleanup: if (proc_exe_path) g_free(proc_exe_path); if (proc_root_path) g_free(proc_root_path); if (exe) g_free(exe); if (root) g_free(root); return ret; }
/** * gpk_dbus_get_exec_for_sender: **/ static gchar * gpk_dbus_get_exec_for_sender (GpkDbus *dbus, const gchar *sender) { gchar *filename = NULL; gchar *cmdline = NULL; GError *error = NULL; guint pid; g_return_val_if_fail (PK_IS_DBUS (dbus), NULL); g_return_val_if_fail (sender != NULL, NULL); /* get pid */ pid = gpk_dbus_get_pid (dbus, sender); if (pid == G_MAXUINT) { g_warning ("failed to get PID"); goto out; } /* get command line from proc */ filename = g_strdup_printf ("/proc/%i/exe", pid); cmdline = g_file_read_link (filename, &error); if (cmdline == NULL) { g_warning ("failed to find exec: %s", error->message); g_error_free (error); } out: g_free (filename); return cmdline; }
static gchar* get_device_name (const gchar *major_minor, GError **error) { gchar *path = NULL; gchar *link = NULL; gchar *ret = NULL; path = g_strdup_printf ("/dev/block/%s", major_minor); link = g_file_read_link (path, error); g_free (path); if (!link) { g_prefix_error (error, "Failed to determine device name for '%s'", major_minor); return NULL; } /* 'link' should be something like "../sda" */ /* get the last '/' */ ret = strrchr (link, '/'); if (!ret) { g_set_error (error, BD_MPATH_ERROR, BD_MPATH_ERROR_INVAL, "Failed to determine device name for '%s'", major_minor); g_free (link); return NULL; } /* move right after the last '/' */ ret++; /* create a new copy and free the whole link path */ ret = g_strdup (ret); g_free (link); return ret; }
GtkStatusIcon* ui_statusicon() { GObject* status_icon = gtk_builder_get_object(builder, "statusicon"); #ifdef DEBUG GError* error = NULL; gchar* exe_path = g_file_read_link("/proc/self/exe", &error); if(error) { g_message("g_file_read_link() failed (%s)", error->message); g_error_free(error); g_free(exe_path); return GTK_STATUS_ICON(status_icon); } gchar* dirname = g_path_get_dirname(exe_path); g_free(exe_path); gchar* icon_file = g_build_path("/", dirname, "../data/pasystray.svg", NULL); g_free(dirname); if(g_file_test(icon_file, G_FILE_TEST_EXISTS)) { gtk_status_icon_set_from_file(GTK_STATUS_ICON(status_icon), icon_file); g_message("using icon: %s", icon_file); } g_free(icon_file); #endif return GTK_STATUS_ICON(status_icon); }
gchar* termit_get_pid_dir(pid_t pid) { gchar* file = g_strdup_printf("/proc/%d/cwd", pid); gchar* link = g_file_read_link(file, NULL); g_free(file); return link; }
static int GetMimeClassic(const char * path_folder, const char * full_name) { struct stat file_stat; if(lstat( full_name, &file_stat )) return ICON_GNOME_TEXT; if(S_ISDIR(file_stat.st_mode)) return ICON_GNOME_FOLDER; int mime_type=ICON_GNOME_TEXT; if(S_ISLNK(file_stat.st_mode)) { ClassString link=g_file_read_link(full_name,NULL); if(link.s) { if(link.s[0]!='/') link = g_build_filename(path_folder,link.s,NULL); } if(link.s && !lstat( link.s, &file_stat ) ) { mime_type=GetMimeForFile(link.s,&file_stat); mime_type|=MIME_FLAG_LINK; } else { mime_type=ICON_GNOME_BREAK_LINK; mime_type|=MIME_FLAG_LINK; printf("error l=%s n=%s\n",link.s,full_name); } } else mime_type=GetMimeForFile(full_name,&file_stat); return mime_type; }
static int get_file_type (const char *sound_name, char **linked_name) { char *name, *filename; *linked_name = NULL; name = g_strdup_printf ("%s.disabled", sound_name); filename = custom_theme_dir_path (name); g_free (name); if (g_file_test (filename, G_FILE_TEST_IS_REGULAR) != FALSE) { g_free (filename); return SOUND_TYPE_OFF; } g_free (filename); /* We only check for .ogg files because those are the * only ones we create */ name = g_strdup_printf ("%s.ogg", sound_name); filename = custom_theme_dir_path (name); g_free (name); if (g_file_test (filename, G_FILE_TEST_IS_SYMLINK) != FALSE) { *linked_name = g_file_read_link (filename, NULL); g_free (filename); return SOUND_TYPE_CUSTOM; } g_free (filename); return SOUND_TYPE_BUILTIN; }
static void _restart_server (void) { gchar *exe; gint fd; exe = g_strdup_printf ("/proc/%d/exe", getpid ()); exe = g_file_read_link (exe, NULL); if (exe == NULL) exe = BINDIR "/ibus-daemon"; /* close all fds except stdin, stdout, stderr */ for (fd = 3; fd <= sysconf (_SC_OPEN_MAX); fd ++) { close (fd); } _restart = FALSE; execv (exe, g_argv); /* If the server binary is replaced while the server is running, * "readlink /proc/[pid]/exe" might return a path with " (deleted)" * suffix. */ const gchar suffix[] = " (deleted)"; if (g_str_has_suffix (exe, suffix)) { exe [strlen (exe) - sizeof (suffix) + 1] = '\0'; execv (exe, g_argv); } g_warning ("execv %s failed!", g_argv[0]); exit (-1); }
static VFIOGroup *vfio_ap_get_group(VFIOAPDevice *vapdev, Error **errp) { GError *gerror = NULL; char *symlink, *group_path; int groupid; symlink = g_strdup_printf("%s/iommu_group", vapdev->vdev.sysfsdev); group_path = g_file_read_link(symlink, &gerror); g_free(symlink); if (!group_path) { error_setg(errp, "%s: no iommu_group found for %s: %s", VFIO_AP_DEVICE_TYPE, vapdev->vdev.sysfsdev, gerror->message); return NULL; } if (sscanf(basename(group_path), "%d", &groupid) != 1) { error_setg(errp, "vfio: failed to read %s", group_path); g_free(group_path); return NULL; } g_free(group_path); return vfio_get_group(groupid, &address_space_memory, errp); }
static gchar * mmp_plugin_proxy_get_xpi_moonlight_path () { // If Moonlight is installed by the user into their Firefox profile (XPI), // we need to find the directory. Originally I used XPCOM and the directory // service provided by Mozilla, but I really wanted to avoid libstdc++ // and linking against libxpcom, etc. // // Instead I use an lsof inspired hack to look for the profile directory // of the running process. // gchar pid_path[32]; gchar fd_path[sizeof (pid_path) * 2]; const gchar *fd_name = NULL; gchar *xpi_dir = NULL; GDir *dir; if ((gsize)g_snprintf (pid_path, sizeof (pid_path), "/proc/%d/fd", getpid ()) > sizeof (pid_path)) { return NULL; } if ((dir = g_dir_open (pid_path, 0, NULL)) == NULL) { return NULL; } while (xpi_dir == NULL && (fd_name = g_dir_read_name (dir)) != NULL) { gchar *fd_resolved_path; gchar *file_name; gchar *dir_name; gint ext_offset; if ((gsize)g_snprintf (fd_path, sizeof (fd_path), "%s/%s", pid_path, fd_name) > sizeof (fd_path) || (fd_resolved_path = g_file_read_link (fd_path, NULL)) == NULL) { continue; } file_name = g_path_get_basename (fd_resolved_path); ext_offset = strlen (file_name) - strlen (".sqlite"); if (strcmp (file_name, ".parentlock") == 0 || (ext_offset > 0 && strcmp (file_name + ext_offset, ".sqlite") == 0)) { dir_name = g_path_get_dirname (fd_resolved_path); xpi_dir = g_build_filename (dir_name, "extensions", "*****@*****.**", "plugins", NULL); g_free (dir_name); } g_free (file_name); g_free (fd_resolved_path); } g_dir_close (dir); return xpi_dir; }
string real_regular_path(string path) { if (!g_path_is_absolute(path.c_str())) return "" ; if (!g_file_test(path.c_str(), G_FILE_TEST_EXISTS)) return "" ; // compute realpath FileInfo info(path) ; path = info.realpath() ; // remove symlink string base = "" ; string dir = path ; string symdone = "" ; std::vector<string> bases ; // for each step in path check if we're a symlink while (base!=dir && !dir.empty() && symdone.empty()) { // keep all basenames we skip if (!base.empty()) bases.insert(bases.begin(), base) ; // if we have a symlink, resolve it if ( g_file_test(dir.c_str(), G_FILE_TEST_IS_SYMLINK) ) { GError** error ; dir = g_file_read_link(dir.c_str(), error) ; symdone = dir ; } // prepare for next loop base = g_path_get_basename(dir.c_str()) ; dir = g_path_get_dirname(dir.c_str()) ; #ifdef WIN32 if (base == "\\") base = dir; #endif } if (!symdone.empty()) { std::vector<string>::iterator it ; path = symdone ; // reconstruct path from symdone with all skipped basenames for (it=bases.begin(); it!=bases.end(); it++) { FileInfo info(path) ; path = std::string(info.join(*it)) ; } // check if the newly path really exist (if not, we've done an error) if (!g_file_test(path.c_str(), G_FILE_TEST_EXISTS)) path = "" ; } return path ; }
static void child_check_open_fds(void) { for (int i = 3; i < 128; i++) { gchar *proc = g_strdup_printf("/proc/%d/fd/%d", getpid(), i); gchar *link = g_file_read_link(proc, NULL); g_free(proc); if (link != NULL) { printf("%s\n", link); g_free(link); } } }
/** * Retrieve some basic information about system. */ void appInfo() { GError *err; // get some system data appPid = getpid(); appPath = g_file_read_link("/proc/self/exe", &err); appHomeDir = g_get_home_dir(); appUserName = g_get_user_name(); appRealName = g_get_real_name(); appHostName = g_get_host_name(); }
char * util_resolve_symlink(char *path) { char *ret = path; if (g_file_test(path, G_FILE_TEST_IS_SYMLINK)) { ret = g_file_read_link(path, NULL); if (ret == NULL) return path; g_free(path); } return ret; }
char * frida_test_process_backend_filename_of (void * handle) { #ifdef HAVE_QNX g_assert (handle == &frida_magic_self_handle); struct dlopen_handle ** _handle = dlopen (NULL, RTLD_NOW); struct dlopen_handle * p_u = *(_handle); return g_strdup (p_u->p_lm->l_path); #else return g_file_read_link ("/proc/self/exe", NULL); #endif }
// FIXME put in g_roccat_helper static gchar *g_roccat_file_read_link_utf8(gchar const *filename, GError **error) { gchar *link; gchar *utf8_link; link = g_file_read_link(filename, error); if (*error) return NULL; utf8_link = g_filename_to_utf8(link, -1, NULL, NULL, error); g_free(link); if (*error) return NULL; return utf8_link; }
/* Read the soft symlink from /etc/localtime */ static gchar * system_timezone_read_etc_localtime_softlink (GHashTable *ical_zones) { gchar *file; gchar *tz; if (!g_file_test (ETC_LOCALTIME, G_FILE_TEST_IS_SYMLINK)) return NULL; file = g_file_read_link (ETC_LOCALTIME, NULL); tz = system_timezone_strip_path_if_valid (file); g_free (file); return tz; }
FridaHostProcessInfo * frida_system_enumerate_processes (int * result_length1) { GArray * processes; FridaImageData no_icon; GDir * proc_dir; const gchar * proc_name; processes = g_array_new (FALSE, FALSE, sizeof (FridaHostProcessInfo)); frida_image_data_init (&no_icon, 0, 0, 0, ""); proc_dir = g_dir_open ("/proc", 0, NULL); g_assert (proc_dir != NULL); while ((proc_name = g_dir_read_name (proc_dir)) != NULL) { guint pid; gchar * tmp = NULL; gchar * name; FridaHostProcessInfo * process_info; pid = strtoul (proc_name, &tmp, 10); if (*tmp != '\0') continue; tmp = g_build_filename ("/proc", proc_name, "exe", NULL); name = g_file_read_link (tmp, NULL); g_free (tmp); if (name == NULL) continue; tmp = g_path_get_basename (name); g_free (name); name = tmp; g_array_set_size (processes, processes->len + 1); process_info = &g_array_index (processes, FridaHostProcessInfo, processes->len - 1); frida_host_process_info_init (process_info, pid, name, &no_icon, &no_icon); g_free (name); } g_dir_close (proc_dir); *result_length1 = processes->len; return (FridaHostProcessInfo *) g_array_free (processes, FALSE); }
char *common_get_fd_path(int fd) { struct stat st; if (fstat(fd, &st)) { return NULL; } #if defined WIN32 // Windows HANDLE hdl = (HANDLE) _get_osfhandle(fd); if (hdl != INVALID_HANDLE_VALUE) { DWORD size = GetFinalPathNameByHandle(hdl, NULL, 0, 0); if (size) { char *path = g_malloc(size); DWORD ret = GetFinalPathNameByHandle(hdl, path, size - 1, 0); if (ret > 0 && ret <= size) { return path; } g_free(path); } } #elif defined HAVE_PROC_PIDFDINFO // Mac OS X // Ignore kqueues, since they can be opened behind our back for // Grand Central Dispatch struct kqueue_fdinfo kqi; if (proc_pidfdinfo(getpid(), fd, PROC_PIDFDKQUEUEINFO, &kqi, sizeof(kqi))) { return NULL; } char *path = g_malloc(MAXPATHLEN); if (!fcntl(fd, F_GETPATH, path)) { return path; } g_free(path); #else // Fallback; works only on Linux char *link_path = g_strdup_printf("/proc/%d/fd/%d", getpid(), fd); char *path = g_file_read_link(link_path, NULL); g_free(link_path); if (path) { return path; } #endif return g_strdup("<unknown>"); }
/* Calls g_file_read_link() until we find a real filename. */ static char * follow_symlinks (char const *filename, GError **error) { gchar *followed_filename, *link; gint link_count = 0; g_return_val_if_fail (filename != NULL, NULL); followed_filename = g_strdup (filename); while ((link = g_file_read_link (followed_filename, NULL)) != NULL && ++link_count <= GSF_MAX_LINK_LEVEL) { if (g_path_is_absolute (link)) { g_free (followed_filename); followed_filename = link; } else { /* If the linkname is not an absolute path name, append * it to the directory name of the followed filename. E.g. * we may have /foo/bar/baz.lnk -> eek.txt, which really * is /foo/bar/eek.txt. */ gchar *dir = g_path_get_dirname (followed_filename); g_free (followed_filename); followed_filename = g_build_filename (dir, link, NULL); g_free (dir); g_free (link); } } if (link == NULL) return followed_filename; /* Too many symlinks */ if (error != NULL) { #ifdef ELOOP int err = ELOOP; #else /* We have links, but not ELOOP. Very strange. */ int err = EINVAL; #endif *error = g_error_new_literal (gsf_output_error_id (), err, g_strerror (err)); } g_free (followed_filename); return NULL; }
static void init_seafile_path () { GError *error = NULL; char *binary = g_file_read_link ("/proc/self/exe", &error); char *tmp = NULL; if (error != NULL) { seaf_warning ("failed to readlink: %s\n", error->message); return; } bin_dir = g_path_get_dirname (binary); tmp = g_path_get_dirname (bin_dir); installpath = g_path_get_dirname (tmp); topdir = g_path_get_dirname (installpath); g_free (binary); g_free (tmp); }
void ui_init() { GtkWidget *window = NULL; GtkBuilder *builder; GError *err = NULL; gchar *exec_name = NULL; gchar *tmp = NULL; gchar exe_path[MAX_PATH]; GtkEntry *entry; gtk_init(NULL, NULL); builder = gtk_builder_new(); exec_name = g_file_read_link("/proc/self/exe", NULL); tmp = g_strrstr(exec_name, "/"); *tmp = 0; g_strlcpy(exe_path, exec_name, MAX_PATH); g_strlcat(exe_path, "/audio_player.glade", MAX_PATH); g_free(exec_name); gtk_builder_add_from_file(builder, exe_path, &err); gtk_builder_connect_signals(builder, NULL); window = GTK_WIDGET(gtk_builder_get_object(builder, "main_window")); main_window_sub_widget.statusbar = GTK_STATUSBAR(gtk_builder_get_object(builder, "statusbar1")); main_window_sub_widget.contextId = gtk_statusbar_get_context_id( GTK_STATUSBAR(main_window_sub_widget.statusbar), "Editor Messages"); entry = GTK_ENTRY(gtk_builder_get_object(builder, "entry1")); main_window_sub_widget.entry1 = entry; g_signal_connect(window, "destroy", G_CALLBACK (gtk_main_quit), &window); g_object_unref(G_OBJECT(builder)); gtk_widget_show_all(window); }
static GVariant *get_timezone(void) { gchar *link, *zone; GVariant *ret; link = g_file_read_link(LOCALTIME_PATH, NULL); if (!link) goto error; zone = g_strrstr(link, ZONEINFO_PATH); if (!zone) goto error; zone += strlen(ZONEINFO_PATH); ret = g_variant_new_string(zone); g_free(link); return ret; error: /* Empty string means N/A */ return g_variant_new_string(""); }
static char * get_location (void) { static char location [256]; char *buffer; FILE *zone; int i, len, count; /* Old method : works for glibc < 2.2 */ zone = fopen("/etc/timezone", "r"); if (zone) { count = fscanf (zone, "%255s", location); fclose (zone); /* if we could read it, we return what we got */ if (count == 1) return location; } /* New method : works for glibc 2.2 */ /* FIXME: this is broken for many distros, see the clock code */ buffer = g_file_read_link ("/etc/localtime", NULL); if (!buffer) return NULL; len = strlen (buffer); for (i = len, count = 0; (i > 0) && (count != 2); i--) if (buffer [i] == '/') count++; if (count != 2) { return NULL; g_free (buffer); } memcpy (location, &buffer [i + 2], len - i - 2); g_free (buffer); return location; }
// It will return NULL if fault // The returned string should be freed when no longer needed. gchar *get_tab_name_with_current_dir(pid_t pid) { #ifdef FULL g_debug("! Launch get_tab_name_with_current_dir() for pid %d", pid); #endif if (! proc_exist) return NULL; if (pid>0) { gchar *cwd_path = g_strdup_printf("/proc/%d/cwd", pid); #ifdef DEFENSIVE if (cwd_path) { #endif gchar *current_dir = g_file_read_link(cwd_path, NULL); g_free(cwd_path); return current_dir; #ifdef DEFENSIVE } #endif } return NULL; }
/* dwb_check_directory(char *filename (alloc) ) return: char * (alloc) {{{*/ char * util_check_directory(char *filename) { GError *error = NULL; char *ret = filename; g_return_val_if_fail(filename != NULL, NULL); if (g_file_test(filename, G_FILE_TEST_IS_SYMLINK)) { ret = g_file_read_link(filename, &error); if (error != NULL) { fprintf(stderr, "Cannot read link %s : %s, creating a new directory\n", filename, error->message); g_mkdir_with_parents(filename, 0700); ret = filename; g_clear_error(&error); } else g_free(filename); } else if (! g_file_test(filename, G_FILE_TEST_IS_DIR) ) g_mkdir_with_parents(filename, 0700); return ret; }/*}}}*/
/* Returns the working directory of the terminal * * @param tt the tilda_term to get working directory of * * SUCCESS: return non-NULL char* that should be freed with g_free when done * FAILURE: return NULL */ char* tilda_term_get_cwd(struct tilda_term_* tt) { char *file; char *cwd; GError *error = NULL; if (tt->pid < 0) { return NULL; } file = g_strdup_printf ("/proc/%d/cwd", tt->pid); cwd = g_file_read_link (file, &error); g_free (file); if (cwd == NULL) { g_printerr (_("Problem reading link %s: %s\n"), file, error->message); g_error_free (error); } return cwd; }
/* util_set_file_content(const char *filename, const char *content) {{{*/ gboolean util_set_file_content(const char *filename, const char *content) { GError *error = NULL; gboolean ret = true; char *link = NULL; char *dname = NULL; char *realpath = NULL; char buffer[PATH_MAX]; if (content == NULL || filename == NULL) return false; filename = util_expand_home(buffer, filename, sizeof(buffer)); if (g_file_test(filename, G_FILE_TEST_IS_SYMLINK)) { link = g_file_read_link(filename, &error); if (link == NULL) { fprintf(stderr, "Cannot save %s : %s\n", filename, error->message); g_clear_error(&error); return false; } dname = g_path_get_dirname(filename); realpath = g_build_filename(dname, link, NULL); g_free(link); g_free(dname); filename = realpath; } if (!g_file_set_contents(filename, content, -1, &error)) { fprintf(stderr, "Cannot save %s : %s", filename, error->message); g_clear_error(&error); ret = false; } g_free(realpath); return ret; }/*}}}*/
char* get_file_or_linked(char *loc, char *basedir) { char *true_loc = NULL; // check for symlink if (g_file_test(loc, G_FILE_TEST_IS_SYMLINK)) { true_loc = g_file_read_link(loc, NULL); // if relative, add basedir if (!g_str_has_prefix(true_loc, "/") && !g_str_has_prefix(true_loc, "~")) { GString *base_str = g_string_new(basedir); g_string_append(base_str, true_loc); free(true_loc); true_loc = base_str->str; g_string_free(base_str, FALSE); } // use given location } else { true_loc = strdup(loc); } return true_loc; }
bool PluginPackage::load() { if (m_isLoaded) { m_loadCount++; return true; } GOwnPtr<gchar> finalPath(g_strdup(m_path.utf8().data())); while (g_file_test(finalPath.get(), G_FILE_TEST_IS_SYMLINK)) { GOwnPtr<GFile> file(g_file_new_for_path(finalPath.get())); GOwnPtr<GFile> dir(g_file_get_parent(file.get())); GOwnPtr<gchar> linkPath(g_file_read_link(finalPath.get(), 0)); GOwnPtr<GFile> resolvedFile(g_file_resolve_relative_path(dir.get(), linkPath.get())); finalPath.set(g_file_get_path(resolvedFile.get())); } // No joke. If there is a netscape component in the path, go back // to the symlink, as flash breaks otherwise. // See http://src.chromium.org/viewvc/chrome/trunk/src/webkit/glue/plugins/plugin_list_posix.cc GOwnPtr<gchar> baseName(g_path_get_basename(finalPath.get())); if (!g_strcmp0(baseName.get(), "libflashplayer.so") && g_strstr_len(finalPath.get(), -1, "/netscape/")) finalPath.set(g_strdup(m_path.utf8().data())); m_module = g_module_open(finalPath.get(), G_MODULE_BIND_LOCAL); if (!m_module) { LOG(Plugins,"Module Load Failed :%s, Error:%s\n", (m_path.utf8()).data(), g_module_error()); return false; } m_isLoaded = true; NP_InitializeFuncPtr NP_Initialize = 0; m_NPP_Shutdown = 0; NPError npErr; g_module_symbol(m_module, "NP_Initialize", (void**)&NP_Initialize); g_module_symbol(m_module, "NP_Shutdown", (void**)&m_NPP_Shutdown); if (!NP_Initialize || !m_NPP_Shutdown) goto abort; memset(&m_pluginFuncs, 0, sizeof(m_pluginFuncs)); m_pluginFuncs.size = sizeof(m_pluginFuncs); initializeBrowserFuncs(); #if defined(XP_UNIX) npErr = NP_Initialize(&m_browserFuncs, &m_pluginFuncs); #else npErr = NP_Initialize(&m_browserFuncs); #endif if (npErr != NPERR_NO_ERROR) goto abort; m_loadCount++; return true; abort: unloadWithoutShutdown(); return false; }