summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorGuillaume Cottenceau <gc@mandriva.com>2000-12-12 21:05:30 +0000
committerGuillaume Cottenceau <gc@mandriva.com>2000-12-12 21:05:30 +0000
commit2b2914cc04a93ca362e4eb3663061c3039aa4049 (patch)
tree3f8dbeae1bc114e58f3246cd76b9b0156392b720
parent7852f76ee05551c05a4f833f9a55bec15f44f85d (diff)
downloaddrakx-backup-do-not-use-2b2914cc04a93ca362e4eb3663061c3039aa4049.tar
drakx-backup-do-not-use-2b2914cc04a93ca362e4eb3663061c3039aa4049.tar.gz
drakx-backup-do-not-use-2b2914cc04a93ca362e4eb3663061c3039aa4049.tar.bz2
drakx-backup-do-not-use-2b2914cc04a93ca362e4eb3663061c3039aa4049.tar.xz
drakx-backup-do-not-use-2b2914cc04a93ca362e4eb3663061c3039aa4049.zip
- add pci probing feature
- add listing of available modules and insmod'ing on user request - make rescue-stage2 working
-rw-r--r--mdk-stage1/Makefile14
-rw-r--r--mdk-stage1/cdrom.c12
-rw-r--r--mdk-stage1/disk.c11
-rw-r--r--mdk-stage1/frontend.h3
-rw-r--r--mdk-stage1/init.c34
-rw-r--r--mdk-stage1/minilibc.c15
-rw-r--r--mdk-stage1/minilibc.h1
-rw-r--r--mdk-stage1/modules.c71
-rw-r--r--mdk-stage1/modules.h5
-rw-r--r--mdk-stage1/mount.c11
-rw-r--r--mdk-stage1/network.c2
-rw-r--r--mdk-stage1/newt-frontend.c20
-rw-r--r--mdk-stage1/pci-resource/Makefile26
-rwxr-xr-xmdk-stage1/pci-resource/update-pci-ids.pl41
-rw-r--r--mdk-stage1/probing.c102
-rw-r--r--mdk-stage1/probing.h3
-rw-r--r--mdk-stage1/stage1-data/stage1-with-sash.tar.bz2bin345007 -> 345069 bytes
-rw-r--r--mdk-stage1/stage1.c17
-rw-r--r--mdk-stage1/stdio-frontend.c63
-rw-r--r--mdk-stage1/tools.c22
20 files changed, 362 insertions, 111 deletions
diff --git a/mdk-stage1/Makefile b/mdk-stage1/Makefile
index 1ce2e3eba..1bf95ada9 100644
--- a/mdk-stage1/Makefile
+++ b/mdk-stage1/Makefile
@@ -40,15 +40,21 @@ INITSRC = minilibc.c init.c
INITOBJS = $(subst .c,.o,$(INITSRC))
- #- frontend
+ #- frontends
NEWT_FRONTEND_SRC = newt-frontend.c
NEWT_FRONTEND_LIBS = /usr/lib/libnewt.a /usr/lib/libslang.a
STDIO_FRONTEND_SRC = stdio-frontend.c
STDIO_FRONTEND_LIBS =
-FRONTEND_OBJS = $(subst .c,.o,$(STDIO_FRONTEND_SRC))
-FRONTEND_LIBS = $(STDIO_FRONTEND_LIBS)
+WSLIB_FRONTEND_SRC = wslib-frontend.c
+WSLIB_FRONTEND_LIBS = /usr/lib/libwslib.a
+
+ #- default frontend is newt
+F = NEWT
+
+FRONTEND_OBJS = $(subst .c,.o,$($(F)_FRONTEND_SRC))
+FRONTEND_LIBS = $($(F)_FRONTEND_LIBS)
#- stage1 itself (minus stage1.c)
@@ -94,7 +100,7 @@ BINS = init stage1-network
#BINS += stage1-all
#endif
-DIRS = mar insmod-busybox
+DIRS = mar insmod-busybox pci-resource
all: dirs $(BINS)
diff --git a/mdk-stage1/cdrom.c b/mdk-stage1/cdrom.c
index 7a43e8ccc..901d4ac5c 100644
--- a/mdk-stage1/cdrom.c
+++ b/mdk-stage1/cdrom.c
@@ -49,7 +49,7 @@ static enum return_type try_with_device(char *dev_name)
return results;
}
- if (access("/tmp/image/Mandrake", R_OK)) {
+ if (access("/tmp/image/Mandrake/mdkinst", R_OK)) {
enum return_type results;
umount("/tmp/image");
results = ask_yes_no("That CDROM disc does not seem to be a Linux-Mandrake Installation CDROM.\nRetry with another disc?");
@@ -78,10 +78,8 @@ enum return_type cdrom_prepare(void)
my_insmod("ide-cd");
my_insmod("sr_mod");
- my_insmod("isofs");
- medias = get_medias(CDROM, QUERY_NAME);
- medias_models = get_medias(CDROM, QUERY_MODEL);
+ get_medias(CDROM, &medias, &medias_models);
ptr = medias;
while (ptr && *ptr) {
@@ -91,7 +89,7 @@ enum return_type cdrom_prepare(void)
if (count == 0) {
error_message("No CDROM device found.");
- i = ask_scsi_insmod();
+ i = ask_insmod(SCSI_ADAPTERS);
if (i == RETURN_BACK)
return RETURN_BACK;
return cdrom_prepare();
@@ -101,7 +99,7 @@ enum return_type cdrom_prepare(void)
results = try_with_device(*medias);
if (results == RETURN_OK)
return RETURN_OK;
- i = ask_scsi_insmod();
+ i = ask_insmod(SCSI_ADAPTERS);
if (i == RETURN_BACK)
return RETURN_BACK;
return cdrom_prepare();
@@ -115,7 +113,7 @@ enum return_type cdrom_prepare(void)
results = try_with_device(choice);
if (results == RETURN_OK)
return RETURN_OK;
- i = ask_scsi_insmod();
+ i = ask_insmod(SCSI_ADAPTERS);
if (i == RETURN_BACK)
return RETURN_BACK;
return cdrom_prepare();
diff --git a/mdk-stage1/disk.c b/mdk-stage1/disk.c
index 58658fc3c..e324f0bee 100644
--- a/mdk-stage1/disk.c
+++ b/mdk-stage1/disk.c
@@ -48,18 +48,17 @@ enum return_type disk_prepare(void)
my_insmod("vfat");
my_insmod("reiserfs");
- medias = get_medias(DISK, QUERY_NAME);
+ get_medias(DISK, &medias, &medias_models);
ptr = medias;
while (ptr && *ptr) {
- log_message("found DISK %s", *ptr);
count++;
ptr++;
}
if (count == 0) {
error_message("No DISK drive found.");
- i = ask_scsi_insmod();
+ i = ask_insmod(SCSI_ADAPTERS);
if (i == RETURN_BACK)
return RETURN_BACK;
return disk_prepare();
@@ -69,14 +68,12 @@ enum return_type disk_prepare(void)
results = try_with_device(*medias);
if (results == RETURN_OK)
return RETURN_OK;
- i = ask_scsi_insmod();
+ i = ask_insmod(SCSI_ADAPTERS);
if (i == RETURN_BACK)
return RETURN_BACK;
return disk_prepare();
}
- medias_models = get_medias(DISK, QUERY_MODEL);
-
results = ask_from_list_comments("Please choose the DISK drive to use for the installation.", medias, medias_models, &choice);
if (results != RETURN_OK)
@@ -85,7 +82,7 @@ enum return_type disk_prepare(void)
results = try_with_device(choice);
if (results == RETURN_OK)
return RETURN_OK;
- i = ask_scsi_insmod();
+ i = ask_insmod(SCSI_ADAPTERS);
if (i == RETURN_BACK)
return RETURN_BACK;
return disk_prepare();
diff --git a/mdk-stage1/frontend.h b/mdk-stage1/frontend.h
index ae125fa27..9e8f1974e 100644
--- a/mdk-stage1/frontend.h
+++ b/mdk-stage1/frontend.h
@@ -24,7 +24,8 @@
void init_frontend(void);
void finish_frontend(void);
-void error_message(char *msg); /* blocking */
+void error_message(char *msg, ...); /* blocking */
+void info_message(char *msg, ...); /* blocking */
void wait_message(char *msg, ...); /* non-blocking */
void remove_wait_message(void);
diff --git a/mdk-stage1/init.c b/mdk-stage1/init.c
index 3783bc8c7..22a381e6e 100644
--- a/mdk-stage1/init.c
+++ b/mdk-stage1/init.c
@@ -54,6 +54,7 @@ char * env[] = {
*/
int testing;
+int klog_pid;
void fatal_error(char *msg)
@@ -107,12 +108,11 @@ void doklog()
return;
}
- if (fork()) {
+ if ((klog_pid = fork())) {
/* parent */
close(in);
close(out);
close(log);
- sleep(1);
return;
}
@@ -364,6 +364,17 @@ void disable_swap(void)
}
}
+int is_rescue()
+{
+ int fd, size;
+ char buf[512];
+ if ((fd = open("/proc/cmdline", O_RDONLY, 0)) == -1)
+ fatal_error("could not open /proc/cmdline");
+ size = read(fd, buf, sizeof(buf));
+ buf[size-1] = 0;
+ close(fd);
+ return (strstr(buf, "rescue") != NULL);
+}
int main(int argc, char **argv)
{
@@ -372,7 +383,7 @@ int main(int argc, char **argv)
int fd;
int abnormal_termination = 0;
int end_stage2 = 0;
-
+
/* getpid() != 1 should work, by linuxrc tends to get a larger pid */
testing = (getpid() > 50);
@@ -452,8 +463,8 @@ int main(int argc, char **argv)
printf("execing: %s\n", child_argv[0]);
execve(child_argv[0], child_argv, env);
-
- exit(0);
+ printf("error in exec of stage1 :-(\n");
+ return 0;
}
while (!end_stage2) {
@@ -468,12 +479,16 @@ int main(int argc, char **argv)
printf("-- received signal %d", WTERMSIG(wait_status));
printf("\n");
abnormal_termination = 1;
- }
- else
- printf("back to stage1-initializer control -- install exited normally\n");
+ } else if (is_rescue()) {
+ kill(klog_pid, 9);
+ printf("exiting stage1-initializer -- giving hand to rescue\n");
+ return 0;
+ }
+
+ printf("back to stage1-initializer control -- install exited normally\n");
if (testing)
- exit(0);
+ return 0;
sync(); sync();
@@ -501,6 +516,5 @@ int main(int argc, char **argv)
while (1);
}
- exit(0);
return 0;
}
diff --git a/mdk-stage1/minilibc.c b/mdk-stage1/minilibc.c
index c98d87e24..ac0ffe334 100644
--- a/mdk-stage1/minilibc.c
+++ b/mdk-stage1/minilibc.c
@@ -188,6 +188,21 @@ char * strchr(char * str, int ch)
return NULL;
}
+
+char * strstr(char *haystack, char *needle)
+{
+ char * tmp = haystack;
+ while ((tmp = strchr(tmp, needle[0])) != NULL) {
+ int i = 1;
+ while (i < strlen(tmp) && i < strlen(needle) && tmp[i] == needle[i])
+ i++;
+ if (needle[i] == '\0')
+ return tmp;
+ tmp++;
+ }
+ return NULL;
+}
+
void print_int(int fd, int i)
{
char buf[10];
diff --git a/mdk-stage1/minilibc.h b/mdk-stage1/minilibc.h
index e6743a854..8682ae3d2 100644
--- a/mdk-stage1/minilibc.h
+++ b/mdk-stage1/minilibc.h
@@ -134,6 +134,7 @@ void * memcpy(void * dst, const void * src, size_t count);
int strcmp(const char * a, const char * b);
int strncmp(const char * a, const char * b, int len);
char * strchr(char * str, int ch);
+char * strstr(char *haystack, char *needle);
char * strncpy(char * dst, const char * src, int len);
void print_str(int fd, char * string);
diff --git a/mdk-stage1/modules.c b/mdk-stage1/modules.c
index 70bdc4a9f..1b3e91d84 100644
--- a/mdk-stage1/modules.c
+++ b/mdk-stage1/modules.c
@@ -30,18 +30,12 @@
static struct module_deps_elem * modules_deps = NULL;
+static char * archive_name = "/modules/modules.mar";
+static struct mar_stream s = { 0, NULL, NULL };
-/* unarchive and insmod given module
- * WARNING: module must not contain the trailing ".o"
- */
-int insmod_archived_file(char * mod_name)
-{
- char * archive_name = "/modules/modules.mar";
- char module_name[50];
- char final_name[50] = "/tmp/";
- static struct mar_stream s = { 0, NULL, NULL };
- int i;
+static int ensure_archive_opened(void)
+{
/* don't consume too much memory */
if (s.first_element == NULL) {
if (mar_open_file(archive_name, &s) != 0) {
@@ -49,6 +43,20 @@ int insmod_archived_file(char * mod_name)
return -1;
}
}
+ return 0;
+}
+
+/* unarchive and insmod given module
+ * WARNING: module must not contain the trailing ".o"
+ */
+static int insmod_archived_file(const char * mod_name)
+{
+ char module_name[50];
+ char final_name[50] = "/tmp/";
+ int i, rc;
+
+ if (ensure_archive_opened() == -1)
+ return -1;
strncpy(module_name, mod_name, sizeof(module_name));
strncat(module_name, ".o", sizeof(module_name));
@@ -63,7 +71,11 @@ int insmod_archived_file(char * mod_name)
strncat(final_name, mod_name, sizeof(final_name));
strncat(final_name, ".o", sizeof(final_name));
- return insmod_call(final_name);
+ rc = insmod_call(final_name);
+ if (rc)
+ log_message("\tfailed.");
+ unlink(final_name); /* sucking no space left on device */
+ return rc;
}
@@ -157,7 +169,7 @@ int load_modules_dependencies(void)
}
-int insmod_with_deps(char * mod_name)
+static int insmod_with_deps(const char * mod_name)
{
struct module_deps_elem * dep;
@@ -180,7 +192,7 @@ int insmod_with_deps(char * mod_name)
}
-int my_insmod(char * mod_name)
+int my_insmod(const char * mod_name)
{
int i;
log_message("have to insmod %s", mod_name);
@@ -196,7 +208,36 @@ int my_insmod(char * mod_name)
}
-enum return_type ask_scsi_insmod(void)
+enum return_type ask_insmod(enum driver_type type)
{
- return ask_yes_no("Try to load a SCSI module");
+ char * mytype;
+ char msg[200];
+ enum return_type results;
+ char * choice;
+
+ if (type == SCSI_ADAPTERS)
+ mytype = "SCSI";
+ else if (type == NETWORK_DEVICES)
+ mytype = "NET";
+ else
+ return RETURN_ERROR;
+
+ if (ensure_archive_opened() == -1)
+ return -1;
+
+ snprintf(msg, sizeof(msg), "Which driver should I try to gain %s access?", mytype);
+
+ results = ask_from_list(msg, mar_list_contents(&s), &choice);
+
+ if (results == RETURN_OK) {
+ int rc;
+ choice[strlen(choice)-2] = '\0'; /* remove trailing .o */
+ rc = my_insmod(choice);
+ if (rc) {
+ error_message("Insmod failed.");
+ return RETURN_ERROR;
+ } else
+ return RETURN_OK;
+ } else
+ return results;
}
diff --git a/mdk-stage1/modules.h b/mdk-stage1/modules.h
index cf7eadebe..29914f5fc 100644
--- a/mdk-stage1/modules.h
+++ b/mdk-stage1/modules.h
@@ -16,11 +16,12 @@
#define _MODULES_H_
#include "stage1.h"
+#include "probing.h"
int load_modules_dependencies(void);
-int my_insmod(char * mod_name);
+int my_insmod(const char * mod_name);
-enum return_type ask_scsi_insmod(void);
+enum return_type ask_insmod(enum driver_type);
struct module_deps_elem {
diff --git a/mdk-stage1/mount.c b/mdk-stage1/mount.c
index ef0c0f676..6de11b480 100644
--- a/mdk-stage1/mount.c
+++ b/mdk-stage1/mount.c
@@ -26,6 +26,7 @@
#include <sys/stat.h>
#include <sys/types.h>
#include "log.h"
+#include "modules.h"
#include "mount.h"
@@ -130,11 +131,15 @@ int my_mount(char *dev, char *location, char *fs)
flags = MS_MGC_VAL;
- if (!strcmp(fs, "vfat"))
+ if (!strcmp(fs, "vfat")) {
+ my_insmod("vfat");
opts = "check=relaxed";
-
- if (!strcmp(fs, "iso9660"))
+ }
+
+ if (!strcmp(fs, "iso9660")) {
+ my_insmod("isofs");
flags |= MS_RDONLY;
+ }
rc = mount(dev, location, fs, flags, opts);
diff --git a/mdk-stage1/network.c b/mdk-stage1/network.c
index e6d0c6c4e..021a8d26a 100644
--- a/mdk-stage1/network.c
+++ b/mdk-stage1/network.c
@@ -32,6 +32,8 @@
enum return_type nfs_prepare(void)
{
+ pci_probing(NETWORK_DEVICES);
+
return RETURN_ERROR;
}
diff --git a/mdk-stage1/newt-frontend.c b/mdk-stage1/newt-frontend.c
index fcaeabcb6..8a057f98e 100644
--- a/mdk-stage1/newt-frontend.c
+++ b/mdk-stage1/newt-frontend.c
@@ -44,7 +44,7 @@ void init_frontend(void)
newtDrawRootText(0, 0, "Welcome to Linux-Mandrake (" VERSION ") " __DATE__ " " __TIME__);
- newtPushHelpLine(" <Tab>/<Alt-Tab> between elements, <Space>/<Enter> selects");
+ newtPushHelpLine(" <Alt-F1> for here, <Alt-F3> to see the logs, <Alt-F4> for kernel msg");
}
@@ -54,14 +54,25 @@ void finish_frontend(void)
}
-void error_message(char *msg)
+void error_message(char *msg, ...)
{
- newtWinMessage("Error", "Ok", msg);
+ va_list args;
+ va_start(args, msg);
+ va_end(args);
+ newtWinMessagev("Error", "Ok", msg, args);
+}
+
+void info_message(char *msg, ...)
+{
+ va_list args;
+ va_start(args, msg);
+ va_end(args);
+ newtWinMessagev("Notice", "Ok", msg, args);
}
void wait_message(char *msg, ...)
{
- int width = strlen(msg) + 12;
+ int width = 8;
int height = 3;
char * title = "Please wait...";
newtComponent t, f;
@@ -77,6 +88,7 @@ void wait_message(char *msg, ...)
if (buf) free(buf);
buf = malloc(size);
i = vsnprintf(buf, size, msg, args);
+ width += i;
} while (i == size);
va_end(args);
diff --git a/mdk-stage1/pci-resource/Makefile b/mdk-stage1/pci-resource/Makefile
new file mode 100644
index 000000000..ed16b6f67
--- /dev/null
+++ b/mdk-stage1/pci-resource/Makefile
@@ -0,0 +1,26 @@
+ #******************************************************************************
+ #
+ # $Id$
+ #
+ # Guillaume Cottenceau (gc@mandrakesoft.com)
+ #
+ # Copyright 2000 MandrakeSoft
+ #
+ # This software may be freely redistributed under the terms of the GNU
+ # public license.
+ #
+ # 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., 675 Mass Ave, Cambridge, MA 02139, USA.
+ #
+ # Portions from Erik Troan (ewt@redhat.com) Copyright 1996 Red Hat Software
+ #
+ #*****************************************************************************
+
+
+pci-ids.h: ../../perl-install/pci_probing/pcitable
+ make -C ../../perl-install/pci_probing
+ perl update-pci-ids.pl > $@
+
+clean:
+ rm -f pci-ids.h
diff --git a/mdk-stage1/pci-resource/update-pci-ids.pl b/mdk-stage1/pci-resource/update-pci-ids.pl
new file mode 100755
index 000000000..4aaa04b70
--- /dev/null
+++ b/mdk-stage1/pci-resource/update-pci-ids.pl
@@ -0,0 +1,41 @@
+#!/usr/bin/perl
+
+use lib "../../perl-install";
+use common qw(:common);
+use pci_probing::pcitable;
+
+print '
+#define PCI_REVISION_ID 0x08 /* Revision ID */
+
+struct pci_module_map {
+ unsigned short vendor; /* PCI vendor id */
+ unsigned short device; /* PCI device id */
+ const char *name; /* PCI human readable name */
+ const char *module; /* module to load */
+};
+
+';
+
+my %t = (scsi => 'scsi', eth => 'net');
+
+foreach (keys %t) {
+ print "
+struct pci_module_map ${_}_pci_ids[] = {
+";
+ my %l;
+ foreach (glob("../../kernel*/lib/modules/*/$t{$_}/*.o")) {
+ m|([^/]*)\.o$|;
+ $l{$1} = 1;
+ }
+ while (my ($k, $v) = each %pci_probing::pcitable::ids) {
+ $l{$v->[1]} or next;
+ printf qq|\t{0x%04x , 0x%04x , ( "%s" ), ( "%s" )} ,\n|,
+ $k / 0x10000, $k % 0x10000, $v->[0], $v->[1];
+ }
+
+print "
+};
+int ${_}_num_ids=sizeof(${_}_pci_ids)/sizeof(struct pci_module_map);
+"
+
+}
diff --git a/mdk-stage1/probing.c b/mdk-stage1/probing.c
index e252194ba..b41500314 100644
--- a/mdk-stage1/probing.c
+++ b/mdk-stage1/probing.c
@@ -38,19 +38,74 @@
#include "log.h"
#include "frontend.h"
#include "modules.h"
+#include "pci-resource/pci-ids.h"
#include "probing.h"
-static void pci_probing(enum driver_type type)
+void pci_probing(enum driver_type type)
{
- if (IS_EXPERT) {
- error_message("You should be asked if you have some SCSI.");
- } else {
-/* wait_message("Installing SCSI module...");
- my_insmod("advansys");
- remove_wait_message();
-*/ }
+ if (IS_EXPERT)
+ ask_insmod(type);
+ else {
+ /* do it automatically */
+ char * mytype;
+ FILE * f;
+ int len;
+ char buf[100];
+ struct pci_module_map * pcidb;
+
+ if (type == SCSI_ADAPTERS)
+ mytype = "SCSI";
+ else if (type == NETWORK_DEVICES)
+ mytype = "NET";
+ else
+ return;
+
+ f = fopen("/proc/bus/pci/devices", "rb");
+
+ if (!f) {
+ log_message("PCI: could not open proc file");
+ return;
+ }
+
+ switch (type) {
+ case SCSI_ADAPTERS:
+ pcidb = scsi_pci_ids;
+ len = scsi_num_ids;
+ break;
+ case NETWORK_DEVICES:
+ pcidb = eth_pci_ids;
+ len = eth_num_ids;
+ break;
+ default:
+ return;
+ }
+
+ while (1) {
+ int i, garb, vendor, device;
+
+ if (!fgets(buf,100,f)) break;
+
+ sscanf(buf, "%x %04x%04x", &garb, &vendor, &device);
+
+ for (i = 0; i < len; i++) {
+ if (pcidb[i].vendor == vendor && pcidb[i].device == device) {
+ log_message("PCI: found suggestion for %s (%s)", pcidb[i].name, pcidb[i].module);
+ if (type == SCSI_ADAPTERS) {
+ /* insmod takes time, let's use the wait message */
+ wait_message("Installing %s driver for %s", mytype, pcidb[i].name);
+ my_insmod(pcidb[i].module);
+ remove_wait_message();
+ } else if (type == NETWORK_DEVICES) {
+ /* insmod is quick, let's use the info message */
+ info_message("Found %s driver for %s", mytype, pcidb[i].name);
+ my_insmod(pcidb[i].module);
+ }
+ }
+ }
+ }
+ }
}
@@ -64,8 +119,10 @@ static void find_media(void)
int count;
int fd;
- if (medias)
- return;
+ if (!medias)
+ pci_probing(SCSI_ADAPTERS);
+ else
+ free(medias); /* that does not free the strings, by the way */
/* ----------------------------------------------- */
log_message("looking for ide media");
@@ -138,7 +195,6 @@ static void find_media(void)
/* ----------------------------------------------- */
log_message("looking for scsi media");
- pci_probing(SCSI_ADAPTERS);
fd = open("/proc/scsi/scsi", O_RDONLY);
if (fd != -1) {
@@ -268,11 +324,11 @@ static void find_media(void)
/* Finds by media */
-char ** get_medias(enum media_type media, enum media_query_type qtype)
+void get_medias(enum media_type media, char *** names, char *** models)
{
struct media_info * m;
- char * tmp[50];
- char ** answer;
+ char * tmp_names[50];
+ char * tmp_models[50];
int count;
find_media();
@@ -282,19 +338,17 @@ char ** get_medias(enum media_type media, enum media_query_type qtype)
count = 0;
while (m && m->name) {
if (m->type == media) {
- if (qtype == QUERY_NAME)
- tmp[count] = m->name;
- else
- tmp[count] = m->model;
- count++;
+ tmp_names[count] = strdup(m->name);
+ tmp_models[count++] = strdup(m->model);
}
m++;
}
- tmp[count] = NULL;
- count++;
+ tmp_names[count] = NULL;
+ tmp_models[count++] = NULL;
- answer = (char **) malloc(sizeof(char *) * count);
- memcpy(answer, tmp, sizeof(char *) * count);
+ *names = (char **) malloc(sizeof(char *) * count);
+ memcpy(*names, tmp_names, sizeof(char *) * count);
- return answer;
+ *models = (char **) malloc(sizeof(char *) * count);
+ memcpy(*models, tmp_models, sizeof(char *) * count);
}
diff --git a/mdk-stage1/probing.h b/mdk-stage1/probing.h
index 8fe43251e..4d29eabca 100644
--- a/mdk-stage1/probing.h
+++ b/mdk-stage1/probing.h
@@ -38,7 +38,8 @@ enum media_query_type { QUERY_NAME, QUERY_MODEL };
enum driver_type { SCSI_ADAPTERS, NETWORK_DEVICES };
-char ** get_medias(enum media_type media, enum media_query_type qtype);
+void pci_probing(enum driver_type type);
+void get_medias(enum media_type media, char *** names, char *** models);
#endif
diff --git a/mdk-stage1/stage1-data/stage1-with-sash.tar.bz2 b/mdk-stage1/stage1-data/stage1-with-sash.tar.bz2
index 5deeaa266..082976ffa 100644
--- a/mdk-stage1/stage1-data/stage1-with-sash.tar.bz2
+++ b/mdk-stage1/stage1-data/stage1-with-sash.tar.bz2
Binary files differ
diff --git a/mdk-stage1/stage1.c b/mdk-stage1/stage1.c
index 04cba80e7..b99435c59 100644
--- a/mdk-stage1/stage1.c
+++ b/mdk-stage1/stage1.c
@@ -56,11 +56,12 @@ void fatal_error(char *msg)
}
+
/* spawns a shell on console #2 */
void spawn_shell(void)
{
- pid_t pid;
int fd;
+ pid_t pid;
char * shell_name = "/sbin/sash";
log_message("spawning a shell..");
@@ -94,6 +95,7 @@ void spawn_shell(void)
}
}
+
enum return_type method_select_and_prepare(void)
{
char * disk_install = "Hard disk";
@@ -180,8 +182,19 @@ int main(int argc, char **argv)
fatal_error("symlink to /tmp/stage2 failed");
}
+ if (IS_RESCUE) {
+ int fd = open("/proc/sys/kernel/real-root-dev", O_RDWR);
+#ifdef __sparc__
+ write(fd, "0x1030000", sizeof("0x1030000")); /* ram3 or sparc */
+#else
+ write(fd, "0x103", sizeof("0x103")); /* ram3 */
+#endif
+ close(fd);
+ return 0;
+ }
+
if (IS_TESTING)
- return 0;
+ return 0;
argptr = stage2_args;
*argptr++ = "/usr/bin/runinstall2";
diff --git a/mdk-stage1/stdio-frontend.c b/mdk-stage1/stdio-frontend.c
index e702a79a7..bb6755176 100644
--- a/mdk-stage1/stdio-frontend.c
+++ b/mdk-stage1/stdio-frontend.c
@@ -48,37 +48,55 @@ void finish_frontend(void)
{
}
-static char get_char_response(void)
+static void get_any_response(void)
{
- unsigned char cmd1, cmd2;
-
+ unsigned char t;
fflush(stdout);
- if (read(0, &cmd1, 1) > 0) {
- fcntl(0, F_SETFL, O_NONBLOCK);
- while (read(0, &cmd2, 1) > 0);
- fcntl(0, F_SETFL, 0);
- }
+ read(0, &t, 1);
+ fcntl(0, F_SETFL, O_NONBLOCK);
+ while (read(0, &t, 1) > 0);
+ fcntl(0, F_SETFL, 0);
+}
+
+static int get_int_response(void)
+{
+ int i = 0; /* (0) tied to Cancel */
+ fflush(stdout);
+ scanf(" %d", &i);
+ return i;
+}
- return cmd1;
+static void blocking_msg(char *type, char *fmt, va_list args)
+{
+ printf(type);
+ vprintf(fmt, args);
+ get_any_response();
+ printf("\n");
}
+void error_message(char *msg, ...)
+{
+ va_list args;
+ va_start(args, msg);
+ va_end(args);
+ blocking_msg("> Error! ", msg, args);
+}
-void error_message(char *msg)
+void info_message(char *msg, ...)
{
- printf("Error! %s", msg);
- get_char_response();
- printf("\n");
+ va_list args;
+ va_start(args, msg);
+ va_end(args);
+ blocking_msg("> Info! ", msg, args);
}
void wait_message(char *msg, ...)
{
va_list args;
-
printf("Please wait: ");
va_start(args, msg);
vprintf(msg, args);
va_end(args);
-
fflush(stdout);
}
@@ -92,7 +110,6 @@ enum return_type ask_from_list_comments(char *msg, char ** elems, char ** elems_
{
char ** sav_elems = elems;
int i, j;
- unsigned char answ;
printf("> %s\n(0) Cancel\n", msg);
i = 1;
@@ -105,9 +122,7 @@ enum return_type ask_from_list_comments(char *msg, char ** elems, char ** elems_
printf("? ");
- answ = get_char_response();
-
- j = answ - '0';
+ j = get_int_response();
if (j == 0)
return RETURN_BACK;
@@ -125,7 +140,6 @@ enum return_type ask_from_list(char *msg, char ** elems, char ** choice)
{
char ** sav_elems = elems;
int i, j;
- unsigned char answ;
printf("> %s\n(0) Cancel\n", msg);
i = 1;
@@ -137,9 +151,7 @@ enum return_type ask_from_list(char *msg, char ** elems, char ** choice)
printf("? ");
- answ = get_char_response();
-
- j = answ - '0';
+ j = get_int_response();
if (j == 0)
return RETURN_BACK;
@@ -155,14 +167,11 @@ enum return_type ask_from_list(char *msg, char ** elems, char ** choice)
enum return_type ask_yes_no(char *msg)
{
- unsigned char answ;
int j;
printf("> %s\n(0) Yes\n(1) No\n(2) Back\n? ", msg);
- answ = get_char_response();
-
- j = answ - '0';
+ j = get_int_response();
if (j == 0)
return RETURN_OK;
diff --git a/mdk-stage1/tools.c b/mdk-stage1/tools.c
index 71516b354..930c1027f 100644
--- a/mdk-stage1/tools.c
+++ b/mdk-stage1/tools.c
@@ -94,10 +94,18 @@ void process_cmdline(void)
if (!strcmp(name, "cdrom")) set_param(MODE_CDROM);
if (!strcmp(name, "special_stage2")) set_param(MODE_SPECIAL_STAGE2);
}
- tmp_params[p].name = NULL;
+
+ if (IS_RESCUE) {
+ tmp_params[p].name = "special_stage2";
+ tmp_params[p].value = "rescue";
+ p++;
+ set_param(MODE_SPECIAL_STAGE2);
+ }
- params = (struct cmdline_elem *) malloc(sizeof(struct cmdline_elem) * (p+1));
- memcpy(params, tmp_params, sizeof(struct cmdline_elem) * (p+1));
+ tmp_params[p++].name = NULL;
+
+ params = (struct cmdline_elem *) malloc(sizeof(struct cmdline_elem) * p);
+ memcpy(params, tmp_params, sizeof(struct cmdline_elem) * p);
log_message("\tgot %d args", p);
}
@@ -184,7 +192,7 @@ enum return_type load_ramdisk(void)
{
char * img_name;
gzFile st2;
- char * ramdisk = "/dev/ram"; /* warning, verify that this file exists in the initrd (and actually is a ramdisk device file) */
+ char * ramdisk = "/dev/ram3"; /* warning, verify that this file exists in the initrd (and actually is a ramdisk device file) */
int ram_fd;
char buffer[4096];
char * stg2_name = get_param_valued("special_stage2");
@@ -194,6 +202,9 @@ enum return_type load_ramdisk(void)
if (!stg2_name)
stg2_name = "mdkinst";
+
+ if (IS_RESCUE)
+ stg2_name = "rescue";
img_name = malloc(strlen(begin_img) + strlen(stg2_name) + strlen(end_img) + 1);
strcpy(img_name, begin_img);
@@ -238,6 +249,9 @@ enum return_type load_ramdisk(void)
gzclose(st2);
close(ram_fd);
+ if (IS_RESCUE)
+ return RETURN_OK; /* fucksike, I lost several hours wondering why the kernel won't see the rescue if it is alreay mounted */
+
if (my_mount(ramdisk, "/tmp/stage2", "ext2"))
return RETURN_ERROR;