From: Ethan Benson Date: Tue, 26 Mar 2002 15:05:27 +0000 (+0000) Subject: Commit yaboot 1.3.4 X-Git-Tag: yaboot-1.3.13~67 X-Git-Url: http://git.ozlabs.org/?p=yaboot.git;a=commitdiff_plain;h=0ef1539b6f680ba09c88be5bb94a821fd2599931;ds=sidebyside Commit yaboot 1.3.4 Commit yaboot 1.3.4. git-archimport-id: erbenson@alaska.net--public/yaboot--devel--1.3--patch-8 --- diff --git a/ChangeLog b/ChangeLog index 5cfcdca..6279e5f 100644 --- a/ChangeLog +++ b/ChangeLog @@ -2,6 +2,23 @@ # tag: automatic-ChangeLog--erbenson@alaska.net--public/yaboot--devel--1.3 # +2002-03-26 15:05:27 GMT Ethan Benson patch-8 + + Summary: + Commit yaboot 1.3.4 + Revision: + yaboot--devel--1.3--patch-8 + + Commit yaboot 1.3.4. + + modified files: + ChangeLog Makefile changelog include/bootinfo.h + include/ctype.h include/debug.h include/file.h second/cfg.c + second/file.c second/fs.c second/fs_ext2.c second/fs_iso.c + second/iso_util.c second/partition.c second/prom.c + second/yaboot.c util/addnote.c ybin/ybin + + 2002-03-26 15:00:49 GMT Ethan Benson patch-7 Summary: diff --git a/Makefile b/Makefile index 5f6fc9a..068d3e5 100644 --- a/Makefile +++ b/Makefile @@ -2,7 +2,7 @@ include Config -VERSION = 1.3.4pre3 +VERSION = 1.3.4 # Debug mode (spam/verbose) DEBUG = 0 # make install vars diff --git a/changelog b/changelog index 477ca6c..4c14141 100644 --- a/changelog +++ b/changelog @@ -1,42 +1,30 @@ -2001-10-12 Ethan Benson +2001-10-13 Ethan Benson - * Version 1.3.4pre3 + * Version 1.3.4 * ybin: Correct a verbosity message. - * yaboot: - - Add non-fatal warning when bootstrap partition has wrong type (pmac only). - - Minor code rearrangment. - -2001-10-10 Ethan Benson - - * Version 1.3.4pre2 - - * yaboot: - - Fix netboot when using the `n' key. - - Make configuration file open error consistent with other file - open errors. - -2001-10-09 Ethan Benson - - * Version 1.3.4pre1 - * yaboot: - Add SGI XFS filesystem support. - Rewrite OpenFirmware device path parsing code. This fixes many bugs and inconsistencies in yaboot's file loading. - Fix OpenFirmware filesystem support to automatically convert path separator from / to \. CDROM authors no longer need to use - hacks like image=\\install\\powermac\\vmlinux. + kludges like image=\\install\\powermac\\vmlinux. - Fix kernel loading on some systems. - Allow for getting files from tftp server that does not run a bootpd/dhcpd. + - Fix netboot when using the `n' key. - Fix a great deal of incorrect format strings which could cause yaboot crashes. - Fix all filesystems to properly return error conditions, and report those error conditions (instead of just saying `image not found'). + - Make configuration file open error consistent with other file + open errors. - Add `help' command to yaboot which prints out basic usage information. + - Add non-fatal warning when bootstrap partition has wrong type (pmac only). + - Minor code rearrangement. - General cruft removal and code cleanup. * Makefile cleanup, make filesystems configurable. diff --git a/include/bootinfo.h b/include/bootinfo.h index b5b5a04..ffc3f04 100644 --- a/include/bootinfo.h +++ b/include/bootinfo.h @@ -24,9 +24,9 @@ #define _MACH_walnut 0x00001000 /* IBM "Walnut" 405GP eval. board */ struct bi_record { - unsigned long tag; /* tag ID */ - unsigned long size; /* size of record (in bytes) */ - unsigned long data[0]; /* data */ + unsigned long tag; /* tag ID */ + unsigned long size; /* size of record (in bytes) */ + unsigned long data[0]; /* data */ }; #define BI_FIRST 0x1010 /* first record - marker */ @@ -39,3 +39,9 @@ struct bi_record { #endif /* _PPC_BOOTINFO_H */ +/* + * Local variables: + * c-file-style: "K&R" + * c-basic-offset: 5 + * End: + */ diff --git a/include/ctype.h b/include/ctype.h index afa3639..9a219dc 100644 --- a/include/ctype.h +++ b/include/ctype.h @@ -36,19 +36,26 @@ extern unsigned char _ctype[]; static inline unsigned char __tolower(unsigned char c) { - if (isupper(c)) - c -= 'A'-'a'; - return c; + if (isupper(c)) + c -= 'A'-'a'; + return c; } static inline unsigned char __toupper(unsigned char c) { - if (islower(c)) - c -= 'a'-'A'; - return c; + if (islower(c)) + c -= 'a'-'A'; + return c; } #define tolower(c) __tolower(c) #define toupper(c) __toupper(c) #endif + +/* + * Local variables: + * c-file-style: "K&R" + * c-basic-offset: 5 + * End: + */ diff --git a/include/debug.h b/include/debug.h index 7b5665d..8683df1 100644 --- a/include/debug.h +++ b/include/debug.h @@ -43,3 +43,10 @@ #define DEBUG_OPEN #define DEBUG_SLEEP #endif + +/* + * Local variables: + * c-file-style: "K&R" + * c-basic-offset: 5 + * End: + */ diff --git a/include/file.h b/include/file.h index 8717dd3..f395dc8 100644 --- a/include/file.h +++ b/include/file.h @@ -65,16 +65,5 @@ extern int parse_device_path(char *imagepath, char *defdevice, int defpart, char *deffile, struct boot_fspec_t *result); -#if 0 -extern int validate_fspec( - struct boot_fspec_t* spec, - char* default_device, - int default_part); -extern char *parse_device_path( - char* of_device, - char** file_spec, - int* partition); -#endif - #endif diff --git a/second/cfg.c b/second/cfg.c index 58b3d60..62085e0 100644 --- a/second/cfg.c +++ b/second/cfg.c @@ -28,13 +28,13 @@ extern int strcasecmp(const char *s1, const char *s2); typedef enum { - cft_strg, cft_flag, cft_end + cft_strg, cft_flag, cft_end } CONFIG_TYPE; typedef struct { - CONFIG_TYPE type; - char *name; - void *data; + CONFIG_TYPE type; + char *name; + void *data; } CONFIG; #define MAX_TOKEN 200 @@ -43,53 +43,53 @@ typedef struct { CONFIG cf_options[] = { - {cft_strg, "device", NULL}, - {cft_strg, "partition", NULL}, - {cft_strg, "default", NULL}, - {cft_strg, "timeout", NULL}, - {cft_strg, "password", NULL}, - {cft_flag, "restricted", NULL}, - {cft_strg, "message", NULL}, - {cft_strg, "root", NULL}, - {cft_strg, "ramdisk", NULL}, - {cft_flag, "read-only", NULL}, - {cft_flag, "read-write", NULL}, - {cft_strg, "append", NULL}, - {cft_strg, "initrd", NULL}, - {cft_flag, "initrd-prompt", NULL}, - {cft_strg, "initrd-size", NULL}, - {cft_flag, "pause-after", NULL}, - {cft_strg, "pause-message", NULL}, - {cft_strg, "init-code", NULL}, - {cft_strg, "init-message", NULL}, - {cft_strg, "fgcolor", NULL}, - {cft_strg, "bgcolor", NULL}, - {cft_strg, "ptypewarning", NULL}, - {cft_end, NULL, NULL}}; + {cft_strg, "device", NULL}, + {cft_strg, "partition", NULL}, + {cft_strg, "default", NULL}, + {cft_strg, "timeout", NULL}, + {cft_strg, "password", NULL}, + {cft_flag, "restricted", NULL}, + {cft_strg, "message", NULL}, + {cft_strg, "root", NULL}, + {cft_strg, "ramdisk", NULL}, + {cft_flag, "read-only", NULL}, + {cft_flag, "read-write", NULL}, + {cft_strg, "append", NULL}, + {cft_strg, "initrd", NULL}, + {cft_flag, "initrd-prompt", NULL}, + {cft_strg, "initrd-size", NULL}, + {cft_flag, "pause-after", NULL}, + {cft_strg, "pause-message", NULL}, + {cft_strg, "init-code", NULL}, + {cft_strg, "init-message", NULL}, + {cft_strg, "fgcolor", NULL}, + {cft_strg, "bgcolor", NULL}, + {cft_strg, "ptypewarning", NULL}, + {cft_end, NULL, NULL}}; CONFIG cf_image[] = { - {cft_strg, "image", NULL}, - {cft_strg, "label", NULL}, - {cft_strg, "alias", NULL}, - {cft_flag, "single-key", NULL}, - {cft_flag, "restricted", NULL}, - {cft_strg, "device", NULL}, - {cft_strg, "partition", NULL}, - {cft_strg, "root", NULL}, - {cft_strg, "ramdisk", NULL}, - {cft_flag, "read-only", NULL}, - {cft_flag, "read-write", NULL}, - {cft_strg, "append", NULL}, - {cft_strg, "literal", NULL}, - {cft_strg, "initrd", NULL}, - {cft_flag, "initrd-prompt", NULL}, - {cft_strg, "initrd-size", NULL}, - {cft_flag, "pause-after", NULL}, - {cft_strg, "pause-message", NULL}, - {cft_flag, "novideo", NULL}, - {cft_strg, "sysmap", NULL}, - {cft_end, NULL, NULL}}; + {cft_strg, "image", NULL}, + {cft_strg, "label", NULL}, + {cft_strg, "alias", NULL}, + {cft_flag, "single-key", NULL}, + {cft_flag, "restricted", NULL}, + {cft_strg, "device", NULL}, + {cft_strg, "partition", NULL}, + {cft_strg, "root", NULL}, + {cft_strg, "ramdisk", NULL}, + {cft_flag, "read-only", NULL}, + {cft_flag, "read-write", NULL}, + {cft_strg, "append", NULL}, + {cft_strg, "literal", NULL}, + {cft_strg, "initrd", NULL}, + {cft_flag, "initrd-prompt", NULL}, + {cft_strg, "initrd-size", NULL}, + {cft_flag, "pause-after", NULL}, + {cft_strg, "pause-message", NULL}, + {cft_flag, "novideo", NULL}, + {cft_strg, "sysmap", NULL}, + {cft_end, NULL, NULL}}; static char flag_set; static char *last_token = NULL, *last_item = NULL, *last_value = NULL; @@ -102,177 +102,177 @@ static CONFIG *curr_table = cf_options; static jmp_buf env; static struct IMAGES { - CONFIG table[sizeof (cf_image) / sizeof (cf_image[0])]; - struct IMAGES *next; + CONFIG table[sizeof (cf_image) / sizeof (cf_image[0])]; + struct IMAGES *next; } *images = NULL; void cfg_error (char *msg,...) { - va_list ap; - - va_start (ap, msg); - prom_printf ("Config file error: "); - prom_vprintf (msg, ap); - va_end (ap); - prom_printf (" near line %d in file %s\n", line_num, file_name); - longjmp (env, 1); + va_list ap; + + va_start (ap, msg); + prom_printf ("Config file error: "); + prom_vprintf (msg, ap); + va_end (ap); + prom_printf (" near line %d in file %s\n", line_num, file_name); + longjmp (env, 1); } void cfg_warn (char *msg,...) { - va_list ap; + va_list ap; - va_start (ap, msg); - prom_printf ("Config file warning: "); - prom_vprintf (msg, ap); - va_end (ap); - prom_printf (" near line %d in file %s\n", line_num, file_name); + va_start (ap, msg); + prom_printf ("Config file warning: "); + prom_vprintf (msg, ap); + va_end (ap); + prom_printf (" near line %d in file %s\n", line_num, file_name); } inline int getc () { - if (currp == endp) - return EOF; - return *currp++; + if (currp == endp) + return EOF; + return *currp++; } #define next_raw next static int next (void) { - int ch; + int ch; - if (!back) - return getc (); - ch = back; - back = 0; - return ch; + if (!back) + return getc (); + ch = back; + back = 0; + return ch; } static void again (int ch) { - back = ch; + back = ch; } static char *cfg_get_token (void) { - char buf[MAX_TOKEN + 1]; - char *here; - int ch, escaped; - - if (last_token) { - here = last_token; - last_token = NULL; - return here; - } - while (1) { - while (ch = next (), ch == ' ' || ch == '\t' || ch == '\n' || ch == '\r') - if (ch == '\n' || ch == '\r') - line_num++; - if (ch == EOF || ch == (int)NULL) - return NULL; - if (ch != '#') - break; - while (ch = next_raw (), (ch != '\n' && ch != '\r')) - if (ch == EOF) - return NULL; - line_num++; - } - if (ch == '=') - return strdup ("="); - if (ch == '"') { - here = buf; - while (here - buf < MAX_TOKEN) { - if ((ch = next ()) == EOF) - cfg_error ("EOF in quoted string"); - if (ch == '"') { - *here = 0; - return strdup (buf); - } - if (ch == '\\') { - ch = next (); - switch (ch) { - case '"': - case '\\': - break; - case '\n': - case '\r': - while ((ch = next ()), ch == ' ' || ch == '\t'); - if (!ch) - continue; + char buf[MAX_TOKEN + 1]; + char *here; + int ch, escaped; + + if (last_token) { + here = last_token; + last_token = NULL; + return here; + } + while (1) { + while (ch = next (), ch == ' ' || ch == '\t' || ch == '\n' || ch == '\r') + if (ch == '\n' || ch == '\r') + line_num++; + if (ch == EOF || ch == (int)NULL) + return NULL; + if (ch != '#') + break; + while (ch = next_raw (), (ch != '\n' && ch != '\r')) + if (ch == EOF) + return NULL; + line_num++; + } + if (ch == '=') + return strdup ("="); + if (ch == '"') { + here = buf; + while (here - buf < MAX_TOKEN) { + if ((ch = next ()) == EOF) + cfg_error ("EOF in quoted string"); + if (ch == '"') { + *here = 0; + return strdup (buf); + } + if (ch == '\\') { + ch = next (); + switch (ch) { + case '"': + case '\\': + break; + case '\n': + case '\r': + while ((ch = next ()), ch == ' ' || ch == '\t'); + if (!ch) + continue; + again (ch); + ch = ' '; + break; + case 'n': + ch = '\n'; + break; + default: + cfg_error ("Bad use of \\ in quoted string"); + } + } else if ((ch == '\n') || (ch == '\r')) + cfg_error ("newline is not allowed in quoted strings"); + *here++ = ch; + } + cfg_error ("Quoted string is too long"); + return 0; /* not reached */ + } + here = buf; + escaped = 0; + while (here - buf < MAX_TOKEN) { + if (escaped) { + if (ch == EOF) + cfg_error ("\\ precedes EOF"); + if (ch == '\n') + line_num++; + else + *here++ = ch == '\t' ? ' ' : ch; + escaped = 0; + } else { + if (ch == ' ' || ch == '\t' || ch == '\n' || ch == '\r' || ch == '#' || + ch == '=' || ch == EOF) { again (ch); - ch = ' '; - break; - case 'n': - ch = '\n'; - break; - default: - cfg_error ("Bad use of \\ in quoted string"); - } - } else if ((ch == '\n') || (ch == '\r')) - cfg_error ("newline is not allowed in quoted strings"); - *here++ = ch; - } - cfg_error ("Quoted string is too long"); - return 0; /* not reached */ - } - here = buf; - escaped = 0; - while (here - buf < MAX_TOKEN) { - if (escaped) { - if (ch == EOF) - cfg_error ("\\ precedes EOF"); - if (ch == '\n') - line_num++; - else - *here++ = ch == '\t' ? ' ' : ch; - escaped = 0; - } else { - if (ch == ' ' || ch == '\t' || ch == '\n' || ch == '\r' || ch == '#' || - ch == '=' || ch == EOF) { - again (ch); - *here = 0; - return strdup (buf); - } - if (!(escaped = (ch == '\\'))) - *here++ = ch; - } - ch = next (); - } - cfg_error ("Token is too long"); - return 0; /* not reached */ + *here = 0; + return strdup (buf); + } + if (!(escaped = (ch == '\\'))) + *here++ = ch; + } + ch = next (); + } + cfg_error ("Token is too long"); + return 0; /* not reached */ } static void cfg_return_token (char *token) { - last_token = token; + last_token = token; } static int cfg_next (char **item, char **value) { - char *this; - - if (last_item) { - *item = last_item; - *value = last_value; - last_item = NULL; - return 1; - } - *value = NULL; - if (!(*item = cfg_get_token ())) - return 0; - if (!strcmp (*item, "=")) - cfg_error ("Syntax error"); - if (!(this = cfg_get_token ())) - return 1; - if (strcmp (this, "=")) { - cfg_return_token (this); - return 1; - } - if (!(*value = cfg_get_token ())) - cfg_error ("Value expected at EOF"); - if (!strcmp (*value, "=")) - cfg_error ("Syntax error after %s", *item); - return 1; + char *this; + + if (last_item) { + *item = last_item; + *value = last_value; + last_item = NULL; + return 1; + } + *value = NULL; + if (!(*item = cfg_get_token ())) + return 0; + if (!strcmp (*item, "=")) + cfg_error ("Syntax error"); + if (!(this = cfg_get_token ())) + return 1; + if (strcmp (this, "=")) { + cfg_return_token (this); + return 1; + } + if (!(*value = cfg_get_token ())) + cfg_error ("Value expected at EOF"); + if (!strcmp (*value, "=")) + cfg_error ("Syntax error after %s", *item); + return 1; } #if 0 @@ -280,175 +280,182 @@ static int cfg_next (char **item, char **value) // below, so we don't need this unless we decide to use it again. static void cfg_return (char *item, char *value) { - last_item = item; - last_value = value; + last_item = item; + last_value = value; } #endif static int cfg_set (char *item, char *value) { - CONFIG *walk; - - if (!strcasecmp (item, "image")) { - struct IMAGES **p = &images; - - while (*p) - p = &((*p)->next); - *p = (struct IMAGES *)malloc (sizeof (struct IMAGES)); - if (*p == NULL) { - prom_printf("malloc error in cfg_set\n"); - return -1; - } - (*p)->next = 0; - curr_table = ((*p)->table); - memcpy (curr_table, cf_image, sizeof (cf_image)); - } - for (walk = curr_table; walk->type != cft_end; walk++) { - if (walk->name && !strcasecmp (walk->name, item)) { - if (value && walk->type != cft_strg) - cfg_warn ("'%s' doesn't have a value", walk->name); - else if (!value && walk->type == cft_strg) - cfg_warn ("Value expected for '%s'", walk->name); - else { - if (walk->data) - cfg_warn ("Duplicate entry '%s'", walk->name); - if (walk->type == cft_flag) - walk->data = &flag_set; - else if (walk->type == cft_strg) - walk->data = value; - } - break; - } - } - if (walk->type != cft_end) - return 1; + CONFIG *walk; + + if (!strcasecmp (item, "image")) { + struct IMAGES **p = &images; + + while (*p) + p = &((*p)->next); + *p = (struct IMAGES *)malloc (sizeof (struct IMAGES)); + if (*p == NULL) { + prom_printf("malloc error in cfg_set\n"); + return -1; + } + (*p)->next = 0; + curr_table = ((*p)->table); + memcpy (curr_table, cf_image, sizeof (cf_image)); + } + for (walk = curr_table; walk->type != cft_end; walk++) { + if (walk->name && !strcasecmp (walk->name, item)) { + if (value && walk->type != cft_strg) + cfg_warn ("'%s' doesn't have a value", walk->name); + else if (!value && walk->type == cft_strg) + cfg_warn ("Value expected for '%s'", walk->name); + else { + if (walk->data) + cfg_warn ("Duplicate entry '%s'", walk->name); + if (walk->type == cft_flag) + walk->data = &flag_set; + else if (walk->type == cft_strg) + walk->data = value; + } + break; + } + } + if (walk->type != cft_end) + return 1; // cfg_return (item, value); - return 0; + return 0; } int cfg_parse (char *cfg_file, char *buff, int len) { - char *item, *value; - - file_name = cfg_file; - currp = buff; - endp = currp + len; - - if (setjmp (env)) - return -1; - while (1) { - if (!cfg_next (&item, &value)) - return 0; - if (!cfg_set (item, value)) { + char *item, *value; + + file_name = cfg_file; + currp = buff; + endp = currp + len; + + if (setjmp (env)) + return -1; + while (1) { + if (!cfg_next (&item, &value)) + return 0; + if (!cfg_set (item, value)) { #if DEBUG - prom_printf("Can't set item %s to value %s\n", item, value); + prom_printf("Can't set item %s to value %s\n", item, value); #endif - } - free (item); - } + } + free (item); + } } static char *cfg_get_strg_i (CONFIG * table, char *item) { - CONFIG *walk; + CONFIG *walk; - for (walk = table; walk->type != cft_end; walk++) - if (walk->name && !strcasecmp (walk->name, item)) - return walk->data; - return 0; + for (walk = table; walk->type != cft_end; walk++) + if (walk->name && !strcasecmp (walk->name, item)) + return walk->data; + return 0; } char *cfg_get_strg (char *image, char *item) { - struct IMAGES *p; - char *label, *alias; - char *ret; - - if (!image) - return cfg_get_strg_i (cf_options, item); - for (p = images; p; p = p->next) { - label = cfg_get_strg_i (p->table, "label"); - if (!label) { - label = cfg_get_strg_i (p->table, "image"); - alias = strrchr (label, '/'); - if (alias) - label = alias + 1; - } - alias = cfg_get_strg_i (p->table, "alias"); - if (!strcmp (label, image) || (alias && !strcmp (alias, image))) { - ret = cfg_get_strg_i (p->table, item); - if (!ret) - ret = cfg_get_strg_i (cf_options, item); - return ret; - } - } - return 0; + struct IMAGES *p; + char *label, *alias; + char *ret; + + if (!image) + return cfg_get_strg_i (cf_options, item); + for (p = images; p; p = p->next) { + label = cfg_get_strg_i (p->table, "label"); + if (!label) { + label = cfg_get_strg_i (p->table, "image"); + alias = strrchr (label, '/'); + if (alias) + label = alias + 1; + } + alias = cfg_get_strg_i (p->table, "alias"); + if (!strcmp (label, image) || (alias && !strcmp (alias, image))) { + ret = cfg_get_strg_i (p->table, item); + if (!ret) + ret = cfg_get_strg_i (cf_options, item); + return ret; + } + } + return 0; } int cfg_get_flag (char *image, char *item) { - return !!cfg_get_strg (image, item); + return !!cfg_get_strg (image, item); } static int printl_count = 0; static void printlabel (char *label, int defflag) { - int len = strlen (label); - - if (!printl_count) - prom_printf ("\n"); - prom_printf ("%s %s",defflag?"*":" ", label); - while (len++ < 25) - prom_putchar (' '); - printl_count++; - if (printl_count == 3) - printl_count = 0; + int len = strlen (label); + + if (!printl_count) + prom_printf ("\n"); + prom_printf ("%s %s",defflag?"*":" ", label); + while (len++ < 25) + prom_putchar (' '); + printl_count++; + if (printl_count == 3) + printl_count = 0; } void cfg_print_images (void) { - struct IMAGES *p; - char *label, *alias; - - char *ret = cfg_get_strg_i (cf_options, "default"); - int defflag=0; - - printl_count = 0; - for (p = images; p; p = p->next) { - label = cfg_get_strg_i (p->table, "label"); - if (!label) { - label = cfg_get_strg_i (p->table, "image"); - alias = strrchr (label, '/'); - if (alias) - label = alias + 1; - } - if(!strcmp(ret,label)) - defflag=1; - else - defflag=0; - alias = cfg_get_strg_i (p->table, "alias"); - printlabel (label, defflag); - if (alias) - printlabel (alias, 0); - } - prom_printf("\n"); + struct IMAGES *p; + char *label, *alias; + + char *ret = cfg_get_strg_i (cf_options, "default"); + int defflag=0; + + printl_count = 0; + for (p = images; p; p = p->next) { + label = cfg_get_strg_i (p->table, "label"); + if (!label) { + label = cfg_get_strg_i (p->table, "image"); + alias = strrchr (label, '/'); + if (alias) + label = alias + 1; + } + if(!strcmp(ret,label)) + defflag=1; + else + defflag=0; + alias = cfg_get_strg_i (p->table, "alias"); + printlabel (label, defflag); + if (alias) + printlabel (alias, 0); + } + prom_printf("\n"); } char *cfg_get_default (void) { - char *label; - char *ret = cfg_get_strg_i (cf_options, "default"); - - if (ret) - return ret; - if (!images) - return 0; - ret = cfg_get_strg_i (images->table, "label"); - if (!ret) { - ret = cfg_get_strg_i (images->table, "image"); - label = strrchr (ret, '/'); - if (label) - ret = label + 1; - } - return ret; + char *label; + char *ret = cfg_get_strg_i (cf_options, "default"); + + if (ret) + return ret; + if (!images) + return 0; + ret = cfg_get_strg_i (images->table, "label"); + if (!ret) { + ret = cfg_get_strg_i (images->table, "image"); + label = strrchr (ret, '/'); + if (label) + ret = label + 1; + } + return ret; } + +/* + * Local variables: + * c-file-style: "K&R" + * c-basic-offset: 5 + * End: + */ diff --git a/second/file.c b/second/file.c index 712222c..763e3e6 100644 --- a/second/file.c +++ b/second/file.c @@ -67,7 +67,7 @@ parse_device_path(char *imagepath, char *defdevice, int defpart, *ptr = 0; result->dev = strdup(ipath); } else - result->dev = strdup(ipath); + result->dev = strdup(ipath); else if ((ptr = strchr(ipath, ':')) != NULL) { *ptr = 0; result->dev = strdup(ipath); @@ -79,7 +79,7 @@ parse_device_path(char *imagepath, char *defdevice, int defpart, return 0; } - punt: +punt: if (!result->dev) result->dev = strdup(defdev); @@ -99,46 +99,46 @@ file_block_open( struct boot_file_t* file, const char* file_name, int partition) { - struct partition_t* parts; - struct partition_t* p; - struct partition_t* found; + struct partition_t* parts; + struct partition_t* p; + struct partition_t* found; - parts = partitions_lookup(dev_name); - found = NULL; + parts = partitions_lookup(dev_name); + found = NULL; #if DEBUG - if (parts) - prom_printf("partitions:\n"); - else - prom_printf("no partitions found.\n"); + if (parts) + prom_printf("partitions:\n"); + else + prom_printf("no partitions found.\n"); #endif - for (p = parts; p && !found; p=p->next) { - DEBUG_F("number: %02d, start: 0x%08lx, length: 0x%08lx\n", - p->part_number, p->part_start, p->part_size ); - if (partition == -1) { - file->fs = fs_open( file, dev_name, p, file_name ); - if (file->fs != NULL) - goto bail; - } - if ((partition >= 0) && (partition == p->part_number)) - found = p; + for (p = parts; p && !found; p=p->next) { + DEBUG_F("number: %02d, start: 0x%08lx, length: 0x%08lx\n", + p->part_number, p->part_start, p->part_size ); + if (partition == -1) { + file->fs = fs_open( file, dev_name, p, file_name ); + if (file->fs != NULL) + goto bail; + } + if ((partition >= 0) && (partition == p->part_number)) + found = p; #if DEBUG - if (found) - prom_printf(" (match)\n"); + if (found) + prom_printf(" (match)\n"); #endif - } + } - /* Note: we don't skip when found is NULL since we can, in some - * cases, let OF figure out a default partition. - */ - DEBUG_F( "Using OF defaults.. (found = %p)\n", found ); - file->fs = fs_open( file, dev_name, found, file_name ); + /* Note: we don't skip when found is NULL since we can, in some + * cases, let OF figure out a default partition. + */ + DEBUG_F( "Using OF defaults.. (found = %p)\n", found ); + file->fs = fs_open( file, dev_name, found, file_name ); bail: - if (parts) - partitions_free(parts); + if (parts) + partitions_free(parts); - return fserrorno; + return fserrorno; } static int @@ -146,8 +146,8 @@ file_net_open( struct boot_file_t* file, const char* dev_name, const char* file_name) { - file->fs = fs_of_netboot; - return fs_of_netboot->open(file, dev_name, NULL, file_name); + file->fs = fs_of_netboot; + return fs_of_netboot->open(file, dev_name, NULL, file_name); } static int @@ -155,60 +155,60 @@ default_read( struct boot_file_t* file, unsigned int size, void* buffer) { - prom_printf("WARNING ! default_read called !\n"); - return FILE_ERR_EOF; + prom_printf("WARNING ! default_read called !\n"); + return FILE_ERR_EOF; } static int default_seek( struct boot_file_t* file, unsigned int newpos) { - prom_printf("WARNING ! default_seek called !\n"); - return FILE_ERR_EOF; + prom_printf("WARNING ! default_seek called !\n"); + return FILE_ERR_EOF; } static int default_close( struct boot_file_t* file) { - prom_printf("WARNING ! default_close called !\n"); - return FILE_ERR_OK; + prom_printf("WARNING ! default_close called !\n"); + return FILE_ERR_OK; } static struct fs_t fs_default = { - "defaults", - NULL, - default_read, - default_seek, - default_close + "defaults", + NULL, + default_read, + default_seek, + default_close }; int open_file(const struct boot_fspec_t* spec, struct boot_file_t* file) { - int result; + int result; - memset(file, 0, sizeof(struct boot_file_t*)); - file->fs = &fs_default; + memset(file, 0, sizeof(struct boot_file_t*)); + file->fs = &fs_default; - DEBUG_F("dev_path = %s\nfile_name = %s\npartition = %d\n", - spec->dev, spec->file, spec->part); + DEBUG_F("dev_path = %s\nfile_name = %s\npartition = %d\n", + spec->dev, spec->file, spec->part); - result = prom_get_devtype(spec->dev); - if (result > 0) - file->device_kind = result; - else - return result; + result = prom_get_devtype(spec->dev); + if (result > 0) + file->device_kind = result; + else + return result; - switch(file->device_kind) { - case FILE_DEVICE_BLOCK: - DEBUG_F("device is a block device\n"); - return file_block_open(file, spec->dev, spec->file, spec->part); - case FILE_DEVICE_NET: - DEBUG_F("device is a network device\n"); - return file_net_open(file, spec->dev, spec->file); - } - return 0; + switch(file->device_kind) { + case FILE_DEVICE_BLOCK: + DEBUG_F("device is a block device\n"); + return file_block_open(file, spec->dev, spec->file, spec->part); + case FILE_DEVICE_NET: + DEBUG_F("device is a network device\n"); + return file_net_open(file, spec->dev, spec->file); + } + return 0; } /* diff --git a/second/fs.c b/second/fs.c index 1744f7d..e08f66c 100644 --- a/second/fs.c +++ b/second/fs.c @@ -39,15 +39,15 @@ extern const struct fs_t reiserfs_filesystem; /* Filesystem handlers yaboot knows about */ static const struct fs_t *block_filesystems[] = { - &ext2_filesystem, /* ext2 */ + &ext2_filesystem, /* ext2 */ #ifdef CONFIG_FS_XFS - &xfs_filesystem, /* XFS */ + &xfs_filesystem, /* XFS */ #endif /* CONFIG_FS_XFS */ #ifdef CONFIG_FS_REISERFS - &reiserfs_filesystem, /* reiserfs */ + &reiserfs_filesystem, /* reiserfs */ #endif /* CONFIG_FS_REISERFS */ - &of_filesystem, /* HFS/HFS+, ISO9660, UDF, UFS */ - NULL + &of_filesystem, /* HFS/HFS+, ISO9660, UDF, UFS */ + NULL }; const struct fs_t *fs_of = &of_filesystem; /* needed by ISO9660 */ @@ -64,3 +64,10 @@ fs_open(struct boot_file_t *file, const char *dev_name, return *fs; } + +/* + * Local variables: + * c-file-style: "K&R" + * c-basic-offset: 5 + * End: + */ diff --git a/second/fs_ext2.c b/second/fs_ext2.c index 66e1ba8..2f2bada 100644 --- a/second/fs_ext2.c +++ b/second/fs_ext2.c @@ -57,11 +57,11 @@ static int ext2_close( struct boot_file_t* file); struct fs_t ext2_filesystem = { - "ext2", - ext2_open, - ext2_read, - ext2_seek, - ext2_close + "ext2", + ext2_open, + ext2_read, + ext2_seek, + ext2_close }; /* IO manager structure for the ext2 library */ @@ -75,14 +75,14 @@ static errcode_t linux_flush (io_channel channel); static struct struct_io_manager struct_linux_manager = { - EXT2_ET_MAGIC_IO_MANAGER, - "linux I/O Manager", - linux_open, - linux_close, - linux_set_blksize, - linux_read_blk, - linux_write_blk, - linux_flush + EXT2_ET_MAGIC_IO_MANAGER, + "linux I/O Manager", + linux_open, + linux_close, + linux_set_blksize, + linux_read_blk, + linux_write_blk, + linux_flush }; static io_manager linux_io_manager = &struct_linux_manager; @@ -116,7 +116,7 @@ static struct ext2_inode cur_inode; void com_err (const char *a, long i, const char *fmt,...) { - prom_printf ((char *) fmt); + prom_printf ((char *) fmt); } static int @@ -125,147 +125,147 @@ ext2_open( struct boot_file_t* file, struct partition_t* part, const char* file_name) { - int result = 0; - int error = FILE_ERR_NOTFOUND; - static char buffer[1024]; - int ofopened = 0; + int result = 0; + int error = FILE_ERR_NOTFOUND; + static char buffer[1024]; + int ofopened = 0; - DEBUG_ENTER; - DEBUG_OPEN; - - if (opened) { - prom_printf("ext2_open() : fs busy\n"); - DEBUG_LEAVE(FILE_ERR_FSBUSY); - return FILE_ERR_FSBUSY; - } - if (file->device_kind != FILE_DEVICE_BLOCK) { - prom_printf("Can't open ext2 filesystem on non-block device\n"); - DEBUG_LEAVE(FILE_ERR_BADDEV); - return FILE_ERR_BADDEV; - } - - fs = NULL; + DEBUG_ENTER; + DEBUG_OPEN; + + if (opened) { + prom_printf("ext2_open() : fs busy\n"); + DEBUG_LEAVE(FILE_ERR_FSBUSY); + return FILE_ERR_FSBUSY; + } + if (file->device_kind != FILE_DEVICE_BLOCK) { + prom_printf("Can't open ext2 filesystem on non-block device\n"); + DEBUG_LEAVE(FILE_ERR_BADDEV); + return FILE_ERR_BADDEV; + } + + fs = NULL; - /* We don't care too much about the device block size since we run - * thru the deblocker. We may have to change that is we plan to be - * compatible with older versions of OF - */ - bs = 1024; - doff = 0; - if (part) - doff = (unsigned long long)(part->part_start) * part->blocksize; - cur_file = file; + /* We don't care too much about the device block size since we run + * thru the deblocker. We may have to change that is we plan to be + * compatible with older versions of OF + */ + bs = 1024; + doff = 0; + if (part) + doff = (unsigned long long)(part->part_start) * part->blocksize; + cur_file = file; - DEBUG_F("partition offset: %Lu\n", doff); + DEBUG_F("partition offset: %Lu\n", doff); - /* Open the OF device for the entire disk */ - strncpy(buffer, dev_name, 1020); - strcat(buffer, ":0"); + /* Open the OF device for the entire disk */ + strncpy(buffer, dev_name, 1020); + strcat(buffer, ":0"); - DEBUG_F("<%s>\n", buffer); + DEBUG_F("<%s>\n", buffer); - file->of_device = prom_open(buffer); + file->of_device = prom_open(buffer); - DEBUG_F("file->of_device = %p\n", file->of_device); + DEBUG_F("file->of_device = %p\n", file->of_device); - if (file->of_device == PROM_INVALID_HANDLE) { + if (file->of_device == PROM_INVALID_HANDLE) { - DEBUG_F("Can't open device %p\n", file->of_device); - DEBUG_LEAVE(FILE_IOERR); - return FILE_IOERR; - } - ofopened = 1; + DEBUG_F("Can't open device %p\n", file->of_device); + DEBUG_LEAVE(FILE_IOERR); + return FILE_IOERR; + } + ofopened = 1; - /* Open the ext2 filesystem */ - result = ext2fs_open (buffer, EXT2_FLAG_RW, 0, 0, linux_io_manager, &fs); - if (result) { - - if(result == EXT2_ET_BAD_MAGIC) - { - DEBUG_F( "ext2fs_open returned bad magic loading file %p\n", - file ); - } - else - { - DEBUG_F( "ext2fs_open error #%d while loading file %s\n", - result, file_name); - } - error = FILE_ERR_BAD_FSYS; - goto bail; - } - - /* Allocate the block buffer */ - block_buffer = malloc(fs->blocksize * 2); - if (!block_buffer) { - - DEBUG_F("ext2fs: can't alloc block buffer (%d bytes)\n", fs->blocksize * 2); - error = FILE_IOERR; - goto bail; - } + /* Open the ext2 filesystem */ + result = ext2fs_open (buffer, EXT2_FLAG_RW, 0, 0, linux_io_manager, &fs); + if (result) { + + if(result == EXT2_ET_BAD_MAGIC) + { + DEBUG_F( "ext2fs_open returned bad magic loading file %p\n", + file ); + } + else + { + DEBUG_F( "ext2fs_open error #%d while loading file %s\n", + result, file_name); + } + error = FILE_ERR_BAD_FSYS; + goto bail; + } + + /* Allocate the block buffer */ + block_buffer = malloc(fs->blocksize * 2); + if (!block_buffer) { + + DEBUG_F("ext2fs: can't alloc block buffer (%d bytes)\n", fs->blocksize * 2); + error = FILE_IOERR; + goto bail; + } - /* Lookup file by pathname */ - root = cwd = EXT2_ROOT_INO; - result = ext2fs_namei_follow(fs, root, cwd, file_name, &file->inode); - if (result) { - - DEBUG_F("ext2fs_namei error #%d while loading file %s\n", result, file_name); - if (result == EXT2_ET_SYMLINK_LOOP) - error = FILE_ERR_SYMLINK_LOOP; - else if (result == EXT2_ET_FILE_NOT_FOUND) - error = FILE_ERR_NOTFOUND; - else - error = FILE_IOERR; - goto bail; - } + /* Lookup file by pathname */ + root = cwd = EXT2_ROOT_INO; + result = ext2fs_namei_follow(fs, root, cwd, file_name, &file->inode); + if (result) { + + DEBUG_F("ext2fs_namei error #%d while loading file %s\n", result, file_name); + if (result == EXT2_ET_SYMLINK_LOOP) + error = FILE_ERR_SYMLINK_LOOP; + else if (result == EXT2_ET_FILE_NOT_FOUND) + error = FILE_ERR_NOTFOUND; + else + error = FILE_IOERR; + goto bail; + } #if 0 - result = ext2fs_follow_link(fs, root, cwd, file->inode, &file->inode); - if (result) { + result = ext2fs_follow_link(fs, root, cwd, file->inode, &file->inode); + if (result) { - DEBUG_F("ext2fs_follow_link error #%d while loading file %s\n", result, file_name); - error = FILE_ERR_NOTFOUND; - goto bail; - } + DEBUG_F("ext2fs_follow_link error #%d while loading file %s\n", result, file_name); + error = FILE_ERR_NOTFOUND; + goto bail; + } #endif #ifndef FAST_VERSION - result = ext2fs_read_inode(fs, file->inode, &cur_inode); - if (result) { - - DEBUG_F("ext2fs_read_inode error #%d while loading file %s\n", result, file_name); - if (result == EXT2_ET_FILE_TOO_BIG) - error = FILE_ERR_LENGTH; - else if (result == EXT2_ET_LLSEEK_FAILED) - error = FILE_CANT_SEEK; - else if (result == EXT2_ET_FILE_NOT_FOUND) - error = FILE_ERR_NOTFOUND; - else - error = FILE_IOERR; - goto bail; - } + result = ext2fs_read_inode(fs, file->inode, &cur_inode); + if (result) { + + DEBUG_F("ext2fs_read_inode error #%d while loading file %s\n", result, file_name); + if (result == EXT2_ET_FILE_TOO_BIG) + error = FILE_ERR_LENGTH; + else if (result == EXT2_ET_LLSEEK_FAILED) + error = FILE_CANT_SEEK; + else if (result == EXT2_ET_FILE_NOT_FOUND) + error = FILE_ERR_NOTFOUND; + else + error = FILE_IOERR; + goto bail; + } #endif /* FAST_VERSION */ - file->pos = 0; + file->pos = 0; - opened = 1; + opened = 1; bail: - if (!opened) { - if (fs) - ext2fs_close(fs); - fs = NULL; - if (ofopened) - prom_close(file->of_device); - if (block_buffer) - free(block_buffer); - block_buffer = NULL; - cur_file = NULL; + if (!opened) { + if (fs) + ext2fs_close(fs); + fs = NULL; + if (ofopened) + prom_close(file->of_device); + if (block_buffer) + free(block_buffer); + block_buffer = NULL; + cur_file = NULL; - DEBUG_LEAVE_F(error); - return error; - } + DEBUG_LEAVE_F(error); + return error; + } - DEBUG_LEAVE(FILE_ERR_OK); - return FILE_ERR_OK; + DEBUG_LEAVE(FILE_ERR_OK); + return FILE_ERR_OK; } #ifdef FAST_VERSION @@ -273,158 +273,158 @@ bail: static int read_dump_range(void) { - int count = read_range_count; - int size; + int count = read_range_count; + int size; #ifdef VERBOSE_DEBUG - DEBUG_F(" dumping range: start: 0x%x count: 0x%x\n", - read_range_count, read_range_start); + DEBUG_F(" dumping range: start: 0x%x count: 0x%x\n", + read_range_count, read_range_start); #endif - /* Check if we need to handle a special case for the last block */ - if ((count * bs) > read_max) - count--; - if (count) { - size = count * bs; - read_result = io_channel_read_blk(fs->io, read_range_start, count, read_buffer); - if (read_result) - return BLOCK_ABORT; - read_buffer += size; - read_max -= size; - read_total += size; - read_cur_file->pos += size; - read_range_count -= count; - read_range_start += count; - read_last_logical += count; - } - /* Handle remaining block */ - if (read_max && read_range_count) { - read_result = io_channel_read_blk(fs->io, read_range_start, 1, block_buffer); - if (read_result) - return BLOCK_ABORT; - memcpy(read_buffer, block_buffer, read_max); - read_cur_file->pos += read_max; - read_total += read_max; - read_max = 0; - } - read_range_count = read_range_start = 0; - - return (read_max == 0) ? BLOCK_ABORT : 0; + /* Check if we need to handle a special case for the last block */ + if ((count * bs) > read_max) + count--; + if (count) { + size = count * bs; + read_result = io_channel_read_blk(fs->io, read_range_start, count, read_buffer); + if (read_result) + return BLOCK_ABORT; + read_buffer += size; + read_max -= size; + read_total += size; + read_cur_file->pos += size; + read_range_count -= count; + read_range_start += count; + read_last_logical += count; + } + /* Handle remaining block */ + if (read_max && read_range_count) { + read_result = io_channel_read_blk(fs->io, read_range_start, 1, block_buffer); + if (read_result) + return BLOCK_ABORT; + memcpy(read_buffer, block_buffer, read_max); + read_cur_file->pos += read_max; + read_total += read_max; + read_max = 0; + } + read_range_count = read_range_start = 0; + + return (read_max == 0) ? BLOCK_ABORT : 0; } static int read_iterator(ext2_filsys fs, blk_t *blocknr, int lg_block, void *private) { #ifdef VERBOSE_DEBUG - DEBUG_F("read_it: p_bloc: 0x%x, l_bloc: 0x%x, f_pos: 0x%x, rng_pos: 0x%x ", - *blocknr, lg_block, read_cur_file->pos, read_last_logical); + DEBUG_F("read_it: p_bloc: 0x%x, l_bloc: 0x%x, f_pos: 0x%x, rng_pos: 0x%x ", + *blocknr, lg_block, read_cur_file->pos, read_last_logical); #endif - if (lg_block < 0) { + if (lg_block < 0) { #ifdef VERBOSE_DEBUG - DEBUG_F(" \n"); + DEBUG_F(" \n"); #endif - return 0; - } + return 0; + } - /* If we have not reached the start block yet, we skip */ - if (lg_block < read_cur_file->pos / bs) { + /* If we have not reached the start block yet, we skip */ + if (lg_block < read_cur_file->pos / bs) { #ifdef VERBOSE_DEBUG - DEBUG_F(" \n"); + DEBUG_F(" \n"); #endif - return 0; - } - - /* If block is contiguous to current range, just extend range, - * exit if we pass the remaining bytes count to read - */ - if (read_range_start && read_range_count < MAX_READ_RANGE - && (*blocknr == read_range_start + read_range_count) - && (lg_block == read_last_logical + read_range_count)) { + return 0; + } + + /* If block is contiguous to current range, just extend range, + * exit if we pass the remaining bytes count to read + */ + if (read_range_start && read_range_count < MAX_READ_RANGE + && (*blocknr == read_range_start + read_range_count) + && (lg_block == read_last_logical + read_range_count)) { #ifdef VERBOSE_DEBUG - DEBUG_F(" block in range\n"); + DEBUG_F(" block in range\n"); #endif - ++read_range_count; - return ((read_range_count * bs) >= read_max) ? BLOCK_ABORT : 0; - } + ++read_range_count; + return ((read_range_count * bs) >= read_max) ? BLOCK_ABORT : 0; + } - /* Range doesn't match. Dump existing range */ - if (read_range_start) { + /* Range doesn't match. Dump existing range */ + if (read_range_start) { #ifdef VERBOSE_DEBUG - DEBUG_F(" calling dump range \n"); + DEBUG_F(" calling dump range \n"); #endif - if (read_dump_range()) - return BLOCK_ABORT; - } + if (read_dump_range()) + return BLOCK_ABORT; + } - /* Here we handle holes in the file */ - if (lg_block && lg_block != read_last_logical) { - unsigned long nzero; + /* Here we handle holes in the file */ + if (lg_block && lg_block != read_last_logical) { + unsigned long nzero; #ifdef VERBOSE_DEBUG - DEBUG_F(" hole from lg_bloc 0x%x\n", read_last_logical); + DEBUG_F(" hole from lg_bloc 0x%x\n", read_last_logical); #endif - if (read_cur_file->pos % bs) { - int offset = read_cur_file->pos % bs; - int size = bs - offset; - if (size > read_max) - size = read_max; - memset(read_buffer, 0, size); - read_max -= size; - read_total += size; - read_buffer += size; - read_cur_file->pos += size; - ++read_last_logical; - if (read_max == 0) - return BLOCK_ABORT; - } - nzero = (lg_block - read_last_logical) * bs; - if (nzero) { - if (nzero > read_max) - nzero = read_max; - memset(read_buffer, 0, nzero); - read_max -= nzero; - read_total += nzero; - read_buffer += nzero; - read_cur_file->pos += nzero; - if (read_max == 0) - return BLOCK_ABORT; - } - read_last_logical = lg_block; - } + if (read_cur_file->pos % bs) { + int offset = read_cur_file->pos % bs; + int size = bs - offset; + if (size > read_max) + size = read_max; + memset(read_buffer, 0, size); + read_max -= size; + read_total += size; + read_buffer += size; + read_cur_file->pos += size; + ++read_last_logical; + if (read_max == 0) + return BLOCK_ABORT; + } + nzero = (lg_block - read_last_logical) * bs; + if (nzero) { + if (nzero > read_max) + nzero = read_max; + memset(read_buffer, 0, nzero); + read_max -= nzero; + read_total += nzero; + read_buffer += nzero; + read_cur_file->pos += nzero; + if (read_max == 0) + return BLOCK_ABORT; + } + read_last_logical = lg_block; + } /* If we are not aligned, handle that case */ - if (read_cur_file->pos % bs) { - int offset = read_cur_file->pos % bs; - int size = bs - offset; + if (read_cur_file->pos % bs) { + int offset = read_cur_file->pos % bs; + int size = bs - offset; #ifdef VERBOSE_DEBUG - DEBUG_F(" handle unaligned start\n"); + DEBUG_F(" handle unaligned start\n"); #endif - read_result = io_channel_read_blk(fs->io, *blocknr, 1, block_buffer); - if (read_result) - return BLOCK_ABORT; - if (size > read_max) - size = read_max; - memcpy(read_buffer, block_buffer + offset, size); - read_cur_file->pos += size; - read_max -= size; - read_total += size; - read_buffer += size; - read_last_logical = lg_block + 1; - return (read_max == 0) ? BLOCK_ABORT : 0; - } - - /* If there is still a physical block to add, then create a new range */ - if (*blocknr) { + read_result = io_channel_read_blk(fs->io, *blocknr, 1, block_buffer); + if (read_result) + return BLOCK_ABORT; + if (size > read_max) + size = read_max; + memcpy(read_buffer, block_buffer + offset, size); + read_cur_file->pos += size; + read_max -= size; + read_total += size; + read_buffer += size; + read_last_logical = lg_block + 1; + return (read_max == 0) ? BLOCK_ABORT : 0; + } + + /* If there is still a physical block to add, then create a new range */ + if (*blocknr) { #ifdef VERBOSE_DEBUG - DEBUG_F(" new range\n"); + DEBUG_F(" new range\n"); #endif - read_range_start = *blocknr; - read_range_count = 1; - return (bs >= read_max) ? BLOCK_ABORT : 0; - } + read_range_start = *blocknr; + read_range_count = 1; + return (bs >= read_max) ? BLOCK_ABORT : 0; + } #ifdef VERBOSE_DEBUG - DEBUG_F("\n"); + DEBUG_F("\n"); #endif - return 0; + return 0; } #endif /* FAST_VERSION */ @@ -434,89 +434,89 @@ ext2_read( struct boot_file_t* file, unsigned int size, void* buffer) { - errcode_t retval; + errcode_t retval; #ifdef FAST_VERSION - if (!opened) - return FILE_IOERR; + if (!opened) + return FILE_IOERR; - DEBUG_F("ext_read() from pos 0x%Lx, size: 0x%ux\n", file->pos, size); + DEBUG_F("ext_read() from pos 0x%Lx, size: 0x%ux\n", file->pos, size); - read_cur_file = file; - read_range_start = 0; - read_range_count = 0; - read_last_logical = file->pos / bs; - read_total = 0; - read_max = size; - read_buffer = (unsigned char*)buffer; - read_result = 0; + read_cur_file = file; + read_range_start = 0; + read_range_count = 0; + read_last_logical = file->pos / bs; + read_total = 0; + read_max = size; + read_buffer = (unsigned char*)buffer; + read_result = 0; - retval = ext2fs_block_iterate(fs, file->inode, 0, 0, read_iterator, 0); - if (retval == BLOCK_ABORT) - retval = read_result; - if (!retval && read_range_start) { + retval = ext2fs_block_iterate(fs, file->inode, 0, 0, read_iterator, 0); + if (retval == BLOCK_ABORT) + retval = read_result; + if (!retval && read_range_start) { #ifdef VERBOSE_DEBUG - DEBUG_F("on exit: range_start is 0x%x, calling dump...\n", - read_range_start); + DEBUG_F("on exit: range_start is 0x%x, calling dump...\n", + read_range_start); #endif - read_dump_range(); - retval = read_result; - } - if (retval) - prom_printf ("ext2: i/o error %ld in read\n", (long) retval); + read_dump_range(); + retval = read_result; + } + if (retval) + prom_printf ("ext2: i/o error %ld in read\n", (long) retval); - return read_total; + return read_total; #else /* FAST_VERSION */ - int status; - unsigned int read = 0; + int status; + unsigned int read = 0; - if (!opened) - return FILE_IOERR; + if (!opened) + return FILE_IOERR; - DEBUG_F("ext_read() from pos 0x%x, size: 0x%x\n", file->pos, size); + DEBUG_F("ext_read() from pos 0x%x, size: 0x%x\n", file->pos, size); - while(size) { - blk_t fblock = file->pos / bs; - blk_t pblock; - unsigned int blkorig, s, b; + while(size) { + blk_t fblock = file->pos / bs; + blk_t pblock; + unsigned int blkorig, s, b; - pblock = 0; - status = ext2fs_bmap(fs, file->inode, &cur_inode, - block_buffer, 0, fblock, &pblock); - if (status) { - - DEBUG_F("ext2fs_bmap(fblock:%d) return: %d\n", fblock, status); - return read; - } - blkorig = fblock * bs; - b = file->pos - blkorig; - s = ((bs - b) > size) ? size : (bs - b); - if (pblock) { - unsigned long long pos = - ((unsigned long long)pblock) * (unsigned long long)bs; - pos += doff; - prom_lseek(file->of_device, pos); - status = prom_read(file->of_device, block_buffer, bs); - if (status != bs) { + pblock = 0; + status = ext2fs_bmap(fs, file->inode, &cur_inode, + block_buffer, 0, fblock, &pblock); + if (status) { + + DEBUG_F("ext2fs_bmap(fblock:%d) return: %d\n", fblock, status); + return read; + } + blkorig = fblock * bs; + b = file->pos - blkorig; + s = ((bs - b) > size) ? size : (bs - b); + if (pblock) { + unsigned long long pos = + ((unsigned long long)pblock) * (unsigned long long)bs; + pos += doff; + prom_lseek(file->of_device, pos); + status = prom_read(file->of_device, block_buffer, bs); + if (status != bs) { prom_printf("ext2: io error in read, ex: %d, got: %d\n", - bs, status); + bs, status); return read; - } - } else - memset(block_buffer, 0, bs); - - memcpy(buffer, block_buffer + b, s); - read += s; - size -= s; - buffer += s; - file->pos += s; - } - return read; + } + } else + memset(block_buffer, 0, bs); + + memcpy(buffer, block_buffer + b, s); + read += s; + size -= s; + buffer += s; + file->pos += s; + } + return read; #endif /* FAST_VERSION */ } @@ -524,99 +524,106 @@ static int ext2_seek( struct boot_file_t* file, unsigned int newpos) { - if (!opened) - return FILE_CANT_SEEK; + if (!opened) + return FILE_CANT_SEEK; - file->pos = newpos; - return FILE_ERR_OK; + file->pos = newpos; + return FILE_ERR_OK; } static int ext2_close( struct boot_file_t* file) { - if (!opened) - return FILE_IOERR; + if (!opened) + return FILE_IOERR; - if (block_buffer) - free(block_buffer); - block_buffer = NULL; + if (block_buffer) + free(block_buffer); + block_buffer = NULL; - if (fs) - ext2fs_close(fs); - fs = NULL; + if (fs) + ext2fs_close(fs); + fs = NULL; - prom_close(file->of_device); - DEBUG_F("ext2_close called\n"); + prom_close(file->of_device); + DEBUG_F("ext2_close called\n"); - opened = 0; + opened = 0; - return 0; + return 0; } static errcode_t linux_open (const char *name, int flags, io_channel * channel) { - io_channel io; - - - if (!name) - return EXT2_ET_BAD_DEVICE_NAME; - io = (io_channel) malloc (sizeof (struct struct_io_channel)); - if (!io) - return EXT2_ET_BAD_DEVICE_NAME; - memset (io, 0, sizeof (struct struct_io_channel)); - io->magic = EXT2_ET_MAGIC_IO_CHANNEL; - io->manager = linux_io_manager; - io->name = (char *) malloc (strlen (name) + 1); - strcpy (io->name, name); - io->block_size = bs; - io->read_error = 0; - io->write_error = 0; - *channel = io; - - return 0; + io_channel io; + + + if (!name) + return EXT2_ET_BAD_DEVICE_NAME; + io = (io_channel) malloc (sizeof (struct struct_io_channel)); + if (!io) + return EXT2_ET_BAD_DEVICE_NAME; + memset (io, 0, sizeof (struct struct_io_channel)); + io->magic = EXT2_ET_MAGIC_IO_CHANNEL; + io->manager = linux_io_manager; + io->name = (char *) malloc (strlen (name) + 1); + strcpy (io->name, name); + io->block_size = bs; + io->read_error = 0; + io->write_error = 0; + *channel = io; + + return 0; } static errcode_t linux_close (io_channel channel) { - free(channel); - return 0; + free(channel); + return 0; } static errcode_t linux_set_blksize (io_channel channel, int blksize) { - channel->block_size = bs = blksize; - if (block_buffer) { - free(block_buffer); - block_buffer = malloc(bs * 2); - } - return 0; + channel->block_size = bs = blksize; + if (block_buffer) { + free(block_buffer); + block_buffer = malloc(bs * 2); + } + return 0; } static errcode_t linux_read_blk (io_channel channel, unsigned long block, int count, void *data) { - int size; - unsigned long long tempb; + int size; + unsigned long long tempb; - if (count == 0) - return 0; + if (count == 0) + return 0; - tempb = (((unsigned long long) block) * - ((unsigned long long)bs)) + (unsigned long long)doff; - size = (count < 0) ? -count : count * bs; - prom_lseek(cur_file->of_device, tempb); - if (prom_read(cur_file->of_device, data, size) != size) { - DEBUG_F("\nRead error on block %ld\n", block); - return EXT2_ET_SHORT_READ; - } - return 0; + tempb = (((unsigned long long) block) * + ((unsigned long long)bs)) + (unsigned long long)doff; + size = (count < 0) ? -count : count * bs; + prom_lseek(cur_file->of_device, tempb); + if (prom_read(cur_file->of_device, data, size) != size) { + DEBUG_F("\nRead error on block %ld\n", block); + return EXT2_ET_SHORT_READ; + } + return 0; } static errcode_t linux_write_blk (io_channel channel, unsigned long block, int count, const void *data) { - return 0; + return 0; } static errcode_t linux_flush (io_channel channel) { - return 0; + return 0; } + +/* + * Local variables: + * c-file-style: "K&R" + * c-basic-offset: 5 + * End: + */ diff --git a/second/fs_iso.c b/second/fs_iso.c index 50479a9..2fe3df1 100644 --- a/second/fs_iso.c +++ b/second/fs_iso.c @@ -39,11 +39,11 @@ static int iso_close( struct boot_file_t* file); struct fs_t iso_filesystem = { - "iso9660", - iso_open, - iso_read, - iso_seek, - iso_close + "iso9660", + iso_open, + iso_read, + iso_seek, + iso_close }; static int @@ -52,7 +52,7 @@ iso_open( struct boot_file_t* file, struct partition_t* part, const char* file_name) { - return FILE_ERR_BAD_FSYS; + return FILE_ERR_BAD_FSYS; } static int @@ -60,18 +60,25 @@ iso_read( struct boot_file_t* file, unsigned int size, void* buffer) { - return FILE_ERR_BAD_FSYS; + return FILE_ERR_BAD_FSYS; } static int iso_seek( struct boot_file_t* file, unsigned int newpos) { - return FILE_ERR_BAD_FSYS; + return FILE_ERR_BAD_FSYS; } static int iso_close( struct boot_file_t* file) { - return 0; + return 0; } + +/* + * Local variables: + * c-file-style: "K&R" + * c-basic-offset: 5 + * End: + */ diff --git a/second/iso_util.c b/second/iso_util.c index b8fca04..c5da532 100644 --- a/second/iso_util.c +++ b/second/iso_util.c @@ -12,75 +12,81 @@ int isonum_711 (char * p) { - return (*p & 0xff); + return (*p & 0xff); } int isonum_712 (char * p) { - int val; + int val; - val = *p; - if (val & 0x80) - val |= 0xffffff00; - return (val); + val = *p; + if (val & 0x80) + val |= 0xffffff00; + return (val); } int isonum_721 (char * p) { - return ((p[0] & 0xff) | ((p[1] & 0xff) << 8)); + return ((p[0] & 0xff) | ((p[1] & 0xff) << 8)); } int isonum_722 (char * p) { - return (((p[0] & 0xff) << 8) | (p[1] & 0xff)); + return (((p[0] & 0xff) << 8) | (p[1] & 0xff)); } int isonum_723 (char * p) { #if 0 - if (p[0] != p[3] || p[1] != p[2]) { - fprintf (stderr, "invalid format 7.2.3 number\n"); - exit (1); - } + if (p[0] != p[3] || p[1] != p[2]) { + fprintf (stderr, "invalid format 7.2.3 number\n"); + exit (1); + } #endif - return (isonum_721 (p)); + return (isonum_721 (p)); } int isonum_731 (char * p) { - return ((p[0] & 0xff) - | ((p[1] & 0xff) << 8) - | ((p[2] & 0xff) << 16) - | ((p[3] & 0xff) << 24)); + return ((p[0] & 0xff) + | ((p[1] & 0xff) << 8) + | ((p[2] & 0xff) << 16) + | ((p[3] & 0xff) << 24)); } int isonum_732 (char * p) { - return (((p[0] & 0xff) << 24) - | ((p[1] & 0xff) << 16) - | ((p[2] & 0xff) << 8) - | (p[3] & 0xff)); + return (((p[0] & 0xff) << 24) + | ((p[1] & 0xff) << 16) + | ((p[2] & 0xff) << 8) + | (p[3] & 0xff)); } int isonum_733 (char * p) { #if 0 - int i; + int i; - for (i = 0; i < 4; i++) { - if (p[i] != p[7-i]) { - fprintf (stderr, "bad format 7.3.3 number\n"); - exit (1); - } - } + for (i = 0; i < 4; i++) { + if (p[i] != p[7-i]) { + fprintf (stderr, "bad format 7.3.3 number\n"); + exit (1); + } + } #endif - return (isonum_731 (p)); + return (isonum_731 (p)); } +/* + * Local variables: + * c-file-style: "K&R" + * c-basic-offset: 8 + * End: + */ diff --git a/second/partition.c b/second/partition.c index fff169c..ea84ee2 100644 --- a/second/partition.c +++ b/second/partition.c @@ -39,12 +39,12 @@ #ifdef CHECK_FOR_VALID_MAC_PARTITION_TYPE static const char *valid_mac_partition_types[] = { - "apple_unix_svr2", - "linux", - "apple_hfs", - "apple_boot", - "apple_bootstrap", - NULL + "apple_unix_svr2", + "linux", + "apple_hfs", + "apple_boot", + "apple_bootstrap", + NULL }; #endif @@ -60,19 +60,19 @@ add_new_partition(struct partition_t** list, int part_number, const char *part_t const char *part_name, unsigned long part_start, unsigned long part_size, unsigned short part_blocksize) { - struct partition_t* part; - part = (struct partition_t*)malloc(sizeof(struct partition_t)); + struct partition_t* part; + part = (struct partition_t*)malloc(sizeof(struct partition_t)); - part->part_number = part_number; - strncpy(part->part_type, part_type, MAX_PART_NAME); - strncpy(part->part_name, part_name, MAX_PART_NAME); - part->part_start = part_start; - part->part_size = part_size; - part->blocksize = part_blocksize; + part->part_number = part_number; + strncpy(part->part_type, part_type, MAX_PART_NAME); + strncpy(part->part_name, part_name, MAX_PART_NAME); + part->part_start = part_start; + part->part_size = part_size; + part->blocksize = part_blocksize; - /* Tack this entry onto the list */ - part->next = *list; - *list = part; + /* Tack this entry onto the list */ + part->next = *list; + *list = part; } /* Note, we rely on partitions being dev-block-size aligned, @@ -83,65 +83,65 @@ static void partition_mac_lookup( const char *dev_name, prom_handle disk, unsigned int prom_blksize, struct partition_t** list ) { - int block, map_size; + int block, map_size; - /* block_buffer contains block 0 from the partitions_lookup() stage */ - struct mac_partition* part = (struct mac_partition *)block_buffer; - unsigned short ptable_block_size = - ((struct mac_driver_desc *)block_buffer)->block_size; + /* block_buffer contains block 0 from the partitions_lookup() stage */ + struct mac_partition* part = (struct mac_partition *)block_buffer; + unsigned short ptable_block_size = + ((struct mac_driver_desc *)block_buffer)->block_size; - map_size = 1; - for (block=1; block < map_size + 1; block++) - { + map_size = 1; + for (block=1; block < map_size + 1; block++) + { #ifdef CHECK_FOR_VALID_MAC_PARTITION_TYPE - int valid = 0; - const char *ptype; + int valid = 0; + const char *ptype; #endif - if (prom_readblocks(disk, block, 1, block_buffer) != 1) { - prom_printf("Can't read partition %d\n", block); - break; - } - if (part->signature != MAC_PARTITION_MAGIC) { + if (prom_readblocks(disk, block, 1, block_buffer) != 1) { + prom_printf("Can't read partition %d\n", block); + break; + } + if (part->signature != MAC_PARTITION_MAGIC) { #if 0 - prom_printf("Wrong partition %d signature\n", block); + prom_printf("Wrong partition %d signature\n", block); #endif - break; - } - if (block == 1) - map_size = part->map_count; + break; + } + if (block == 1) + map_size = part->map_count; #ifdef CHECK_FOR_VALID_MAC_PARTITION_TYPE - /* We don't bother looking at swap partitions of any type, - * and the rest are the ones we know about */ - for (ptype = valid_mac_partition_types; ptype; ptype++) - if (!strcmp (part->type, ptype)) - { - valid = 1; - break; - } + /* We don't bother looking at swap partitions of any type, + * and the rest are the ones we know about */ + for (ptype = valid_mac_partition_types; ptype; ptype++) + if (!strcmp (part->type, ptype)) + { + valid = 1; + break; + } #if DEBUG - if (!valid) - prom_printf( "MAC: Unsupported partition #%d; type=%s\n", - block, part->type ); + if (!valid) + prom_printf( "MAC: Unsupported partition #%d; type=%s\n", + block, part->type ); #endif #endif #ifdef CHECK_FOR_VALID_MAC_PARTITION_TYPE - if (valid) + if (valid) #endif - /* We use the partition block size from the partition table. - * The filesystem implmentations are responsible for mapping - * to their own fs blocksize */ - add_new_partition( - list, /* partition list */ - block, /* partition number */ - part->type, /* type */ - part->name, /* name */ - part->start_block + part->data_start, /* start */ - part->data_count, /* size */ - ptable_block_size ); - } + /* We use the partition block size from the partition table. + * The filesystem implmentations are responsible for mapping + * to their own fs blocksize */ + add_new_partition( + list, /* partition list */ + block, /* partition number */ + part->type, /* type */ + part->name, /* name */ + part->start_block + part->data_start, /* start */ + part->data_count, /* size */ + ptable_block_size ); + } } /* @@ -152,25 +152,25 @@ static void partition_fdisk_lookup( const char *dev_name, prom_handle disk, unsigned int prom_blksize, struct partition_t** list ) { - int partition; + int partition; - /* fdisk partition tables start at offset 0x1be - * from byte 0 of the boot drive. - */ - struct fdisk_partition* part = + /* fdisk partition tables start at offset 0x1be + * from byte 0 of the boot drive. + */ + struct fdisk_partition* part = (struct fdisk_partition *) (block_buffer + 0x1be); - for (partition=1; partition <= 4 ;partition++, part++) { - if (part->sys_ind == LINUX_NATIVE) { - add_new_partition( list, - partition, - "Linux", /* type */ - '\0', /* name */ - swab32(*(unsigned int *)(part->start4)), - swab32(*(unsigned int *)(part->size4)), - 512 /*blksize*/ ); - } - } + for (partition=1; partition <= 4 ;partition++, part++) { + if (part->sys_ind == LINUX_NATIVE) { + add_new_partition( list, + partition, + "Linux", /* type */ + '\0', /* name */ + swab32(*(unsigned int *)(part->start4)), + swab32(*(unsigned int *)(part->size4)), + 512 /*blksize*/ ); + } + } } /* I don't know if it's possible to handle multisession and other multitrack @@ -182,87 +182,87 @@ partition_fdisk_lookup( const char *dev_name, prom_handle disk, static int identify_iso_fs(ihandle device, unsigned int *iso_root_block) { - int block; + int block; - for (block = 16; block < 100; block++) { - struct iso_volume_descriptor * vdp; + for (block = 16; block < 100; block++) { + struct iso_volume_descriptor * vdp; - if (prom_readblocks(device, block, 1, block_buffer) != 1) { - prom_printf("Can't read volume desc block %d\n", block); - break; - } + if (prom_readblocks(device, block, 1, block_buffer) != 1) { + prom_printf("Can't read volume desc block %d\n", block); + break; + } - vdp = (struct iso_volume_descriptor *)block_buffer; + vdp = (struct iso_volume_descriptor *)block_buffer; - /* Due to the overlapping physical location of the descriptors, - * ISO CDs can match hdp->id==HS_STANDARD_ID as well. To ensure - * proper identification in this case, we first check for ISO. - */ - if (strncmp (vdp->id, ISO_STANDARD_ID, sizeof vdp->id) == 0) { - *iso_root_block = block; - return 1; - } - } + /* Due to the overlapping physical location of the descriptors, + * ISO CDs can match hdp->id==HS_STANDARD_ID as well. To ensure + * proper identification in this case, we first check for ISO. + */ + if (strncmp (vdp->id, ISO_STANDARD_ID, sizeof vdp->id) == 0) { + *iso_root_block = block; + return 1; + } + } - return 0; + return 0; } struct partition_t* partitions_lookup(const char *device) { - ihandle disk; - struct mac_driver_desc *desc = (struct mac_driver_desc *)block_buffer; - struct partition_t* list = NULL; - unsigned int prom_blksize, iso_root_block; + ihandle disk; + struct mac_driver_desc *desc = (struct mac_driver_desc *)block_buffer; + struct partition_t* list = NULL; + unsigned int prom_blksize, iso_root_block; - strncpy(block_buffer, device, 2040); - strcat(block_buffer, ":0"); + strncpy(block_buffer, device, 2040); + strcat(block_buffer, ":0"); - /* Open device */ - disk = prom_open(block_buffer); - if (disk == NULL) { - prom_printf("Can't open device <%s>\n", block_buffer); - goto bail; - } - prom_blksize = prom_getblksize(disk); - DEBUG_F("block size of device is %d\n", prom_blksize); + /* Open device */ + disk = prom_open(block_buffer); + if (disk == NULL) { + prom_printf("Can't open device <%s>\n", block_buffer); + goto bail; + } + prom_blksize = prom_getblksize(disk); + DEBUG_F("block size of device is %d\n", prom_blksize); - if (prom_blksize <= 1) - prom_blksize = 512; - if (prom_blksize > MAX_BLOCK_SIZE) { - prom_printf("block_size %d not supported !\n", prom_blksize); - goto bail; - } + if (prom_blksize <= 1) + prom_blksize = 512; + if (prom_blksize > MAX_BLOCK_SIZE) { + prom_printf("block_size %d not supported !\n", prom_blksize); + goto bail; + } - /* Read boot blocs */ - if (prom_readblocks(disk, 0, 1, block_buffer) != 1) { - prom_printf("Can't read boot blocks\n"); - goto bail; - } - if (desc->signature == MAC_DRIVER_MAGIC) { - /* pdisk partition format */ - partition_mac_lookup(device, disk, prom_blksize, &list); - } else if ((block_buffer[510] == 0x55) && (block_buffer[511] == 0xaa)) { - /* fdisk partition format */ - partition_fdisk_lookup(device, disk, prom_blksize, &list); - } else if (prom_blksize == 2048 && identify_iso_fs(disk, &iso_root_block)) { - add_new_partition(&list, - 0, - '\0', - '\0', - iso_root_block, - 0, - prom_blksize); - prom_printf("ISO9660 disk\n"); - } else { - prom_printf("No supported partition table detected\n"); - goto bail; - } + /* Read boot blocs */ + if (prom_readblocks(disk, 0, 1, block_buffer) != 1) { + prom_printf("Can't read boot blocks\n"); + goto bail; + } + if (desc->signature == MAC_DRIVER_MAGIC) { + /* pdisk partition format */ + partition_mac_lookup(device, disk, prom_blksize, &list); + } else if ((block_buffer[510] == 0x55) && (block_buffer[511] == 0xaa)) { + /* fdisk partition format */ + partition_fdisk_lookup(device, disk, prom_blksize, &list); + } else if (prom_blksize == 2048 && identify_iso_fs(disk, &iso_root_block)) { + add_new_partition(&list, + 0, + '\0', + '\0', + iso_root_block, + 0, + prom_blksize); + prom_printf("ISO9660 disk\n"); + } else { + prom_printf("No supported partition table detected\n"); + goto bail; + } bail: - prom_close(disk); + prom_close(disk); - return list; + return list; } char * @@ -299,25 +299,25 @@ get_part_type(char *device, int partition) void partitions_free(struct partition_t* list) { - struct partition_t* next; + struct partition_t* next; - while(list) { - next = list->next; - free(list); - list = next; - } + while(list) { + next = list->next; + free(list); + list = next; + } } unsigned long swab32(unsigned long value) { - __u32 result; + __u32 result; - __asm__("rlwimi %0,%1,24,16,23\n\t" - "rlwimi %0,%1,8,8,15\n\t" - "rlwimi %0,%1,24,0,7" - : "=r" (result) - : "r" (value), "0" (value >> 24)); - return result; + __asm__("rlwimi %0,%1,24,16,23\n\t" + "rlwimi %0,%1,8,8,15\n\t" + "rlwimi %0,%1,24,0,7" + : "=r" (result) + : "r" (value), "0" (value >> 24)); + return result; } diff --git a/second/prom.c b/second/prom.c index 33dfcda..209dd87 100644 --- a/second/prom.c +++ b/second/prom.c @@ -30,6 +30,7 @@ #include "ctype.h" #include "asm/processor.h" #include "errors.h" +#include "debug.h" #define READ_BLOCKS_USE_READ 1 @@ -43,125 +44,125 @@ static ihandle prom_mem, prom_mmu; static ihandle prom_chosen, prom_options; struct prom_args { - const char *service; - int nargs; - int nret; - void *args[10]; + const char *service; + int nargs; + int nret; + void *args[10]; }; void * call_prom (const char *service, int nargs, int nret, ...) { - va_list list; - int i; - struct prom_args prom_args; + va_list list; + int i; + struct prom_args prom_args; - prom_args.service = service; - prom_args.nargs = nargs; - prom_args.nret = nret; - va_start (list, nret); - for (i = 0; i < nargs; ++i) - prom_args.args[i] = va_arg(list, void *); - va_end(list); - for (i = 0; i < nret; ++i) - prom_args.args[i + nargs] = 0; - prom (&prom_args); - if (nret > 0) - return prom_args.args[nargs]; - else - return 0; + prom_args.service = service; + prom_args.nargs = nargs; + prom_args.nret = nret; + va_start (list, nret); + for (i = 0; i < nargs; ++i) + prom_args.args[i] = va_arg(list, void *); + va_end(list); + for (i = 0; i < nret; ++i) + prom_args.args[i + nargs] = 0; + prom (&prom_args); + if (nret > 0) + return prom_args.args[nargs]; + else + return 0; } void * call_prom_return (const char *service, int nargs, int nret, ...) { - va_list list; - int i; - void* result; - struct prom_args prom_args; + va_list list; + int i; + void* result; + struct prom_args prom_args; - prom_args.service = service; - prom_args.nargs = nargs; - prom_args.nret = nret; - va_start (list, nret); - for (i = 0; i < nargs; ++i) - prom_args.args[i] = va_arg(list, void *); - for (i = 0; i < nret; ++i) - prom_args.args[i + nargs] = 0; - if (prom (&prom_args) != 0) - return PROM_INVALID_HANDLE; - if (nret > 0) { - result = prom_args.args[nargs]; - for (i=1; i 0) { + result = prom_args.args[nargs]; + for (i=1; i> 32), (unsigned int)(pos & 0xffffffffUL)); - return status == 0 || status == 1; + int status = (int)call_prom ("seek", 3, 1, file, + (unsigned int)(pos >> 32), (unsigned int)(pos & 0xffffffffUL)); + return status == 0 || status == 1; } int prom_loadmethod (prom_handle device, void* addr) { - return (int)call_method_1 ("load", device, 1, addr); + return (int)call_method_1 ("load", device, 1, addr); } int prom_getblksize (prom_handle file) { - return (int)call_method_1 ("block-size", file, 0); + return (int)call_method_1 ("block-size", file, 0); } int prom_readblocks (prom_handle dev, int blockNum, int blockCount, void *buffer) { #if READ_BLOCKS_USE_READ - int status; - unsigned int blksize; + int status; + unsigned int blksize; - blksize = prom_getblksize(dev); - if (blksize <= 1) - blksize = 512; - status = prom_seek(dev, blockNum * blksize); - if (status != 1) { - return 0; - prom_printf("Can't seek to 0x%x\n", blockNum * blksize); - } + blksize = prom_getblksize(dev); + if (blksize <= 1) + blksize = 512; + status = prom_seek(dev, blockNum * blksize); + if (status != 1) { + return 0; + prom_printf("Can't seek to 0x%x\n", blockNum * blksize); + } - status = prom_read(dev, buffer, blockCount * blksize); + status = prom_read(dev, buffer, blockCount * blksize); // prom_printf("prom_readblocks, bl: %d, cnt: %d, status: %d\n", // blockNum, blockCount, status); - return status == (blockCount * blksize); + return status == (blockCount * blksize); #else - int result; - int retries = 10; + int result; + int retries = 10; - if (blockCount == 0) - return blockCount; - while(--retries) { - result = call_method_1 ("read-blocks", dev, 3, buffer, blockNum, blockCount); - if (result != 0) - break; - call_prom("interpret", 1, 1, " 10 ms"); - } + if (blockCount == 0) + return blockCount; + while(--retries) { + result = call_method_1 ("read-blocks", dev, 3, buffer, blockNum, blockCount); + if (result != 0) + break; + call_prom("interpret", 1, 1, " 10 ms"); + } - return result; + return result; #endif } int prom_getchar () { - char c[4]; - int a; + char c[4]; + int a; - while ((a = (int)call_prom ("read", 3, 1, prom_stdin, c, 4)) == 0) - ; - if (a == -1) - prom_abort ("EOF on console\n"); - if (a == 3 && c[0] == '\e' && c[1] == '[') - return 0x100 | c[2]; - return c[0]; + while ((a = (int)call_prom ("read", 3, 1, prom_stdin, c, 4)) == 0) + ; + if (a == -1) + prom_abort ("EOF on console\n"); + if (a == 3 && c[0] == '\e' && c[1] == '[') + return 0x100 | c[2]; + return c[0]; } int prom_nbgetchar() { - char ch; + char ch; - return (int) call_prom("read", 3, 1, prom_stdin, &ch, 1) > 0? ch: -1; + return (int) call_prom("read", 3, 1, prom_stdin, &ch, 1) > 0? ch: -1; } void prom_putchar (char c) { - if (c == '\n') - call_prom ("write", 3, 1, prom_stdout, "\r\n", 2); - else - call_prom ("write", 3, 1, prom_stdout, &c, 1); + if (c == '\n') + call_prom ("write", 3, 1, prom_stdout, "\r\n", 2); + else + call_prom ("write", 3, 1, prom_stdout, &c, 1); } void prom_puts (prom_handle file, char *s) { - const char *p, *q; - - for (p = s; *p != 0; p = q) - { - for (q = p; *q != 0 && *q != '\n'; ++q) - ; - if (q > p) - call_prom ("write", 3, 1, file, p, q - p); - if (*q != 0) - { - ++q; - call_prom ("write", 3, 1, file, "\r\n", 2); - } - } + const char *p, *q; + + for (p = s; *p != 0; p = q) + { + for (q = p; *q != 0 && *q != '\n'; ++q) + ; + if (q > p) + call_prom ("write", 3, 1, file, p, q - p); + if (*q != 0) + { + ++q; + call_prom ("write", 3, 1, file, "\r\n", 2); + } + } } void prom_vfprintf (prom_handle file, char *fmt, va_list ap) { - static char printf_buf[1536]; - vsprintf (printf_buf, fmt, ap); - prom_puts (file, printf_buf); + static char printf_buf[1536]; + vsprintf (printf_buf, fmt, ap); + prom_puts (file, printf_buf); } void prom_vprintf (char *fmt, va_list ap) { - static char printf_buf[1536]; - vsprintf (printf_buf, fmt, ap); - prom_puts (prom_stdout, printf_buf); + static char printf_buf[1536]; + vsprintf (printf_buf, fmt, ap); + prom_puts (prom_stdout, printf_buf); } void prom_fprintf (prom_handle file, char *fmt, ...) { - va_list ap; - va_start (ap, fmt); - prom_vfprintf (file, fmt, ap); - va_end (ap); + va_list ap; + va_start (ap, fmt); + prom_vfprintf (file, fmt, ap); + va_end (ap); } void prom_printf (char *fmt, ...) { - va_list ap; - va_start (ap, fmt); - prom_vfprintf (prom_stdout, fmt, ap); - va_end (ap); + va_list ap; + va_start (ap, fmt); + prom_vfprintf (prom_stdout, fmt, ap); + va_end (ap); } void @@ -480,59 +479,59 @@ prom_perror (int error, char *filename) void prom_readline (char *prompt, char *buf, int len) { - int i = 0; - int c; - - if (prompt) - prom_puts (prom_stdout, prompt); - - while (i < len-1 && (c = prom_getchar ()) != '\r') - { - if (c >= 0x100) - continue; - if (c == 8) - { - if (i > 0) - { - prom_puts (prom_stdout, "\b \b"); - i--; - } + int i = 0; + int c; + + if (prompt) + prom_puts (prom_stdout, prompt); + + while (i < len-1 && (c = prom_getchar ()) != '\r') + { + if (c >= 0x100) + continue; + if (c == 8) + { + if (i > 0) + { + prom_puts (prom_stdout, "\b \b"); + i--; + } + else + prom_putchar ('\a'); + } + else if (isprint (c)) + { + prom_putchar (c); + buf[i++] = c; + } else - prom_putchar ('\a'); - } - else if (isprint (c)) - { - prom_putchar (c); - buf[i++] = c; - } - else - prom_putchar ('\a'); - } - prom_putchar ('\n'); - buf[i] = 0; + prom_putchar ('\a'); + } + prom_putchar ('\n'); + buf[i] = 0; } #ifdef CONFIG_SET_COLORMAP int prom_set_color(prom_handle device, int color, int r, int g, int b) { - return (int)call_prom( "call-method", 6, 1, "color!", device, color, b, g, r ); + return (int)call_prom( "call-method", 6, 1, "color!", device, color, b, g, r ); } #endif /* CONFIG_SET_COLORMAP */ void prom_exit () { - call_prom ("exit", 0, 0); + call_prom ("exit", 0, 0); } void prom_abort (char *fmt, ...) { - va_list ap; - va_start (ap, fmt); - prom_vfprintf (prom_stdout, fmt, ap); - va_end (ap); - prom_exit (); + va_list ap; + va_start (ap, fmt); + prom_vfprintf (prom_stdout, fmt, ap); + va_end (ap); + prom_exit (); } void @@ -546,18 +545,18 @@ prom_sleep (int seconds) void * prom_claim (void *virt, unsigned int size, unsigned int align) { - return call_prom ("claim", 3, 1, virt, size, align); + return call_prom ("claim", 3, 1, virt, size, align); } void prom_release(void *virt, unsigned int size) { // call_prom ("release", 2, 1, virt, size); - /* release in not enough, it needs also an unmap call. This bit of forth - * code inspired from Darwin's bootloader but could be replaced by direct - * calls to the MMU package if needed - */ - call_prom ("interpret", 3, 1, + /* release in not enough, it needs also an unmap call. This bit of forth + * code inspired from Darwin's bootloader but could be replaced by direct + * calls to the MMU package if needed + */ + call_prom ("interpret", 3, 1, #if DEBUG ".\" ReleaseMem:\" 2dup . . cr " #endif @@ -568,62 +567,68 @@ prom_release(void *virt, unsigned int size) "2dup \" release\" ^mmu " // Then free the virtual pages "\" release\" ^mem " // Then free the physical pages ,size, virt - ); + ); } void prom_map (void *phys, void *virt, int size) { - unsigned long msr = mfmsr(); + unsigned long msr = mfmsr(); - /* Only create a mapping if we're running with relocation enabled. */ - if ( (msr & MSR_IR) && (msr & MSR_DR) ) - call_method_1 ("map", prom_mmu, 4, -1, size, virt, phys); + /* Only create a mapping if we're running with relocation enabled. */ + if ( (msr & MSR_IR) && (msr & MSR_DR) ) + call_method_1 ("map", prom_mmu, 4, -1, size, virt, phys); } void prom_unmap (void *phys, void *virt, int size) { - unsigned long msr = mfmsr(); + unsigned long msr = mfmsr(); - /* Only unmap if we're running with relocation enabled. */ - if ( (msr & MSR_IR) && (msr & MSR_DR) ) - call_method_1 ("map", prom_mmu, 4, -1, size, virt, phys); + /* Only unmap if we're running with relocation enabled. */ + if ( (msr & MSR_IR) && (msr & MSR_DR) ) + call_method_1 ("map", prom_mmu, 4, -1, size, virt, phys); } char * prom_getargs () { - static char args[256]; - int l; + static char args[256]; + int l; - l = prom_get_chosen ("bootargs", args, 255); - args[l] = '\0'; - return args; + l = prom_get_chosen ("bootargs", args, 255); + args[l] = '\0'; + return args; } void prom_setargs (char *args) { - int l = strlen (args)+1; - if ((int)call_prom ("setprop", 4, 1, prom_chosen, "bootargs", args, l) != l) - prom_printf ("can't set args\n"); + int l = strlen (args)+1; + if ((int)call_prom ("setprop", 4, 1, prom_chosen, "bootargs", args, l) != l) + prom_printf ("can't set args\n"); } int prom_interpret (char *forth) { - return (int)call_prom("interpret", 1, 1, forth); + return (int)call_prom("interpret", 1, 1, forth); } int prom_getms(void) { - return (int) call_prom("milliseconds", 0, 1); + return (int) call_prom("milliseconds", 0, 1); } void prom_pause(void) { - call_prom("enter", 0, 0); + call_prom("enter", 0, 0); } +/* + * Local variables: + * c-file-style: "K&R" + * c-basic-offset: 5 + * End: + */ diff --git a/second/yaboot.c b/second/yaboot.c index 23a6322..727c725 100644 --- a/second/yaboot.c +++ b/second/yaboot.c @@ -68,16 +68,16 @@ #define KERNEL_LINK_ADDR_PPC64 0xC000000000000000ULL typedef struct { - union { - Elf32_Ehdr elf32hdr; - Elf64_Ehdr elf64hdr; - } elf; - void* base; - unsigned long memsize; - unsigned long filesize; - unsigned long offset; - unsigned long load_loc; - unsigned long entry; + union { + Elf32_Ehdr elf32hdr; + Elf64_Ehdr elf64hdr; + } elf; + void* base; + unsigned long memsize; + unsigned long filesize; + unsigned long offset; + unsigned long load_loc; + unsigned long entry; } loadinfo_t; typedef void (*kernel_entry_t)( void *, @@ -113,27 +113,27 @@ int _machine = _MACH_Pmac; /* Color values for text ui */ static struct ansi_color_t { - char* name; - int index; - int value; + char* name; + int index; + int value; } ansi_color_table[] = { - { "black", 2, 30 }, - { "blue", 0, 31 }, - { "green", 0, 32 }, - { "cyan", 0, 33 }, - { "red", 0, 34 }, - { "purple", 0, 35 }, - { "brown", 0, 36 }, - { "light-gray", 0, 37 }, - { "dark-gray", 1, 30 }, - { "light-blue", 1, 31 }, - { "light-green", 1, 32 }, - { "light-cyan", 1, 33 }, - { "light-red", 1, 34 }, - { "light-purple", 1, 35 }, - { "yellow", 1, 36 }, - { "white", 1, 37 }, - { NULL, 0, 0 }, + { "black", 2, 30 }, + { "blue", 0, 31 }, + { "green", 0, 32 }, + { "cyan", 0, 33 }, + { "red", 0, 34 }, + { "purple", 0, 35 }, + { "brown", 0, 36 }, + { "light-gray", 0, 37 }, + { "dark-gray", 1, 30 }, + { "light-blue", 1, 31 }, + { "light-green", 1, 32 }, + { "light-cyan", 1, 33 }, + { "light-red", 1, 34 }, + { "light-purple", 1, 35 }, + { "yellow", 1, 36 }, + { "white", 1, 37 }, + { NULL, 0, 0 }, }; /* Default colors for text ui */ @@ -166,75 +166,75 @@ static struct first_info *quik_fip = NULL; int yaboot_start (unsigned long r3, unsigned long r4, unsigned long r5) { - int result; - void* malloc_base = NULL; - prom_handle root; + int result; + void* malloc_base = NULL; + prom_handle root; - /* OF seems to do it, but I'm not very confident */ - memset(&__bss_start, 0, &_end - &__bss_start); + /* OF seems to do it, but I'm not very confident */ + memset(&__bss_start, 0, &_end - &__bss_start); - /* Check for quik first stage bootloader (but I don't think we are - * compatible with it anyway, I'll look into backporting to older OF - * versions later - */ - if (r5 == 0xdeadbeef) { - r5 = r3; - quik_fip = (struct first_info *)r4; - } - - /* Initialize OF interface */ - prom_init ((prom_entry) r5); + /* Check for quik first stage bootloader (but I don't think we are + * compatible with it anyway, I'll look into backporting to older OF + * versions later + */ + if (r5 == 0xdeadbeef) { + r5 = r3; + quik_fip = (struct first_info *)r4; + } + + /* Initialize OF interface */ + prom_init ((prom_entry) r5); - /* Allocate some memory for malloc'ator */ - malloc_base = prom_claim((void *)MALLOCADDR, MALLOCSIZE, 0); - if (malloc_base == (void *)-1) { - prom_printf("Can't claim malloc buffer (%d bytes at 0x%08x)\n", - MALLOCSIZE, MALLOCADDR); - return -1; - } - malloc_init(malloc_base, MALLOCSIZE); - DEBUG_F("Malloc buffer allocated at %p (%d bytes)\n", - malloc_base, MALLOCSIZE); + /* Allocate some memory for malloc'ator */ + malloc_base = prom_claim((void *)MALLOCADDR, MALLOCSIZE, 0); + if (malloc_base == (void *)-1) { + prom_printf("Can't claim malloc buffer (%d bytes at 0x%08x)\n", + MALLOCSIZE, MALLOCADDR); + return -1; + } + malloc_init(malloc_base, MALLOCSIZE); + DEBUG_F("Malloc buffer allocated at %p (%d bytes)\n", + malloc_base, MALLOCSIZE); - /* A few useless DEBUG_F's */ - DEBUG_F("reloc_offset : %ld (should be 0)\n", reloc_offset()); - DEBUG_F("test_bss : %d (should be 0)\n", test_bss); - DEBUG_F("test_data : %d (should be 0)\n", test_data); - DEBUG_F("&test_data : %p\n", &test_data); - DEBUG_F("&test_bss : %p\n", &test_bss); - DEBUG_F("linked at : 0x%08x\n", TEXTADDR); - - /* ask the OF info if we're a chrp or pmac */ - /* we need to set _machine before calling finish_device_tree */ - root = prom_finddevice("/"); - if (root != 0) { - static char model[256]; - if (prom_getprop(root, "device_type", model, 256 ) > 0 && - !strncmp("chrp", model, 4)) - _machine = _MACH_chrp; - else { - if (prom_getprop(root, "model", model, 256 ) > 0 && - !strncmp(model, "IBM", 3)) - _machine = _MACH_chrp; - } - } + /* A few useless DEBUG_F's */ + DEBUG_F("reloc_offset : %ld (should be 0)\n", reloc_offset()); + DEBUG_F("test_bss : %d (should be 0)\n", test_bss); + DEBUG_F("test_data : %d (should be 0)\n", test_data); + DEBUG_F("&test_data : %p\n", &test_data); + DEBUG_F("&test_bss : %p\n", &test_bss); + DEBUG_F("linked at : 0x%08x\n", TEXTADDR); + + /* ask the OF info if we're a chrp or pmac */ + /* we need to set _machine before calling finish_device_tree */ + root = prom_finddevice("/"); + if (root != 0) { + static char model[256]; + if (prom_getprop(root, "device_type", model, 256 ) > 0 && + !strncmp("chrp", model, 4)) + _machine = _MACH_chrp; + else { + if (prom_getprop(root, "model", model, 256 ) > 0 && + !strncmp(model, "IBM", 3)) + _machine = _MACH_chrp; + } + } - DEBUG_F("Running on _machine = %d\n", _machine); - DEBUG_SLEEP; + DEBUG_F("Running on _machine = %d\n", _machine); + DEBUG_SLEEP; - /* Call out main */ - result = yaboot_main(); + /* Call out main */ + result = yaboot_main(); - /* Get rid of malloc pool */ - malloc_dispose(); - prom_release(malloc_base, MALLOCSIZE); - DEBUG_F("Malloc buffer released. Exiting with code %d\n", - result); + /* Get rid of malloc pool */ + malloc_dispose(); + prom_release(malloc_base, MALLOCSIZE); + DEBUG_F("Malloc buffer released. Exiting with code %d\n", + result); - /* Return to OF */ - prom_exit(); + /* Return to OF */ + prom_exit(); - return result; + return result; } @@ -245,13 +245,13 @@ yaboot_start (unsigned long r3, unsigned long r4, unsigned long r5) static int check_color_text_ui(char *color) { - int i = 0; - while(ansi_color_table[i].name) { - if (!strcmp(color, ansi_color_table[i].name)) - return i; - i++; - } - return -1; + int i = 0; + while(ansi_color_table[i].name) { + if (!strcmp(color, ansi_color_table[i].name)) + return i; + i++; + } + return -1; } #endif /* CONFIG_COLOR_TEXT */ @@ -262,465 +262,467 @@ check_color_text_ui(char *color) static int load_config_file(char *device, char* path, int partition) { - char *conf_file = NULL, *p; - struct boot_file_t file; - int sz, opened = 0, result = 0; - char conf_path[512]; - struct boot_fspec_t fspec; - - /* Allocate a buffer for the config file */ - conf_file = malloc(CONFIG_FILE_MAX); - if (!conf_file) { - prom_printf("Can't alloc config file buffer\n"); - goto bail; - } - - /* Build the path to the file */ - if (path) - strcpy(conf_path, path); - else if ( _machine == _MACH_chrp ) - strcpy(conf_path, "/etc/"); - else - conf_path[0] = 0; - strcat(conf_path, CONFIG_FILE_NAME); - - /* Open it */ - fspec.dev = device; - fspec.file = conf_path; - fspec.part = partition; - result = open_file(&fspec, &file); - if (result != FILE_ERR_OK) { - prom_printf("%s:%d,", fspec.dev, fspec.part); - prom_perror(result, fspec.file); - prom_printf("Can't open config file\n"); - goto bail; - } - opened = 1; - - /* Read it */ - sz = file.fs->read(&file, CONFIG_FILE_MAX, conf_file); - if (sz <= 0) { - prom_printf("Error, can't read config file\n"); - goto bail; - } - prom_printf("Config file read, %d bytes\n", sz); - - /* Close the file */ - if (opened) - file.fs->close(&file); - opened = 0; - - /* Call the parsing code in cfg.c */ - if (cfg_parse(conf_path, conf_file, sz) < 0) { - prom_printf ("Syntax error or read error config\n"); - goto bail; - } - - DEBUG_F("Config file successfully parsed, %d bytes\n", sz); - - /* Now, we do the initialisations stored in the config file */ - p = cfg_get_strg(0, "init-code"); - if (p) - prom_interpret(p); - - password = cfg_get_strg(0, "password"); + char *conf_file = NULL, *p; + struct boot_file_t file; + int sz, opened = 0, result = 0; + char conf_path[512]; + struct boot_fspec_t fspec; + + /* Allocate a buffer for the config file */ + conf_file = malloc(CONFIG_FILE_MAX); + if (!conf_file) { + prom_printf("Can't alloc config file buffer\n"); + goto bail; + } + + /* Build the path to the file */ + if (path) + strcpy(conf_path, path); + else if ( _machine == _MACH_chrp ) + strcpy(conf_path, "/etc/"); + else + conf_path[0] = 0; + strcat(conf_path, CONFIG_FILE_NAME); + + /* Open it */ + fspec.dev = device; + fspec.file = conf_path; + fspec.part = partition; + result = open_file(&fspec, &file); + if (result != FILE_ERR_OK) { + prom_printf("%s:%d,", fspec.dev, fspec.part); + prom_perror(result, fspec.file); + prom_printf("Can't open config file\n"); + goto bail; + } + opened = 1; + + /* Read it */ + sz = file.fs->read(&file, CONFIG_FILE_MAX, conf_file); + if (sz <= 0) { + prom_printf("Error, can't read config file\n"); + goto bail; + } + prom_printf("Config file read, %d bytes\n", sz); + + /* Close the file */ + if (opened) + file.fs->close(&file); + opened = 0; + + /* Call the parsing code in cfg.c */ + if (cfg_parse(conf_path, conf_file, sz) < 0) { + prom_printf ("Syntax error or read error config\n"); + goto bail; + } + + DEBUG_F("Config file successfully parsed, %d bytes\n", sz); + + /* Now, we do the initialisations stored in the config file */ + p = cfg_get_strg(0, "init-code"); + if (p) + prom_interpret(p); + + password = cfg_get_strg(0, "password"); #ifdef CONFIG_COLOR_TEXT - p = cfg_get_strg(0, "fgcolor"); - if (p) { - DEBUG_F("fgcolor=%s\n", p); - fgcolor = check_color_text_ui(p); - if (fgcolor == -1) { - prom_printf("Invalid fgcolor: \"%s\".\n", p); - } - } - p = cfg_get_strg(0, "bgcolor"); - if (p) { - DEBUG_F("bgcolor=%s\n", p); - bgcolor = check_color_text_ui(p); - if (bgcolor == -1) - prom_printf("Invalid bgcolor: \"%s\".\n", p); - } - if (bgcolor >= 0) { - char temp[64]; - sprintf(temp, "%x to background-color", bgcolor); - prom_interpret(temp); + p = cfg_get_strg(0, "fgcolor"); + if (p) { + DEBUG_F("fgcolor=%s\n", p); + fgcolor = check_color_text_ui(p); + if (fgcolor == -1) { + prom_printf("Invalid fgcolor: \"%s\".\n", p); + } + } + p = cfg_get_strg(0, "bgcolor"); + if (p) { + DEBUG_F("bgcolor=%s\n", p); + bgcolor = check_color_text_ui(p); + if (bgcolor == -1) + prom_printf("Invalid bgcolor: \"%s\".\n", p); + } + if (bgcolor >= 0) { + char temp[64]; + sprintf(temp, "%x to background-color", bgcolor); + prom_interpret(temp); #if !DEBUG - prom_printf("\xc"); + prom_printf("\xc"); #endif /* !DEBUG */ - } - if (fgcolor >= 0) { - char temp[64]; - sprintf(temp, "%x to foreground-color", fgcolor); - prom_interpret(temp); - } + } + if (fgcolor >= 0) { + char temp[64]; + sprintf(temp, "%x to foreground-color", fgcolor); + prom_interpret(temp); + } #endif /* CONFIG_COLOR_TEXT */ - p = cfg_get_strg(0, "init-message"); - if (p) - prom_printf("%s\n", p); + p = cfg_get_strg(0, "init-message"); + if (p) + prom_printf("%s\n", p); #if 0 - p = cfg_get_strg(0, "message"); - if (p) - print_message_file(p); + p = cfg_get_strg(0, "message"); + if (p) + print_message_file(p); #endif - result = 1; + result = 1; bail: - if (opened) - file.fs->close(&file); + if (opened) + file.fs->close(&file); - if (result != 1 && conf_file) - free(conf_file); + if (result != 1 && conf_file) + free(conf_file); - return result; + return result; } void maintabfunc (void) { - if (useconf) { - cfg_print_images(); - prom_printf("boot: %s", cbuff); - } + if (useconf) { + cfg_print_images(); + prom_printf("boot: %s", cbuff); + } } void word_split(char **linep, char **paramsp) { - char *p; - - *paramsp = 0; - p = *linep; - if (p == 0) - return; - while (*p == ' ') - ++p; - if (*p == 0) { - *linep = 0; - return; - } - *linep = p; - while (*p != 0 && *p != ' ') - ++p; - while (*p == ' ') - *p++ = 0; - if (*p != 0) - *paramsp = p; + char *p; + + *paramsp = 0; + p = *linep; + if (p == 0) + return; + while (*p == ' ') + ++p; + if (*p == 0) { + *linep = 0; + return; + } + *linep = p; + while (*p != 0 && *p != ' ') + ++p; + while (*p == ' ') + *p++ = 0; + if (*p != 0) + *paramsp = p; } char * make_params(char *label, char *params) { - char *p, *q; - static char buffer[2048]; - - q = buffer; - *q = 0; - - p = cfg_get_strg(label, "literal"); - if (p) { - strcpy(q, p); - q = strchr(q, 0); - if (params) { - if (*p) - *q++ = ' '; - strcpy(q, params); - } - return buffer; - } - - p = cfg_get_strg(label, "root"); - if (p) { - strcpy (q, "root="); - strcpy (q + 5, p); - q = strchr (q, 0); - *q++ = ' '; - } - if (cfg_get_flag(label, "read-only")) { - strcpy (q, "ro "); - q += 3; - } - if (cfg_get_flag(label, "read-write")) { - strcpy (q, "rw "); - q += 3; - } - p = cfg_get_strg(label, "ramdisk"); - if (p) { - strcpy (q, "ramdisk="); - strcpy (q + 8, p); - q = strchr (q, 0); - *q++ = ' '; - } - p = cfg_get_strg(label, "initrd-size"); - if (p) { - strcpy (q, "ramdisk_size="); - strcpy (q + 13, p); - q = strchr (q, 0); - *q++ = ' '; - } - if (cfg_get_flag(label, "novideo")) { - strcpy (q, "video=ofonly"); - q = strchr (q, 0); - *q++ = ' '; - } - p = cfg_get_strg (label, "append"); - if (p) { - strcpy (q, p); - q = strchr (q, 0); - *q++ = ' '; - } - *q = 0; - pause_after = cfg_get_flag (label, "pause-after"); - p = cfg_get_strg(label, "pause-message"); - if (p) - pause_message = p; - if (params) - strcpy(q, params); - - return buffer; + char *p, *q; + static char buffer[2048]; + + q = buffer; + *q = 0; + + p = cfg_get_strg(label, "literal"); + if (p) { + strcpy(q, p); + q = strchr(q, 0); + if (params) { + if (*p) + *q++ = ' '; + strcpy(q, params); + } + return buffer; + } + + p = cfg_get_strg(label, "root"); + if (p) { + strcpy (q, "root="); + strcpy (q + 5, p); + q = strchr (q, 0); + *q++ = ' '; + } + if (cfg_get_flag(label, "read-only")) { + strcpy (q, "ro "); + q += 3; + } + if (cfg_get_flag(label, "read-write")) { + strcpy (q, "rw "); + q += 3; + } + p = cfg_get_strg(label, "ramdisk"); + if (p) { + strcpy (q, "ramdisk="); + strcpy (q + 8, p); + q = strchr (q, 0); + *q++ = ' '; + } + p = cfg_get_strg(label, "initrd-size"); + if (p) { + strcpy (q, "ramdisk_size="); + strcpy (q + 13, p); + q = strchr (q, 0); + *q++ = ' '; + } + if (cfg_get_flag(label, "novideo")) { + strcpy (q, "video=ofonly"); + q = strchr (q, 0); + *q++ = ' '; + } + p = cfg_get_strg (label, "append"); + if (p) { + strcpy (q, p); + q = strchr (q, 0); + *q++ = ' '; + } + *q = 0; + pause_after = cfg_get_flag (label, "pause-after"); + p = cfg_get_strg(label, "pause-message"); + if (p) + pause_message = p; + if (params) + strcpy(q, params); + + return buffer; } void check_password(char *str) { - int i; + int i; - for (i = 0; i < 3; i++) { - prom_printf ("\n%sassword: ", str); - passwdbuff[0] = 0; - cmdedit ((void (*)(void)) 0, 1); - prom_printf ("\n"); + for (i = 0; i < 3; i++) { + prom_printf ("\n%sassword: ", str); + passwdbuff[0] = 0; + cmdedit ((void (*)(void)) 0, 1); + prom_printf ("\n"); #ifdef USE_MD5_PASSWORDS - if (!strncmp (password, "$1$", 3)) { - if (!check_md5_password(passwdbuff, password)) + if (!strncmp (password, "$1$", 3)) { + if (!check_md5_password(passwdbuff, password)) + return; + } + else if (!strcmp (password, passwdbuff)) return; - } - else if (!strcmp (password, passwdbuff)) - return; #else /* !MD5 */ - if (!strcmp (password, passwdbuff)) - return; + if (!strcmp (password, passwdbuff)) + return; #endif /* USE_MD5_PASSWORDS */ - if (i < 2) - prom_printf ("Password incorrect. Please try again..."); - } - prom_printf ("Seems like you don't know the access password. Go away!\n"); - prom_sleep(3); - prom_interpret("reset-all"); + if (i < 2) + prom_printf ("Password incorrect. Please try again..."); + } + prom_printf ("Seems like you don't know the access password. Go away!\n"); + prom_sleep(3); + prom_interpret("reset-all"); } int get_params(struct boot_param_t* params) { - int defpart; - char *defdevice = 0; - char *p, *q, *endp; - int c, n; - char *imagename = 0, *label; - int timeout = -1; - int beg = 0, end; - int singlekey = 0; - int restricted = 0; - static int first = 1; - static char bootargs[1024]; - static char imagepath[1024]; - static char initrdpath[1024]; - static char sysmappath[1024]; - - pause_after = 0; - memset(params, 0, sizeof(*params)); - params->args = ""; - params->kernel.part = -1; - params->rd.part = -1; - params->sysmap.part = -1; - defpart = boot.part; + int defpart; + char *defdevice = 0; + char *p, *q, *endp; + int c, n; + char *imagename = 0, *label; + int timeout = -1; + int beg = 0, end; + int singlekey = 0; + int restricted = 0; + static int first = 1; + static char bootargs[1024]; + static char imagepath[1024]; + static char initrdpath[1024]; + static char sysmappath[1024]; + + pause_after = 0; + memset(params, 0, sizeof(*params)); + params->args = ""; + params->kernel.part = -1; + params->rd.part = -1; + params->sysmap.part = -1; + defpart = boot.part; - cmdinit(); - - if (first) { - first = 0; - prom_get_chosen("bootargs", bootargs, sizeof(bootargs)); - imagename = bootargs; - word_split(&imagename, ¶ms->args); - timeout = DEFAULT_TIMEOUT; - if (imagename) { - prom_printf("Default supplied on the command line: %s ", imagename); - if (params->args) - prom_printf("%s", params->args); - prom_printf("\n"); - } - if (useconf && (q = cfg_get_strg(0, "timeout")) != 0 && *q != 0) - timeout = simple_strtol(q, NULL, 0); - } - - prom_printf("boot: "); - c = -1; - if (timeout != -1) { - beg = prom_getms(); - if (timeout > 0) { - end = beg + 100 * timeout; - do { - c = prom_nbgetchar(); - } while (c == -1 && prom_getms() <= end); - } - if (c == -1) - c = '\n'; - else if (c != '\n' && c != '\t' && c != '\r' && c != '\b' ) { - cbuff[0] = c; - cbuff[1] = 0; - } - } - - if (c != -1 && c != '\n' && c != '\r') { - if (c == '\t') { - maintabfunc (); - } else if (c >= ' ') { - cbuff[0] = c; - cbuff[1] = 0; - if ((cfg_get_flag (cbuff, "single-key")) && useconf) { - imagename = cbuff; - singlekey = 1; - prom_printf("%s\n", cbuff); - } - } - } - - if (c == '\n' || c == '\r') { - if (!imagename) - imagename = cfg_get_default(); - if (imagename) - prom_printf("%s", imagename); - if (params->args) - prom_printf(" %s", params->args); - prom_printf("\n"); - } else if (!singlekey) { - cmdedit(maintabfunc, 0); - prom_printf("\n"); - strcpy(given_bootargs, cbuff); - given_bootargs_by_user = 1; - imagename = cbuff; - word_split(&imagename, ¶ms->args); - } - - /* chrp gets this wrong, force it -- Cort */ - if ( useconf && (!imagename || imagename[0] == 0 )) - imagename = cfg_get_default(); - - label = 0; - defdevice = boot.dev; - - if (useconf) { - defdevice = cfg_get_strg(0, "device"); - p = cfg_get_strg(0, "partition"); - if (p) { - n = simple_strtol(p, &endp, 10); - if (endp != p && *endp == 0) - defpart = n; - } - p = cfg_get_strg(0, "pause-message"); - if (p) - pause_message = p; - if (cfg_get_flag(0, "restricted")) - restricted = 1; - p = cfg_get_strg(imagename, "image"); - if (p && *p) { - label = imagename; - imagename = p; - defdevice = cfg_get_strg(label, "device"); - if(!defdevice) defdevice=boot.dev; - p = cfg_get_strg(label, "partition"); - if (p) { - n = simple_strtol(p, &endp, 10); - if (endp != p && *endp == 0) + cmdinit(); + + if (first) { + first = 0; + prom_get_chosen("bootargs", bootargs, sizeof(bootargs)); + imagename = bootargs; + word_split(&imagename, ¶ms->args); + timeout = DEFAULT_TIMEOUT; + if (imagename) { + prom_printf("Default supplied on the command line: %s ", imagename); + if (params->args) + prom_printf("%s", params->args); + prom_printf("\n"); + } + if (useconf && (q = cfg_get_strg(0, "timeout")) != 0 && *q != 0) + timeout = simple_strtol(q, NULL, 0); + } + + prom_printf("boot: "); + c = -1; + if (timeout != -1) { + beg = prom_getms(); + if (timeout > 0) { + end = beg + 100 * timeout; + do { + c = prom_nbgetchar(); + } while (c == -1 && prom_getms() <= end); + } + if (c == -1) + c = '\n'; + else if (c != '\n' && c != '\t' && c != '\r' && c != '\b' ) { + cbuff[0] = c; + cbuff[1] = 0; + } + } + + if (c != -1 && c != '\n' && c != '\r') { + if (c == '\t') { + maintabfunc (); + } else if (c >= ' ') { + cbuff[0] = c; + cbuff[1] = 0; + if ((cfg_get_flag (cbuff, "single-key")) && useconf) { + imagename = cbuff; + singlekey = 1; + prom_printf("%s\n", cbuff); + } + } + } + + if (c == '\n' || c == '\r') { + if (!imagename) + imagename = cfg_get_default(); + if (imagename) + prom_printf("%s", imagename); + if (params->args) + prom_printf(" %s", params->args); + prom_printf("\n"); + } else if (!singlekey) { + cmdedit(maintabfunc, 0); + prom_printf("\n"); + strcpy(given_bootargs, cbuff); + given_bootargs_by_user = 1; + imagename = cbuff; + word_split(&imagename, ¶ms->args); + } + + /* chrp gets this wrong, force it -- Cort */ + if ( useconf && (!imagename || imagename[0] == 0 )) + imagename = cfg_get_default(); + + label = 0; + defdevice = boot.dev; + + if (useconf) { + defdevice = cfg_get_strg(0, "device"); + p = cfg_get_strg(0, "partition"); + if (p) { + n = simple_strtol(p, &endp, 10); + if (endp != p && *endp == 0) defpart = n; - } - if (cfg_get_flag(label, "restricted")) - restricted = 1; - if (label) { - if (params->args && password && restricted) - check_password ("To specify image arguments you must enter the p"); - else if (password && !restricted) - check_password ("P"); - } - params->args = make_params(label, params->args); - } - } - - if (!strcmp (imagename, "help")) { - prom_printf( - "\nPress the tab key for a list of defined images.\n" - "The label marked with a \"*\" is is the default image, " - "press to boot it.\n\n" - "To boot any other label simply type its name and press .\n\n" - "To boot a kernel image which is not defined in the yaboot configuration \n" - "file, enter the kernel image name as [device:][partno],/path, where \n" - "\"device:\" is the OpenFirmware device path to the disk the image \n" - "resides on, and \"partno\" is the partition number the image resides on.\n\n" - "If you omit \"device:\" and \"partno\" yaboot will use the values of \n" - "\"device=\" and \"partition=\" in yaboot.conf, right now those are set to: \n" - "device=%s\n" - "partition=%d\n\n", defdevice, defpart); - return 0; - } - - if (!strcmp (imagename, "halt")) { - if (password) - check_password ("P"); - prom_pause(); - return 0; - } - if (!strcmp (imagename, "bye")) { - if (password) { - check_password ("P"); - return 1; - } - return 1; - } - - if (imagename[0] == '$') { - /* forth command string */ - if (password) - check_password ("P"); - prom_interpret(imagename+1); - return 0; - } - - strncpy(imagepath, imagename, 1024); - - if (!label && password) - check_password ("To boot a custom image you must enter the p"); - - if (!parse_device_path(imagepath, defdevice, defpart, - "/vmlinux", ¶ms->kernel)) { - prom_printf("%s: Unable to parse\n", imagepath); - return 0; - } - DEBUG_F("after parse_device_path: dev=%s part=%d file=%s\n", params->kernel.dev, - params->kernel.part, params->kernel.file); - - if (useconf) { - p = cfg_get_strg(label, "initrd"); - if (p && *p) { - DEBUG_F("Parsing initrd path <%s>\n", p); - strncpy(initrdpath, p, 1024); - if (!parse_device_path(initrdpath, defdevice, defpart, - "/root.bin", ¶ms->rd)) { - prom_printf("%s: Unable to parse\n", imagepath); - return 0; - } - } - p = cfg_get_strg(label, "sysmap"); - if (p && *p) { - DEBUG_F("Parsing sysmap path <%s>\n", p); - strncpy(sysmappath, p, 1024); - if (!parse_device_path(sysmappath, defdevice, defpart, - "/boot/System.map", ¶ms->sysmap)) { - prom_printf("%s: Unable to parse\n", imagepath); - return 0; - } - } - } - return 0; + } + p = cfg_get_strg(0, "pause-message"); + if (p) + pause_message = p; + if (cfg_get_flag(0, "restricted")) + restricted = 1; + p = cfg_get_strg(imagename, "image"); + if (p && *p) { + label = imagename; + imagename = p; + defdevice = cfg_get_strg(label, "device"); + if(!defdevice) defdevice=boot.dev; + p = cfg_get_strg(label, "partition"); + if (p) { + n = simple_strtol(p, &endp, 10); + if (endp != p && *endp == 0) + defpart = n; + } + if (cfg_get_flag(label, "restricted")) + restricted = 1; + if (label) { + if (params->args && password && restricted) + check_password ("To specify image arguments you must enter the p"); + else if (password && !restricted) + check_password ("P"); + } + params->args = make_params(label, params->args); + } + } + + if (!strcmp (imagename, "help")) { + prom_printf( + "\nPress the tab key for a list of defined images.\n" + "The label marked with a \"*\" is is the default image, " + "press to boot it.\n\n" + "To boot any other label simply type its name and press .\n\n" + "To boot a kernel image which is not defined in the yaboot configuration \n" + "file, enter the kernel image name as [device:][partno],/path, where \n" + "\"device:\" is the OpenFirmware device path to the disk the image \n" + "resides on, and \"partno\" is the partition number the image resides on.\n" + "Note that the comma (,) is only required if you specify an OpenFirmware\n" + "device, if you only specify a filename you should not start it with a \",\"\n\n" + "If you omit \"device:\" and \"partno\" yaboot will use the values of \n" + "\"device=\" and \"partition=\" in yaboot.conf, right now those are set to: \n" + "device=%s\n" + "partition=%d\n\n", defdevice, defpart); + return 0; + } + + if (!strcmp (imagename, "halt")) { + if (password) + check_password ("P"); + prom_pause(); + return 0; + } + if (!strcmp (imagename, "bye")) { + if (password) { + check_password ("P"); + return 1; + } + return 1; + } + + if (imagename[0] == '$') { + /* forth command string */ + if (password) + check_password ("P"); + prom_interpret(imagename+1); + return 0; + } + + strncpy(imagepath, imagename, 1024); + + if (!label && password) + check_password ("To boot a custom image you must enter the p"); + + if (!parse_device_path(imagepath, defdevice, defpart, + "/vmlinux", ¶ms->kernel)) { + prom_printf("%s: Unable to parse\n", imagepath); + return 0; + } + DEBUG_F("after parse_device_path: dev=%s part=%d file=%s\n", params->kernel.dev, + params->kernel.part, params->kernel.file); + + if (useconf) { + p = cfg_get_strg(label, "initrd"); + if (p && *p) { + DEBUG_F("Parsing initrd path <%s>\n", p); + strncpy(initrdpath, p, 1024); + if (!parse_device_path(initrdpath, defdevice, defpart, + "/root.bin", ¶ms->rd)) { + prom_printf("%s: Unable to parse\n", imagepath); + return 0; + } + } + p = cfg_get_strg(label, "sysmap"); + if (p && *p) { + DEBUG_F("Parsing sysmap path <%s>\n", p); + strncpy(sysmappath, p, 1024); + if (!parse_device_path(sysmappath, defdevice, defpart, + "/boot/System.map", ¶ms->sysmap)) { + prom_printf("%s: Unable to parse\n", imagepath); + return 0; + } + } + } + return 0; } /* This is derived from quik core. To be changed to first parse the headers @@ -733,625 +735,625 @@ yaboot_text_ui(void) { #define MAX_HEADERS 32 - struct boot_file_t file; - int result; - static struct boot_param_t params; - void *initrd_base; - unsigned long initrd_size; - void *sysmap_base; - unsigned long sysmap_size; - kernel_entry_t kernel_entry; - struct bi_record* birec; - char* loc=NULL; - loadinfo_t loadinfo; - void *initrd_more,*initrd_want; - unsigned long initrd_read; + struct boot_file_t file; + int result; + static struct boot_param_t params; + void *initrd_base; + unsigned long initrd_size; + void *sysmap_base; + unsigned long sysmap_size; + kernel_entry_t kernel_entry; + struct bi_record* birec; + char* loc=NULL; + loadinfo_t loadinfo; + void *initrd_more,*initrd_want; + unsigned long initrd_read; - loadinfo.load_loc = 0; + loadinfo.load_loc = 0; - for (;;) { - initrd_size = 0; - initrd_base = 0; - sysmap_base = 0; - sysmap_size = 0; + for (;;) { + initrd_size = 0; + initrd_base = 0; + sysmap_base = 0; + sysmap_size = 0; - if (get_params(¶ms)) - return; - if (!params.kernel.file) - continue; + if (get_params(¶ms)) + return; + if (!params.kernel.file) + continue; - prom_printf("Please wait, loading kernel...\n"); - - memset(&file, 0, sizeof(file)); - - if (strlen(boot.file) && !strcmp(boot.file,"\\\\") && params.kernel.file[0] != '/' - && params.kernel.file[0] != '\\') { - loc=(char*)malloc(strlen(params.kernel.file)+3); - if (!loc) { - prom_printf ("malloc error\n"); - goto next; - } - strcpy(loc,boot.file); - strcat(loc,params.kernel.file); - free(params.kernel.file); - params.kernel.file=loc; - } - result = open_file(¶ms.kernel, &file); - if (result != FILE_ERR_OK) { - prom_printf("%s:%d,", params.kernel.dev, params.kernel.part); - prom_perror(result, params.kernel.file); - goto next; - } - - /* Read the Elf e_ident, e_type and e_machine fields to - * determine Elf file type - */ - if (file.fs->read(&file, sizeof(Elf_Ident), &loadinfo.elf) < sizeof(Elf_Ident)) { - prom_printf("\nCan't read Elf e_ident/e_type/e_machine info\n"); - file.fs->close(&file); - memset(&file, 0, sizeof(file)); - goto next; - } - - if (is_elf32(&loadinfo)) { - if (!load_elf32(&file, &loadinfo)) { - file.fs->close(&file); - memset(&file, 0, sizeof(file)); - goto next; - } - prom_printf(" Elf32 kernel loaded...\n"); - } else if (is_elf64(&loadinfo)) { - if (!load_elf64(&file, &loadinfo)) { - file.fs->close(&file); - memset(&file, 0, sizeof(file)); - goto next; - } - prom_printf(" Elf64 kernel loaded...\n"); - } else { - prom_printf ("%s: Not a valid ELF image\n", params.kernel.file); - file.fs->close(&file); - memset(&file, 0, sizeof(file)); - goto next; - } - file.fs->close(&file); - memset(&file, 0, sizeof(file)); - - /* If sysmap, load it. - */ - if (params.sysmap.file) { - prom_printf("Loading System.map ...\n"); - if(strlen(boot.file) && !strcmp(boot.file,"\\\\") && params.sysmap.file[0] != '/' - && params.sysmap.file[0] != '\\') { - if (loc) free(loc); - loc=(char*)malloc(strlen(params.sysmap.file)+3); - if (!loc) { - prom_printf ("malloc error\n"); - goto next; - } - strcpy(loc,boot.file); - strcat(loc,params.sysmap.file); - free(params.sysmap.file); - params.sysmap.file=loc; - } - - result = open_file(¶ms.sysmap, &file); - if (result != FILE_ERR_OK) { - prom_printf("%s:%d,", params.sysmap.dev, params.sysmap.part); - prom_perror(result, params.sysmap.file); - } - else { - sysmap_base = prom_claim(loadinfo.base+loadinfo.memsize, 0x100000, 0); - if (sysmap_base == (void *)-1) { - prom_printf("Claim failed for sysmap memory\n"); - sysmap_base = 0; - } else { - sysmap_size = file.fs->read(&file, 0xfffff, sysmap_base); - if (sysmap_size == 0) - sysmap_base = 0; - else - ((char *)sysmap_base)[sysmap_size++] = 0; - } - file.fs->close(&file); - memset(&file, 0, sizeof(file)); - } - if (sysmap_base) { - prom_printf("System.map loaded at %p, size: %lu Kbytes\n", - sysmap_base, sysmap_size >> 10); - loadinfo.memsize += _ALIGN(0x100000, 0x1000); - } else { - prom_printf("System.map load failed !\n"); - prom_pause(); - } - } - - /* If ramdisk, load it. For now, we can't tell the size it will be - * so we claim an arbitrary amount of 4Mb - */ - if (params.rd.file) { - if(strlen(boot.file) && !strcmp(boot.file,"\\\\") && params.rd.file[0] != '/' - && params.kernel.file[0] != '\\') - { - if (loc) free(loc); - loc=(char*)malloc(strlen(params.rd.file)+3); - if (!loc) { - prom_printf ("Malloc error\n"); + prom_printf("Please wait, loading kernel...\n"); + + memset(&file, 0, sizeof(file)); + + if (strlen(boot.file) && !strcmp(boot.file,"\\\\") && params.kernel.file[0] != '/' + && params.kernel.file[0] != '\\') { + loc=(char*)malloc(strlen(params.kernel.file)+3); + if (!loc) { + prom_printf ("malloc error\n"); goto next; - } - strcpy(loc,boot.file); - strcat(loc,params.rd.file); - free(params.rd.file); - params.rd.file=loc; - } - prom_printf("Loading ramdisk...\n"); - result = open_file(¶ms.rd, &file); - if (result != FILE_ERR_OK) { - prom_printf("%s:%d,", params.rd.dev, params.rd.part); - prom_perror(result, params.rd.file); - } - else { + } + strcpy(loc,boot.file); + strcat(loc,params.kernel.file); + free(params.kernel.file); + params.kernel.file=loc; + } + result = open_file(¶ms.kernel, &file); + if (result != FILE_ERR_OK) { + prom_printf("%s:%d,", params.kernel.dev, params.kernel.part); + prom_perror(result, params.kernel.file); + goto next; + } + + /* Read the Elf e_ident, e_type and e_machine fields to + * determine Elf file type + */ + if (file.fs->read(&file, sizeof(Elf_Ident), &loadinfo.elf) < sizeof(Elf_Ident)) { + prom_printf("\nCan't read Elf e_ident/e_type/e_machine info\n"); + file.fs->close(&file); + memset(&file, 0, sizeof(file)); + goto next; + } + + if (is_elf32(&loadinfo)) { + if (!load_elf32(&file, &loadinfo)) { + file.fs->close(&file); + memset(&file, 0, sizeof(file)); + goto next; + } + prom_printf(" Elf32 kernel loaded...\n"); + } else if (is_elf64(&loadinfo)) { + if (!load_elf64(&file, &loadinfo)) { + file.fs->close(&file); + memset(&file, 0, sizeof(file)); + goto next; + } + prom_printf(" Elf64 kernel loaded...\n"); + } else { + prom_printf ("%s: Not a valid ELF image\n", params.kernel.file); + file.fs->close(&file); + memset(&file, 0, sizeof(file)); + goto next; + } + file.fs->close(&file); + memset(&file, 0, sizeof(file)); + + /* If sysmap, load it. + */ + if (params.sysmap.file) { + prom_printf("Loading System.map ...\n"); + if(strlen(boot.file) && !strcmp(boot.file,"\\\\") && params.sysmap.file[0] != '/' + && params.sysmap.file[0] != '\\') { + if (loc) free(loc); + loc=(char*)malloc(strlen(params.sysmap.file)+3); + if (!loc) { + prom_printf ("malloc error\n"); + goto next; + } + strcpy(loc,boot.file); + strcat(loc,params.sysmap.file); + free(params.sysmap.file); + params.sysmap.file=loc; + } + + result = open_file(¶ms.sysmap, &file); + if (result != FILE_ERR_OK) { + prom_printf("%s:%d,", params.sysmap.dev, params.sysmap.part); + prom_perror(result, params.sysmap.file); + } + else { + sysmap_base = prom_claim(loadinfo.base+loadinfo.memsize, 0x100000, 0); + if (sysmap_base == (void *)-1) { + prom_printf("Claim failed for sysmap memory\n"); + sysmap_base = 0; + } else { + sysmap_size = file.fs->read(&file, 0xfffff, sysmap_base); + if (sysmap_size == 0) + sysmap_base = 0; + else + ((char *)sysmap_base)[sysmap_size++] = 0; + } + file.fs->close(&file); + memset(&file, 0, sizeof(file)); + } + if (sysmap_base) { + prom_printf("System.map loaded at %p, size: %lu Kbytes\n", + sysmap_base, sysmap_size >> 10); + loadinfo.memsize += _ALIGN(0x100000, 0x1000); + } else { + prom_printf("System.map load failed !\n"); + prom_pause(); + } + } + + /* If ramdisk, load it. For now, we can't tell the size it will be + * so we claim an arbitrary amount of 4Mb + */ + if (params.rd.file) { + if(strlen(boot.file) && !strcmp(boot.file,"\\\\") && params.rd.file[0] != '/' + && params.kernel.file[0] != '\\') + { + if (loc) free(loc); + loc=(char*)malloc(strlen(params.rd.file)+3); + if (!loc) { + prom_printf ("Malloc error\n"); + goto next; + } + strcpy(loc,boot.file); + strcat(loc,params.rd.file); + free(params.rd.file); + params.rd.file=loc; + } + prom_printf("Loading ramdisk...\n"); + result = open_file(¶ms.rd, &file); + if (result != FILE_ERR_OK) { + prom_printf("%s:%d,", params.rd.dev, params.rd.part); + prom_perror(result, params.rd.file); + } + else { #define INITRD_CHUNKSIZE 0x400000 - initrd_base = prom_claim(loadinfo.base+loadinfo.memsize, INITRD_CHUNKSIZE, 0); - if (initrd_base == (void *)-1) { - prom_printf("Claim failed for initrd memory\n"); - initrd_base = 0; - } else { - initrd_size = file.fs->read(&file, INITRD_CHUNKSIZE, initrd_base); - if (initrd_size == 0) - initrd_base = 0; - initrd_read = initrd_size; - initrd_more = initrd_base; - while (initrd_read == INITRD_CHUNKSIZE ) { /* need to read more? */ - initrd_want = (void *)((unsigned long)initrd_more+INITRD_CHUNKSIZE); - initrd_more = prom_claim(initrd_want, INITRD_CHUNKSIZE, 0); - if (initrd_more != initrd_want) { - prom_printf("Claim failed for initrd memory at %p rc=%p\n",initrd_want,initrd_more); - break; - } - initrd_read = file.fs->read(&file, INITRD_CHUNKSIZE, initrd_more); - DEBUG_F(" block at %p rc=%lu\n",initrd_more,initrd_read); - initrd_size += initrd_read; + initrd_base = prom_claim(loadinfo.base+loadinfo.memsize, INITRD_CHUNKSIZE, 0); + if (initrd_base == (void *)-1) { + prom_printf("Claim failed for initrd memory\n"); + initrd_base = 0; + } else { + initrd_size = file.fs->read(&file, INITRD_CHUNKSIZE, initrd_base); + if (initrd_size == 0) + initrd_base = 0; + initrd_read = initrd_size; + initrd_more = initrd_base; + while (initrd_read == INITRD_CHUNKSIZE ) { /* need to read more? */ + initrd_want = (void *)((unsigned long)initrd_more+INITRD_CHUNKSIZE); + initrd_more = prom_claim(initrd_want, INITRD_CHUNKSIZE, 0); + if (initrd_more != initrd_want) { + prom_printf("Claim failed for initrd memory at %p rc=%p\n",initrd_want,initrd_more); + break; + } + initrd_read = file.fs->read(&file, INITRD_CHUNKSIZE, initrd_more); + DEBUG_F(" block at %p rc=%lu\n",initrd_more,initrd_read); + initrd_size += initrd_read; + } } - } - file.fs->close(&file); - memset(&file, 0, sizeof(file)); - } - if (initrd_base) - prom_printf("ramdisk loaded at %p, size: %lu Kbytes\n", - initrd_base, initrd_size >> 10); - else { - prom_printf("ramdisk load failed !\n"); - prom_pause(); - } - } - - DEBUG_F("setting kernel args to: %s\n", params.args); - prom_setargs(params.args); - DEBUG_F("flushing icache..."); - flush_icache_range ((long)loadinfo.base, (long)loadinfo.base+loadinfo.memsize); - DEBUG_F(" done\n"); - - /* - * Fill mew boot infos - * - * The birec is low on memory, probably inside the malloc pool, so - * we don't write it earlier. At this point, we should not use anything - * coming from the malloc pool - */ - birec = (struct bi_record *)_ALIGN(loadinfo.filesize+(1<<20)-1,(1<<20)); - - /* We make sure it's mapped. We map only 64k for now, it's plenty enough - * we don't claim since this precise memory range may already be claimed - * by the malloc pool - */ - prom_map (birec, birec, 0x10000); - DEBUG_F("birec at %p\n", birec); - DEBUG_SLEEP; - - birec->tag = BI_FIRST; - birec->size = sizeof(struct bi_record); - birec = (struct bi_record *)((unsigned long)birec + birec->size); + file.fs->close(&file); + memset(&file, 0, sizeof(file)); + } + if (initrd_base) + prom_printf("ramdisk loaded at %p, size: %lu Kbytes\n", + initrd_base, initrd_size >> 10); + else { + prom_printf("ramdisk load failed !\n"); + prom_pause(); + } + } + + DEBUG_F("setting kernel args to: %s\n", params.args); + prom_setargs(params.args); + DEBUG_F("flushing icache..."); + flush_icache_range ((long)loadinfo.base, (long)loadinfo.base+loadinfo.memsize); + DEBUG_F(" done\n"); + +/* + * Fill mew boot infos + * + * The birec is low on memory, probably inside the malloc pool, so + * we don't write it earlier. At this point, we should not use anything + * coming from the malloc pool + */ + birec = (struct bi_record *)_ALIGN(loadinfo.filesize+(1<<20)-1,(1<<20)); + +/* We make sure it's mapped. We map only 64k for now, it's plenty enough + * we don't claim since this precise memory range may already be claimed + * by the malloc pool + */ + prom_map (birec, birec, 0x10000); + DEBUG_F("birec at %p\n", birec); + DEBUG_SLEEP; + + birec->tag = BI_FIRST; + birec->size = sizeof(struct bi_record); + birec = (struct bi_record *)((unsigned long)birec + birec->size); - birec->tag = BI_BOOTLOADER_ID; - sprintf( (char *)birec->data, "yaboot"); - birec->size = sizeof(struct bi_record) + strlen("yaboot") + 1; - birec = (struct bi_record *)((unsigned long)birec + birec->size); + birec->tag = BI_BOOTLOADER_ID; + sprintf( (char *)birec->data, "yaboot"); + birec->size = sizeof(struct bi_record) + strlen("yaboot") + 1; + birec = (struct bi_record *)((unsigned long)birec + birec->size); - birec->tag = BI_MACHTYPE; - birec->data[0] = _machine; - birec->size = sizeof(struct bi_record) + sizeof(unsigned long); - birec = (struct bi_record *)((unsigned long)birec + birec->size); - - if (sysmap_base) { - birec->tag = BI_SYSMAP; - birec->data[0] = (unsigned long)sysmap_base; - birec->data[1] = sysmap_size; - birec->size = sizeof(struct bi_record) + sizeof(unsigned long)*2; - birec = (struct bi_record *)((unsigned long)birec + birec->size); - } - birec->tag = BI_LAST; - birec->size = sizeof(struct bi_record); - birec = (struct bi_record *)((unsigned long)birec + birec->size); - - /* compute the kernel's entry point. */ - kernel_entry = loadinfo.base + loadinfo.entry - loadinfo.load_loc; - - DEBUG_F("Kernel entry point = %p\n", kernel_entry); - DEBUG_F("kernel: arg1 = %p,\n" - " arg2 = 0x%08lx,\n" - " prom = %p,\n" - " arg4 = %d,\n" - " arg5 = %d\n\n", - initrd_base + loadinfo.load_loc, initrd_size, prom, 0, 0); - - DEBUG_F("Entering kernel...\n"); - - /* call the kernel with our stack. */ - kernel_entry(initrd_base + loadinfo.load_loc, initrd_size, prom, 0, 0); - continue; -next: - ; /* do nothing */ - } + birec->tag = BI_MACHTYPE; + birec->data[0] = _machine; + birec->size = sizeof(struct bi_record) + sizeof(unsigned long); + birec = (struct bi_record *)((unsigned long)birec + birec->size); + + if (sysmap_base) { + birec->tag = BI_SYSMAP; + birec->data[0] = (unsigned long)sysmap_base; + birec->data[1] = sysmap_size; + birec->size = sizeof(struct bi_record) + sizeof(unsigned long)*2; + birec = (struct bi_record *)((unsigned long)birec + birec->size); + } + birec->tag = BI_LAST; + birec->size = sizeof(struct bi_record); + birec = (struct bi_record *)((unsigned long)birec + birec->size); + + /* compute the kernel's entry point. */ + kernel_entry = loadinfo.base + loadinfo.entry - loadinfo.load_loc; + + DEBUG_F("Kernel entry point = %p\n", kernel_entry); + DEBUG_F("kernel: arg1 = %p,\n" + " arg2 = 0x%08lx,\n" + " prom = %p,\n" + " arg4 = %d,\n" + " arg5 = %d\n\n", + initrd_base + loadinfo.load_loc, initrd_size, prom, 0, 0); + + DEBUG_F("Entering kernel...\n"); + + /* call the kernel with our stack. */ + kernel_entry(initrd_base + loadinfo.load_loc, initrd_size, prom, 0, 0); + continue; + next: + ; /* do nothing */ + } } static int load_elf32(struct boot_file_t *file, loadinfo_t *loadinfo) { - int i; - Elf32_Ehdr *e = &(loadinfo->elf.elf32hdr); - Elf32_Phdr *p, *ph; - int size = sizeof(Elf32_Ehdr) - sizeof(Elf_Ident); - unsigned long addr, loadaddr; - - /* Read the rest of the Elf header... */ - if ((*(file->fs->read))(file, size, &e->e_version) < size) { - prom_printf("\nCan't read Elf32 image header\n"); - return 0; - } - - DEBUG_F("Elf32 header:\n"); - DEBUG_F(" e.e_type = %d\n", (int)e->e_type); - DEBUG_F(" e.e_machine = %d\n", (int)e->e_machine); - DEBUG_F(" e.e_version = %d\n", (int)e->e_version); - DEBUG_F(" e.e_entry = 0x%08x\n", (int)e->e_entry); - DEBUG_F(" e.e_phoff = 0x%08x\n", (int)e->e_phoff); - DEBUG_F(" e.e_shoff = 0x%08x\n", (int)e->e_shoff); - DEBUG_F(" e.e_flags = %d\n", (int)e->e_flags); - DEBUG_F(" e.e_ehsize = 0x%08x\n", (int)e->e_ehsize); - DEBUG_F(" e.e_phentsize = 0x%08x\n", (int)e->e_phentsize); - DEBUG_F(" e.e_phnum = %d\n", (int)e->e_phnum); - - loadinfo->entry = e->e_entry; - - if (e->e_phnum > MAX_HEADERS) { - prom_printf ("Can only load kernels with one program header\n"); - return 0; - } - - ph = (Elf32_Phdr *)malloc(sizeof(Elf32_Phdr) * e->e_phnum); - if (!ph) { - prom_printf ("Malloc error\n"); - return 0; - } - - /* Now, we read the section header */ - if ((*(file->fs->seek))(file, e->e_phoff) != FILE_ERR_OK) { - prom_printf ("seek error\n"); - return 0; - } - if ((*(file->fs->read))(file, sizeof(Elf32_Phdr) * e->e_phnum, ph) != - sizeof(Elf32_Phdr) * e->e_phnum) { - prom_printf ("read error\n"); - return 0; - } - - /* Scan through the program header - * HACK: We must return the _memory size of the kernel image, not the - * file size (because we have to leave room before other boot - * infos. This code works as a side effect of the fact that - * we have one section and vaddr == p_paddr - */ - loadinfo->memsize = loadinfo->filesize = loadinfo->offset = 0; - p = ph; - for (i = 0; i < e->e_phnum; ++i, ++p) { - if (p->p_type != PT_LOAD || p->p_offset == 0) - continue; - if (loadinfo->memsize == 0) { - loadinfo->offset = p->p_offset; - loadinfo->memsize = p->p_memsz; - loadinfo->filesize = p->p_filesz; - loadinfo->load_loc = p->p_vaddr; - } else { - loadinfo->memsize = p->p_offset + p->p_memsz - loadinfo->offset; /* XXX Bogus */ - loadinfo->filesize = p->p_offset + p->p_filesz - loadinfo->offset; - } - } - - if (loadinfo->memsize == 0) { - prom_printf("Can't find a loadable segment !\n"); - return 0; - } - - /* leave some room (1Mb) for boot infos */ - loadinfo->memsize = _ALIGN(loadinfo->memsize,(1<<20)) + 0x100000; - /* Claim OF memory */ - DEBUG_F("Before prom_claim, mem_sz: 0x%08lx\n", loadinfo->memsize); - - /* On some systems, loadaddr may already be claimed, so try some - * other nearby addresses before giving up. - */ - loadaddr = (e->e_entry == KERNEL_LINK_ADDR_PPC32 || - e->e_entry == 0) ? KERNELADDR : e->e_entry; - for(addr=loadaddr; addr <= loadaddr * 8 ;addr+=0x100000) { - loadinfo->base = prom_claim((void *)addr, loadinfo->memsize, 0); - if (loadinfo->base != (void *)-1) break; - } - if (loadinfo->base == (void *)-1) { - prom_printf("Claim error, can't allocate kernel memory\n"); - return 0; - } - - DEBUG_F("After ELF parsing, load base: %p, mem_sz: 0x%08lx\n", - loadinfo->base, loadinfo->memsize); - DEBUG_F(" wanted load base: 0x%08lx, mem_sz: 0x%08lx\n", - loadaddr, loadinfo->memsize); - - /* Load the program segments... */ - p = ph; - for (i = 0; i < e->e_phnum; ++i, ++p) { - unsigned long offset; - if (p->p_type != PT_LOAD || p->p_offset == 0) - continue; - - /* Now, we skip to the image itself */ - if ((*(file->fs->seek))(file, p->p_offset) != FILE_ERR_OK) { - prom_printf ("Seek error\n"); - prom_release(loadinfo->base, loadinfo->memsize); - return 0; - } - offset = p->p_vaddr - loadinfo->load_loc; - if ((*(file->fs->read))(file, p->p_filesz, loadinfo->base+offset) != p->p_filesz) { - prom_printf ("Read failed\n"); - prom_release(loadinfo->base, loadinfo->memsize); - return 0; - } - } - - free(ph); + int i; + Elf32_Ehdr *e = &(loadinfo->elf.elf32hdr); + Elf32_Phdr *p, *ph; + int size = sizeof(Elf32_Ehdr) - sizeof(Elf_Ident); + unsigned long addr, loadaddr; + + /* Read the rest of the Elf header... */ + if ((*(file->fs->read))(file, size, &e->e_version) < size) { + prom_printf("\nCan't read Elf32 image header\n"); + return 0; + } + + DEBUG_F("Elf32 header:\n"); + DEBUG_F(" e.e_type = %d\n", (int)e->e_type); + DEBUG_F(" e.e_machine = %d\n", (int)e->e_machine); + DEBUG_F(" e.e_version = %d\n", (int)e->e_version); + DEBUG_F(" e.e_entry = 0x%08x\n", (int)e->e_entry); + DEBUG_F(" e.e_phoff = 0x%08x\n", (int)e->e_phoff); + DEBUG_F(" e.e_shoff = 0x%08x\n", (int)e->e_shoff); + DEBUG_F(" e.e_flags = %d\n", (int)e->e_flags); + DEBUG_F(" e.e_ehsize = 0x%08x\n", (int)e->e_ehsize); + DEBUG_F(" e.e_phentsize = 0x%08x\n", (int)e->e_phentsize); + DEBUG_F(" e.e_phnum = %d\n", (int)e->e_phnum); + + loadinfo->entry = e->e_entry; + + if (e->e_phnum > MAX_HEADERS) { + prom_printf ("Can only load kernels with one program header\n"); + return 0; + } + + ph = (Elf32_Phdr *)malloc(sizeof(Elf32_Phdr) * e->e_phnum); + if (!ph) { + prom_printf ("Malloc error\n"); + return 0; + } + + /* Now, we read the section header */ + if ((*(file->fs->seek))(file, e->e_phoff) != FILE_ERR_OK) { + prom_printf ("seek error\n"); + return 0; + } + if ((*(file->fs->read))(file, sizeof(Elf32_Phdr) * e->e_phnum, ph) != + sizeof(Elf32_Phdr) * e->e_phnum) { + prom_printf ("read error\n"); + return 0; + } + + /* Scan through the program header + * HACK: We must return the _memory size of the kernel image, not the + * file size (because we have to leave room before other boot + * infos. This code works as a side effect of the fact that + * we have one section and vaddr == p_paddr + */ + loadinfo->memsize = loadinfo->filesize = loadinfo->offset = 0; + p = ph; + for (i = 0; i < e->e_phnum; ++i, ++p) { + if (p->p_type != PT_LOAD || p->p_offset == 0) + continue; + if (loadinfo->memsize == 0) { + loadinfo->offset = p->p_offset; + loadinfo->memsize = p->p_memsz; + loadinfo->filesize = p->p_filesz; + loadinfo->load_loc = p->p_vaddr; + } else { + loadinfo->memsize = p->p_offset + p->p_memsz - loadinfo->offset; /* XXX Bogus */ + loadinfo->filesize = p->p_offset + p->p_filesz - loadinfo->offset; + } + } + + if (loadinfo->memsize == 0) { + prom_printf("Can't find a loadable segment !\n"); + return 0; + } + + /* leave some room (1Mb) for boot infos */ + loadinfo->memsize = _ALIGN(loadinfo->memsize,(1<<20)) + 0x100000; + /* Claim OF memory */ + DEBUG_F("Before prom_claim, mem_sz: 0x%08lx\n", loadinfo->memsize); + + /* On some systems, loadaddr may already be claimed, so try some + * other nearby addresses before giving up. + */ + loadaddr = (e->e_entry == KERNEL_LINK_ADDR_PPC32 || + e->e_entry == 0) ? KERNELADDR : e->e_entry; + for(addr=loadaddr; addr <= loadaddr * 8 ;addr+=0x100000) { + loadinfo->base = prom_claim((void *)addr, loadinfo->memsize, 0); + if (loadinfo->base != (void *)-1) break; + } + if (loadinfo->base == (void *)-1) { + prom_printf("Claim error, can't allocate kernel memory\n"); + return 0; + } + + DEBUG_F("After ELF parsing, load base: %p, mem_sz: 0x%08lx\n", + loadinfo->base, loadinfo->memsize); + DEBUG_F(" wanted load base: 0x%08lx, mem_sz: 0x%08lx\n", + loadaddr, loadinfo->memsize); + + /* Load the program segments... */ + p = ph; + for (i = 0; i < e->e_phnum; ++i, ++p) { + unsigned long offset; + if (p->p_type != PT_LOAD || p->p_offset == 0) + continue; + + /* Now, we skip to the image itself */ + if ((*(file->fs->seek))(file, p->p_offset) != FILE_ERR_OK) { + prom_printf ("Seek error\n"); + prom_release(loadinfo->base, loadinfo->memsize); + return 0; + } + offset = p->p_vaddr - loadinfo->load_loc; + if ((*(file->fs->read))(file, p->p_filesz, loadinfo->base+offset) != p->p_filesz) { + prom_printf ("Read failed\n"); + prom_release(loadinfo->base, loadinfo->memsize); + return 0; + } + } + + free(ph); - /* Return success at loading the Elf32 kernel */ - return 1; + /* Return success at loading the Elf32 kernel */ + return 1; } static int load_elf64(struct boot_file_t *file, loadinfo_t *loadinfo) { - int i; - Elf64_Ehdr *e = &(loadinfo->elf.elf64hdr); - Elf64_Phdr *p, *ph; - int size = sizeof(Elf64_Ehdr) - sizeof(Elf_Ident); - unsigned long addr, loadaddr; - - /* Read the rest of the Elf header... */ - if ((*(file->fs->read))(file, size, &e->e_version) < size) { - prom_printf("\nCan't read Elf64 image header\n"); - return 0; - } - - DEBUG_F("Elf64 header:\n"); - DEBUG_F(" e.e_type = %d\n", (int)e->e_type); - DEBUG_F(" e.e_machine = %d\n", (int)e->e_machine); - DEBUG_F(" e.e_version = %d\n", (int)e->e_version); - DEBUG_F(" e.e_entry = 0x%016lx\n", (long)e->e_entry); - DEBUG_F(" e.e_phoff = 0x%016lx\n", (long)e->e_phoff); - DEBUG_F(" e.e_shoff = 0x%016lx\n", (long)e->e_shoff); - DEBUG_F(" e.e_flags = %d\n", (int)e->e_flags); - DEBUG_F(" e.e_ehsize = 0x%08x\n", (int)e->e_ehsize); - DEBUG_F(" e.e_phentsize = 0x%08x\n", (int)e->e_phentsize); - DEBUG_F(" e.e_phnum = %d\n", (int)e->e_phnum); - - loadinfo->entry = e->e_entry; - - if (e->e_phnum > MAX_HEADERS) { - prom_printf ("Can only load kernels with one program header\n"); - return 0; - } - - ph = (Elf64_Phdr *)malloc(sizeof(Elf64_Phdr) * e->e_phnum); - if (!ph) { - prom_printf ("Malloc error\n"); - return 0; - } - - /* Now, we read the section header */ - if ((*(file->fs->seek))(file, e->e_phoff) != FILE_ERR_OK) { - prom_printf ("Seek error\n"); - return 0; - } - if ((*(file->fs->read))(file, sizeof(Elf64_Phdr) * e->e_phnum, ph) != - sizeof(Elf64_Phdr) * e->e_phnum) { - prom_printf ("Read error\n"); - return 0; - } - - /* Scan through the program header - * HACK: We must return the _memory size of the kernel image, not the - * file size (because we have to leave room before other boot - * infos. This code works as a side effect of the fact that - * we have one section and vaddr == p_paddr - */ - loadinfo->memsize = loadinfo->filesize = loadinfo->offset = 0; - p = ph; - for (i = 0; i < e->e_phnum; ++i, ++p) { - if (p->p_type != PT_LOAD || p->p_offset == 0) - continue; - if (loadinfo->memsize == 0) { - loadinfo->offset = p->p_offset; - loadinfo->memsize = p->p_memsz; - loadinfo->filesize = p->p_filesz; - loadinfo->load_loc = p->p_vaddr; - } else { - loadinfo->memsize = p->p_offset + p->p_memsz - loadinfo->offset; /* XXX Bogus */ - loadinfo->filesize = p->p_offset + p->p_filesz - loadinfo->offset; - } - } - - if (loadinfo->memsize == 0) { - prom_printf("Can't find a loadable segment !\n"); - return 0; - } - - /* leave some room (1Mb) for boot infos */ - loadinfo->memsize = _ALIGN(loadinfo->memsize,(1<<20)) + 0x100000; - /* Claim OF memory */ - DEBUG_F("Before prom_claim, mem_sz: 0x%08lx\n", loadinfo->memsize); - - /* On some systems, loadaddr may already be claimed, so try some - * other nearby addresses before giving up. - */ - loadaddr = (e->e_entry == KERNEL_LINK_ADDR_PPC64) ? KERNELADDR : e->e_entry; - for(addr=loadaddr; addr <= loadaddr * 8 ;addr+=0x100000) { - loadinfo->base = prom_claim((void *)addr, loadinfo->memsize, 0); - if (loadinfo->base != (void *)-1) break; - } - if (loadinfo->base == (void *)-1) { - prom_printf("Claim error, can't allocate kernel memory\n"); - return 0; - } - - DEBUG_F("After ELF parsing, load base: %p, mem_sz: 0x%08lx\n", - loadinfo->base, loadinfo->memsize); - DEBUG_F(" wanted load base: 0x%08lx, mem_sz: 0x%08lx\n", - loadaddr, loadinfo->memsize); - - /* Load the program segments... */ - p = ph; - for (i = 0; i < e->e_phnum; ++i, ++p) { - unsigned long offset; - if (p->p_type != PT_LOAD || p->p_offset == 0) - continue; - - /* Now, we skip to the image itself */ - if ((*(file->fs->seek))(file, p->p_offset) != FILE_ERR_OK) { - prom_printf ("Seek error\n"); - prom_release(loadinfo->base, loadinfo->memsize); - return 0; - } - offset = p->p_vaddr - loadinfo->load_loc; - if ((*(file->fs->read))(file, p->p_filesz, loadinfo->base+offset) != p->p_filesz) { - prom_printf ("Read failed\n"); - prom_release(loadinfo->base, loadinfo->memsize); - return 0; - } - } + int i; + Elf64_Ehdr *e = &(loadinfo->elf.elf64hdr); + Elf64_Phdr *p, *ph; + int size = sizeof(Elf64_Ehdr) - sizeof(Elf_Ident); + unsigned long addr, loadaddr; + + /* Read the rest of the Elf header... */ + if ((*(file->fs->read))(file, size, &e->e_version) < size) { + prom_printf("\nCan't read Elf64 image header\n"); + return 0; + } + + DEBUG_F("Elf64 header:\n"); + DEBUG_F(" e.e_type = %d\n", (int)e->e_type); + DEBUG_F(" e.e_machine = %d\n", (int)e->e_machine); + DEBUG_F(" e.e_version = %d\n", (int)e->e_version); + DEBUG_F(" e.e_entry = 0x%016lx\n", (long)e->e_entry); + DEBUG_F(" e.e_phoff = 0x%016lx\n", (long)e->e_phoff); + DEBUG_F(" e.e_shoff = 0x%016lx\n", (long)e->e_shoff); + DEBUG_F(" e.e_flags = %d\n", (int)e->e_flags); + DEBUG_F(" e.e_ehsize = 0x%08x\n", (int)e->e_ehsize); + DEBUG_F(" e.e_phentsize = 0x%08x\n", (int)e->e_phentsize); + DEBUG_F(" e.e_phnum = %d\n", (int)e->e_phnum); + + loadinfo->entry = e->e_entry; + + if (e->e_phnum > MAX_HEADERS) { + prom_printf ("Can only load kernels with one program header\n"); + return 0; + } - free(ph); + ph = (Elf64_Phdr *)malloc(sizeof(Elf64_Phdr) * e->e_phnum); + if (!ph) { + prom_printf ("Malloc error\n"); + return 0; + } + + /* Now, we read the section header */ + if ((*(file->fs->seek))(file, e->e_phoff) != FILE_ERR_OK) { + prom_printf ("Seek error\n"); + return 0; + } + if ((*(file->fs->read))(file, sizeof(Elf64_Phdr) * e->e_phnum, ph) != + sizeof(Elf64_Phdr) * e->e_phnum) { + prom_printf ("Read error\n"); + return 0; + } + + /* Scan through the program header + * HACK: We must return the _memory size of the kernel image, not the + * file size (because we have to leave room before other boot + * infos. This code works as a side effect of the fact that + * we have one section and vaddr == p_paddr + */ + loadinfo->memsize = loadinfo->filesize = loadinfo->offset = 0; + p = ph; + for (i = 0; i < e->e_phnum; ++i, ++p) { + if (p->p_type != PT_LOAD || p->p_offset == 0) + continue; + if (loadinfo->memsize == 0) { + loadinfo->offset = p->p_offset; + loadinfo->memsize = p->p_memsz; + loadinfo->filesize = p->p_filesz; + loadinfo->load_loc = p->p_vaddr; + } else { + loadinfo->memsize = p->p_offset + p->p_memsz - loadinfo->offset; /* XXX Bogus */ + loadinfo->filesize = p->p_offset + p->p_filesz - loadinfo->offset; + } + } + + if (loadinfo->memsize == 0) { + prom_printf("Can't find a loadable segment !\n"); + return 0; + } + + /* leave some room (1Mb) for boot infos */ + loadinfo->memsize = _ALIGN(loadinfo->memsize,(1<<20)) + 0x100000; + /* Claim OF memory */ + DEBUG_F("Before prom_claim, mem_sz: 0x%08lx\n", loadinfo->memsize); + + /* On some systems, loadaddr may already be claimed, so try some + * other nearby addresses before giving up. + */ + loadaddr = (e->e_entry == KERNEL_LINK_ADDR_PPC64) ? KERNELADDR : e->e_entry; + for(addr=loadaddr; addr <= loadaddr * 8 ;addr+=0x100000) { + loadinfo->base = prom_claim((void *)addr, loadinfo->memsize, 0); + if (loadinfo->base != (void *)-1) break; + } + if (loadinfo->base == (void *)-1) { + prom_printf("Claim error, can't allocate kernel memory\n"); + return 0; + } + + DEBUG_F("After ELF parsing, load base: %p, mem_sz: 0x%08lx\n", + loadinfo->base, loadinfo->memsize); + DEBUG_F(" wanted load base: 0x%08lx, mem_sz: 0x%08lx\n", + loadaddr, loadinfo->memsize); + + /* Load the program segments... */ + p = ph; + for (i = 0; i < e->e_phnum; ++i, ++p) { + unsigned long offset; + if (p->p_type != PT_LOAD || p->p_offset == 0) + continue; + + /* Now, we skip to the image itself */ + if ((*(file->fs->seek))(file, p->p_offset) != FILE_ERR_OK) { + prom_printf ("Seek error\n"); + prom_release(loadinfo->base, loadinfo->memsize); + return 0; + } + offset = p->p_vaddr - loadinfo->load_loc; + if ((*(file->fs->read))(file, p->p_filesz, loadinfo->base+offset) != p->p_filesz) { + prom_printf ("Read failed\n"); + prom_release(loadinfo->base, loadinfo->memsize); + return 0; + } + } + + free(ph); - /* Return success at loading the Elf64 kernel */ - return 1; + /* Return success at loading the Elf64 kernel */ + return 1; } static int is_elf32(loadinfo_t *loadinfo) { - Elf32_Ehdr *e = &(loadinfo->elf.elf32hdr); - - return (e->e_ident[EI_MAG0] == ELFMAG0 && - e->e_ident[EI_MAG1] == ELFMAG1 && - e->e_ident[EI_MAG2] == ELFMAG2 && - e->e_ident[EI_MAG3] == ELFMAG3 && - e->e_ident[EI_CLASS] == ELFCLASS32 && - e->e_ident[EI_DATA] == ELFDATA2MSB && - e->e_type == ET_EXEC && - e->e_machine == EM_PPC); + Elf32_Ehdr *e = &(loadinfo->elf.elf32hdr); + + return (e->e_ident[EI_MAG0] == ELFMAG0 && + e->e_ident[EI_MAG1] == ELFMAG1 && + e->e_ident[EI_MAG2] == ELFMAG2 && + e->e_ident[EI_MAG3] == ELFMAG3 && + e->e_ident[EI_CLASS] == ELFCLASS32 && + e->e_ident[EI_DATA] == ELFDATA2MSB && + e->e_type == ET_EXEC && + e->e_machine == EM_PPC); } static int is_elf64(loadinfo_t *loadinfo) { - Elf64_Ehdr *e = &(loadinfo->elf.elf64hdr); - - return (e->e_ident[EI_MAG0] == ELFMAG0 && - e->e_ident[EI_MAG1] == ELFMAG1 && - e->e_ident[EI_MAG2] == ELFMAG2 && - e->e_ident[EI_MAG3] == ELFMAG3 && - e->e_ident[EI_CLASS] == ELFCLASS64 && - e->e_ident[EI_DATA] == ELFDATA2MSB && - e->e_type == ET_EXEC && - e->e_machine == EM_PPC64); + Elf64_Ehdr *e = &(loadinfo->elf.elf64hdr); + + return (e->e_ident[EI_MAG0] == ELFMAG0 && + e->e_ident[EI_MAG1] == ELFMAG1 && + e->e_ident[EI_MAG2] == ELFMAG2 && + e->e_ident[EI_MAG3] == ELFMAG3 && + e->e_ident[EI_CLASS] == ELFCLASS64 && + e->e_ident[EI_DATA] == ELFDATA2MSB && + e->e_type == ET_EXEC && + e->e_machine == EM_PPC64); } static void setup_display(void) { #ifdef CONFIG_SET_COLORMAP - static unsigned char default_colors[] = { - 0x00, 0x00, 0x00, - 0x00, 0x00, 0xaa, - 0x00, 0xaa, 0x00, - 0x00, 0xaa, 0xaa, - 0xaa, 0x00, 0x00, - 0xaa, 0x00, 0xaa, - 0xaa, 0x55, 0x00, - 0xaa, 0xaa, 0xaa, - 0x55, 0x55, 0x55, - 0x55, 0x55, 0xff, - 0x55, 0xff, 0x55, - 0x55, 0xff, 0xff, - 0xff, 0x55, 0x55, - 0xff, 0x55, 0xff, - 0xff, 0xff, 0x55, - 0xff, 0xff, 0xff - }; - int i, result; - prom_handle scrn = PROM_INVALID_HANDLE; - - /* Try Apple's mac-boot screen ihandle */ - result = (int)call_prom_return("interpret", 1, 2, - "\" _screen-ihandle\" $find if execute else 0 then", &scrn); - DEBUG_F("Trying to get screen ihandle, result: %d, scrn: %p\n", result, scrn); - - if (scrn == 0 || scrn == PROM_INVALID_HANDLE) { - char type[32]; - /* Hrm... check to see if stdout is a display */ - scrn = call_prom ("instance-to-package", 1, 1, prom_stdout); - DEBUG_F("instance-to-package of stdout is: %p\n", scrn); - if (prom_getprop(scrn, "device_type", type, 32) > 0 && !strncmp(type, "display", 7)) { - DEBUG_F("got it ! stdout is a screen\n"); - scrn = prom_stdout; - } else { - /* Else, we try to open the package */ - scrn = (prom_handle)call_prom( "open", 1, 1, "screen" ); - DEBUG_F("Open screen result: %p\n", scrn); - } - } + static unsigned char default_colors[] = { + 0x00, 0x00, 0x00, + 0x00, 0x00, 0xaa, + 0x00, 0xaa, 0x00, + 0x00, 0xaa, 0xaa, + 0xaa, 0x00, 0x00, + 0xaa, 0x00, 0xaa, + 0xaa, 0x55, 0x00, + 0xaa, 0xaa, 0xaa, + 0x55, 0x55, 0x55, + 0x55, 0x55, 0xff, + 0x55, 0xff, 0x55, + 0x55, 0xff, 0xff, + 0xff, 0x55, 0x55, + 0xff, 0x55, 0xff, + 0xff, 0xff, 0x55, + 0xff, 0xff, 0xff + }; + int i, result; + prom_handle scrn = PROM_INVALID_HANDLE; + + /* Try Apple's mac-boot screen ihandle */ + result = (int)call_prom_return("interpret", 1, 2, + "\" _screen-ihandle\" $find if execute else 0 then", &scrn); + DEBUG_F("Trying to get screen ihandle, result: %d, scrn: %p\n", result, scrn); + + if (scrn == 0 || scrn == PROM_INVALID_HANDLE) { + char type[32]; + /* Hrm... check to see if stdout is a display */ + scrn = call_prom ("instance-to-package", 1, 1, prom_stdout); + DEBUG_F("instance-to-package of stdout is: %p\n", scrn); + if (prom_getprop(scrn, "device_type", type, 32) > 0 && !strncmp(type, "display", 7)) { + DEBUG_F("got it ! stdout is a screen\n"); + scrn = prom_stdout; + } else { + /* Else, we try to open the package */ + scrn = (prom_handle)call_prom( "open", 1, 1, "screen" ); + DEBUG_F("Open screen result: %p\n", scrn); + } + } - if (scrn == PROM_INVALID_HANDLE) { - prom_printf("No screen device found !/n"); - return; - } - for(i=0;i<16;i++) { - prom_set_color(scrn, i, default_colors[i*3], - default_colors[i*3+1], default_colors[i*3+2]); - } - prom_printf("\x1b[1;37m\x1b[2;40m"); + if (scrn == PROM_INVALID_HANDLE) { + prom_printf("No screen device found !/n"); + return; + } + for(i=0;i<16;i++) { + prom_set_color(scrn, i, default_colors[i*3], + default_colors[i*3+1], default_colors[i*3+2]); + } + prom_printf("\x1b[1;37m\x1b[2;40m"); #ifdef COLOR_TEST - for (i=0;i<16; i++) { - prom_printf("\x1b[%d;%dm\x1b[1;47m%s \x1b[2;40m %s\n", - ansi_color_table[i].index, - ansi_color_table[i].value, - ansi_color_table[i].name, - ansi_color_table[i].name); - prom_printf("\x1b[%d;%dm\x1b[1;37m%s \x1b[2;30m %s\n", - ansi_color_table[i].index, - ansi_color_table[i].value+10, - ansi_color_table[i].name, - ansi_color_table[i].name); - } - prom_printf("\x1b[1;37m\x1b[2;40m"); + for (i=0;i<16; i++) { + prom_printf("\x1b[%d;%dm\x1b[1;47m%s \x1b[2;40m %s\n", + ansi_color_table[i].index, + ansi_color_table[i].value, + ansi_color_table[i].name, + ansi_color_table[i].name); + prom_printf("\x1b[%d;%dm\x1b[1;37m%s \x1b[2;30m %s\n", + ansi_color_table[i].index, + ansi_color_table[i].value+10, + ansi_color_table[i].name, + ansi_color_table[i].name); + } + prom_printf("\x1b[1;37m\x1b[2;40m"); #endif /* COLOR_TEST */ #if !DEBUG - prom_printf("\xc"); + prom_printf("\xc"); #endif /* !DEBUG */ #endif /* CONFIG_SET_COLORMAP */ diff --git a/util/addnote.c b/util/addnote.c index 74c8efc..1ae1636 100644 --- a/util/addnote.c +++ b/util/addnote.c @@ -13,6 +13,7 @@ * * Usage: addnote zImage */ + #include #include #include @@ -22,12 +23,12 @@ char arch[] = "PowerPC"; #define N_DESCR 6 unsigned int descr[N_DESCR] = { - 0xffffffff, /* real-mode = true */ - 0x00c00000, /* real-base, i.e. where we expect OF to be */ - 0xffffffff, /* real-size */ - 0xffffffff, /* virt-base */ - 0xffffffff, /* virt-size */ - 0x4000, /* load-base */ + 0xffffffff, /* real-mode = true */ + 0x00c00000, /* real-base, i.e. where we expect OF to be */ + 0xffffffff, /* real-size */ + 0xffffffff, /* virt-base */ + 0xffffffff, /* virt-size */ + 0x4000, /* load-base */ }; unsigned char buf[512]; @@ -65,99 +66,106 @@ unsigned char elf_magic[4] = { 0x7f, 'E', 'L', 'F' }; int main(int ac, char **av) { - int fd, n, i; - int ph, ps, np; - int nnote, ns; - - if (ac != 2) { - fprintf(stderr, "Usage: %s elf-file\n", av[0]); - exit(1); - } - fd = open(av[1], O_RDWR); - if (fd < 0) { - perror(av[1]); - exit(1); - } - - nnote = strlen(arch) + 1 + (N_DESCR + 3) * 4; - - n = read(fd, buf, sizeof(buf)); - if (n < 0) { - perror("read"); - exit(1); - } - - if (n < E_HSIZE || memcmp(&buf[E_IDENT+EI_MAGIC], elf_magic, 4) != 0) - goto notelf; - - if (buf[E_IDENT+EI_CLASS] != ELFCLASS32 - || buf[E_IDENT+EI_DATA] != ELFDATA2MSB) { - fprintf(stderr, "%s is not a big-endian 32-bit ELF image\n", - av[1]); - exit(1); - } - - ph = GET_32BE(E_PHOFF); - ps = GET_16BE(E_PHENTSIZE); - np = GET_16BE(E_PHNUM); - if (ph < E_HSIZE || ps < PH_HSIZE || np < 1) - goto notelf; - if (ph + (np + 1) * ps + nnote > n) - goto nospace; - - for (i = 0; i < np; ++i) { - if (GET_32BE(ph + PH_TYPE) == PT_NOTE) { - fprintf(stderr, "%s already has a note entry\n", - av[1]); - exit(0); - } - ph += ps; - } - - /* XXX check that the area we want to use is all zeroes */ - for (i = 0; i < ps + nnote; ++i) - if (buf[ph + i] != 0) - goto nospace; - - /* fill in the program header entry */ - ns = ph + ps; - PUT_32BE(ph + PH_TYPE, PT_NOTE); - PUT_32BE(ph + PH_OFFSET, ns); - PUT_32BE(ph + PH_FILESZ, nnote); - - /* fill in the note area we point to */ - /* XXX we should probably make this a proper section */ - PUT_32BE(ns, strlen(arch) + 1); - PUT_32BE(ns + 4, N_DESCR * 4); - PUT_32BE(ns + 8, 0x1275); - strcpy(&buf[ns + 12], arch); - ns += 12 + strlen(arch) + 1; - for (i = 0; i < N_DESCR; ++i) - PUT_32BE(ns + i * 4, descr[i]); - - /* Update the number of program headers */ - PUT_16BE(E_PHNUM, np + 1); - - /* write back */ - lseek(fd, (long) 0, SEEK_SET); - i = write(fd, buf, n); - if (i < 0) { - perror("write"); - exit(1); - } - if (i < n) { - fprintf(stderr, "%s: write truncated\n", av[1]); - exit(1); - } - - exit(0); - - notelf: - fprintf(stderr, "%s does not appear to be an ELF file\n", av[1]); - exit(1); - - nospace: - fprintf(stderr, "sorry, I can't find space in %s to put the note\n", - av[1]); - exit(1); + int fd, n, i; + int ph, ps, np; + int nnote, ns; + + if (ac != 2) { + fprintf(stderr, "Usage: %s elf-file\n", av[0]); + exit(1); + } + fd = open(av[1], O_RDWR); + if (fd < 0) { + perror(av[1]); + exit(1); + } + + nnote = strlen(arch) + 1 + (N_DESCR + 3) * 4; + + n = read(fd, buf, sizeof(buf)); + if (n < 0) { + perror("read"); + exit(1); + } + + if (n < E_HSIZE || memcmp(&buf[E_IDENT+EI_MAGIC], elf_magic, 4) != 0) + goto notelf; + + if (buf[E_IDENT+EI_CLASS] != ELFCLASS32 + || buf[E_IDENT+EI_DATA] != ELFDATA2MSB) { + fprintf(stderr, "%s is not a big-endian 32-bit ELF image\n", + av[1]); + exit(1); + } + + ph = GET_32BE(E_PHOFF); + ps = GET_16BE(E_PHENTSIZE); + np = GET_16BE(E_PHNUM); + if (ph < E_HSIZE || ps < PH_HSIZE || np < 1) + goto notelf; + if (ph + (np + 1) * ps + nnote > n) + goto nospace; + + for (i = 0; i < np; ++i) { + if (GET_32BE(ph + PH_TYPE) == PT_NOTE) { + fprintf(stderr, "%s already has a note entry\n", + av[1]); + exit(0); + } + ph += ps; + } + + /* XXX check that the area we want to use is all zeroes */ + for (i = 0; i < ps + nnote; ++i) + if (buf[ph + i] != 0) + goto nospace; + + /* fill in the program header entry */ + ns = ph + ps; + PUT_32BE(ph + PH_TYPE, PT_NOTE); + PUT_32BE(ph + PH_OFFSET, ns); + PUT_32BE(ph + PH_FILESZ, nnote); + + /* fill in the note area we point to */ + /* XXX we should probably make this a proper section */ + PUT_32BE(ns, strlen(arch) + 1); + PUT_32BE(ns + 4, N_DESCR * 4); + PUT_32BE(ns + 8, 0x1275); + strcpy(&buf[ns + 12], arch); + ns += 12 + strlen(arch) + 1; + for (i = 0; i < N_DESCR; ++i) + PUT_32BE(ns + i * 4, descr[i]); + + /* Update the number of program headers */ + PUT_16BE(E_PHNUM, np + 1); + + /* write back */ + lseek(fd, (long) 0, SEEK_SET); + i = write(fd, buf, n); + if (i < 0) { + perror("write"); + exit(1); + } + if (i < n) { + fprintf(stderr, "%s: write truncated\n", av[1]); + exit(1); + } + + exit(0); + +notelf: + fprintf(stderr, "%s does not appear to be an ELF file\n", av[1]); + exit(1); + +nospace: + fprintf(stderr, "sorry, I can't find space in %s to put the note\n", + av[1]); + exit(1); } + +/* + * Local variables: + * c-file-style: "K&R" + * c-basic-offset: 5 + * End: + */ diff --git a/ybin/ybin b/ybin/ybin index 424acc8..241d241 100755 --- a/ybin/ybin +++ b/ybin/ybin @@ -28,7 +28,7 @@ if [ -n "$PATH_PREFIX" ] ; then fi PRG="${0##*/}" SIGINT="$PRG: Interrupt caught ... exiting" -VERSION=1.3.4pre3 +VERSION=1.3.4 DEBUG=0 VERBOSE=0 TMP="${TMPDIR:-/tmp}"