/* $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; static int stdin_isatty=-1; /* '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 (stdin_isatty==-1) stdin_isatty=isatty(0); if (stdin_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((const char *)type,(const char *)module_available->module->type)); g_return_if_fail(param!=NULL); if (param->do_print) print_ui_line_module_available(module_available); /**/ if (!strcmp((const char *)type,"ntoskrnl.exe")) param->ntoskrnl_exe_found=TRUE; else if (!strcmp((const char *)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(_( "Detection of language localized MS-Windows drivers is missing." " You may need to copy localized ntfs.sys and ntoskrnl.exe to /var/lib/captive/ by cp(1) command;" " contact me for their proper identification, please.\n" "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; if (!(uri=gnome_vfs_uri_new(line))) printf(_("Error paring URI: %s"),line); else { mod_uri_load_base_reporting(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. They can be found in Microsoft Windows XP Service Pack 2 Checked Build.\n" "URL: http://msdn.microsoft.com/security/productinfo/xpsp2\n" "Legal: In some countries you need to have valid Microsoft Windows XP license to use it.\n" "It is needed to download approx 61MB of data right now out of the 307MB file size. You can also download the file separately and load it in the previous screen if some problems occur.\n"))) 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; }