/* $Id$ * Drivers acquiring installation utility * Copyright (C) 2003 Jan Kratochvil * * This program is free software; you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by * the Free Software Foundation; exactly version 2 of June 1991 is required * * This program is distributed in the hope that it will be useful, * but WITHOUT ANY WARRANTY; without even the implied warranty of * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the * GNU General Public License for more details. * * You should have received a copy of the GNU General Public License * along with this program; if not, write to the Free Software * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA */ #include "config.h" #include "ui-line.h" /* self */ #include #include "moduriload.h" #include "main.h" #include #include #include "final.h" #ifdef HAVE_LIBREADLINE #include #ifdef HAVE_READLINE_HISTORY_H #include #endif /* HAVE_READLINE_HISTORY_H */ #endif /* HAVE_LIBREADLINE */ #include static void print_ui_line_module_available(struct module_available *module_available) { gint priority_best; g_return_if_fail(module_available!=NULL); g_return_if_fail(module_available->module!=NULL); if (G_MININT==(priority_best=captivemodid_module_type_best_priority_lookup(module_available->module->type))) printf(_("Found best available \"%s\": %s\n"),module_available->module->type,module_available->module->id); else printf(_("Found although not best \"%s\" (pri=%d; best=%d): %s\n"), module_available->module->type,module_available->module->priority,priority_best, module_available->module->id); } static void ui_line_module_available_notify(struct module_available *module_available) { g_return_if_fail(module_available!=NULL); print_ui_line_module_available(module_available); printf(_("at URI: %s\n"),module_available->uri_text); } static gboolean all_modules_found=FALSE; static void ui_line_all_modules_found_notify(void) { puts(_("All modules found in their best known versions.")); all_modules_found=TRUE; } static gboolean aborted=FALSE; static time_t search_start_time; static gboolean abort_msg_printed=FALSE; static gboolean ui_line_progress(GnomeVFSURI *uri) { fd_set readfds; struct timeval timeval; /* 'uri' may be NULL */ if (aborted) return TRUE; if (all_modules_found) return TRUE; if (!search_start_time) search_start_time=time(NULL); if (!abort_msg_printed && time(NULL)>=search_start_time+2) { puts(_("Searching... Hit ENTER to abort.")); abort_msg_printed=TRUE; } if (isatty(0)) { FD_ZERO(&readfds); FD_SET(0,&readfds); timeval.tv_sec=0; timeval.tv_usec=0; if (1==select(1,&readfds,NULL,NULL,&timeval)) { aborted=TRUE; getchar(); puts(_("*** OPERATION ABORTED ***")); return TRUE; } } return FALSE; } static void ui_line_progress_reset(void) { aborted=FALSE; search_start_time=0; abort_msg_printed=FALSE; } static char *line_read(const gchar *prompt) { #ifdef HAVE_LIBREADLINE char *line; #else /* HAVE_LIBREADLINE */ char line[1024],*s; #endif /* HAVE_LIBREADLINE */ g_return_val_if_fail(prompt!=NULL,NULL); ui_line_progress_reset(); #ifdef HAVE_LIBREADLINE line=readline(prompt); #ifdef HAVE_ADD_HISTORY if (line && *line) add_history(line); #endif /* HAVE_ADD_HISTORY */ #else /* HAVE_LIBREADLINE */ fputs(prompt,stdout); fflush(stdout); line=fgets(line,sizeof(line),stdin); #endif /* HAVE_LIBREADLINE */ if (!line) return NULL; #ifndef HAVE_LIBREADLINE if (line && (s=strchr(line,'\n'))) *s='\0'; #endif /* HAVE_LIBREADLINE */ return line; } /* FIXME: HACK: Encode module essentiality to '.captivemodid.xml'. */ struct print_modules_available_foreach_param { gboolean do_print; gboolean ntoskrnl_exe_found; gboolean ntfs_sys_found; }; static void print_modules_available_foreach (const xmlChar *type /* key */,struct module_available *module_available /* value */, struct print_modules_available_foreach_param *param /* user_data */) { g_return_if_fail(type!=NULL); g_return_if_fail(module_available!=NULL); g_return_if_fail(module_available->module!=NULL); g_return_if_fail(!strcmp(type,module_available->module->type)); g_return_if_fail(param!=NULL); if (param->do_print) print_ui_line_module_available(module_available); /**/ if (!strcmp(type,"ntoskrnl.exe")) param->ntoskrnl_exe_found=TRUE; else if (!strcmp(type,"ntfs.sys")) param->ntfs_sys_found=TRUE; } /* Returns: TRUE if essential modules were found at any priority. */ static gboolean print_modules_available(void) { struct print_modules_available_foreach_param param; gboolean r; static gboolean first_time=TRUE; putchar('\n'); param.do_print=!first_time; param.ntoskrnl_exe_found=FALSE; param.ntfs_sys_found=FALSE; if (module_available_hash) g_hash_table_foreach(module_available_hash,(GHFunc)print_modules_available_foreach,¶m); r=param.ntoskrnl_exe_found && param.ntfs_sys_found; if (!param.ntoskrnl_exe_found) printf(_("Still needed essential module: %s\n"),"ntoskrnl.exe"); if (!param.ntfs_sys_found) printf(_("Still needed essential module: %s\n"),"ntfs.sys"); if (r) puts(_( "Essential modules (\"ntoskrnl.exe\" and \"ntfs.sys\") are available.\n" "You may still want to get their better version and/or more modules.")); putchar('\n'); first_time=FALSE; return r; } static gboolean ui_line_interactive_ask(const gchar *prompt) { char *line; gboolean essentials_available; if (all_modules_found) return FALSE; essentials_available=print_modules_available(); puts(prompt); for (;;) { line=line_read(captive_printf_alloca(_("Enter 'y' for YES, 'n' to NO%s [hit ENTER for YES]: "), (!essentials_available ? "" : _(", 'd' if DONE")))); if (!line) return FALSE; if (!strncasecmp(line,_("yes"),strlen(line))) { free(line); return TRUE; } if (!strncasecmp(line,_("no"),strlen(line))) { free(line); return FALSE; } if (!strncasecmp(line,_("done"),strlen(line))) { putchar('\n'); puts(final_text(all_modules_found)); exit(EXIT_SUCCESS); } free(line); } /* NOTREACHED */ } static void ui_line_interactive(void) { #ifndef HAVE_LIBREADLINE puts(_("Line editing not available, please recompile with readline library installed")); #endif /* HAVE_LIBREADLINE */ if (ui_line_interactive_ask(_("Quickly scan your local disks to find needed drivers?"))) scan_disks_quick(); while (!all_modules_found) { char *line; if (ui_line_interactive_ask(_("Fully scan all directories of your local disks?"))) scan_disks(); if (!all_modules_found) do { print_modules_available(); puts(_("Do you want to enter your custom search path and/or files? You can also enter web URL.")); line=line_read(_("Enter pathname or URL [hit ENTER to skip it]: ")); if (line && *line) { GnomeVFSURI *uri; uri=gnome_vfs_uri_new((strncmp(line,"http://",strlen("http://")) ? line : captive_printf_alloca("httpcaptive://%s",line+strlen("http://")))); if (!uri) printf(_("Error paring URI: %s"),line); else { mod_uri_load(uri); gnome_vfs_uri_unref(uri); } free(line); } else { free(line); line=NULL; } } while (!all_modules_found && line); if (ui_line_interactive_ask(_( "You can download the best available version of needed drivers from Microsoft.\n" "They can be found in Microsoft Windows XP Service Pack 1 Checked Build.\n" "URL: http://www.microsoft.com/WindowsXP/pro/downloads/servicepacks/sp1/checkedbuild.asp\n" "Legal: In some countries you need to have valid Microsoft Windows XP license to use it.\n" "We will need to download approx 29MB of data right now (takes 2 hours on 33.6 modem)."))) microsoft_com(); if (!all_modules_found) puts(_("\nWe tried all available drivers acquiration methods - the options will start again.")); } putchar('\n'); puts(final_text(all_modules_found)); } gboolean ui_line_init(void) { acquire_module_available_notify=ui_line_module_available_notify; acquire_module_all_modules_found_notify=ui_line_all_modules_found_notify; ui_progress=ui_line_progress; ui_interactive=ui_line_interactive; /* 'captivemodid_module_best_priority_notify' left NULL. */ return TRUE; }