470 lines
12 KiB
C
470 lines
12 KiB
C
/*++
|
|
|
|
Copyright (c) 1994-1996 Microsoft Corporation
|
|
|
|
Module Name:
|
|
|
|
setnvram.c
|
|
|
|
Abstract:
|
|
|
|
This program is an example of how you could use a text file to create
|
|
input for nvram.exe.
|
|
|
|
Author:
|
|
|
|
Chuck Lenzmeier (chuckl)
|
|
|
|
Revision History:
|
|
|
|
--*/
|
|
|
|
//
|
|
// setnvram.c
|
|
//
|
|
// This program is an example of
|
|
|
|
#define _DLL 1
|
|
#include <stdio.h>
|
|
#include <stdlib.h>
|
|
#include <string.h>
|
|
|
|
#define SEPARATOR "|"
|
|
|
|
#define MAXLINESIZE 256
|
|
|
|
#define FALSE 0
|
|
#define TRUE 1
|
|
|
|
char Line[MAXLINESIZE];
|
|
|
|
char Countdown[MAXLINESIZE];
|
|
|
|
char LoadIdentifier[MAXLINESIZE];
|
|
char SystemPartition[MAXLINESIZE];
|
|
char OsLoader[MAXLINESIZE];
|
|
char OsLoadPartition[MAXLINESIZE];
|
|
char OsLoadFilename[MAXLINESIZE];
|
|
char OsLoadOptions[MAXLINESIZE];
|
|
|
|
char DefaultSystemPartition[MAXLINESIZE];
|
|
char DefaultOsLoadPartition[MAXLINESIZE];
|
|
char DefaultOsLoadOptions[MAXLINESIZE];
|
|
|
|
char *
|
|
Trim (
|
|
char *String
|
|
)
|
|
{
|
|
char *start;
|
|
char *end;
|
|
|
|
start = String;
|
|
while ( (*start == ' ') || (*start == '\t') ) {
|
|
start++;
|
|
}
|
|
|
|
end = strrchr( start, 0 ) - 1;
|
|
if ( (end > start) && ((*end == ' ') || (*end == '\t')) ) {
|
|
do {
|
|
end--;
|
|
} while ( (*end == ' ') || (*end == '\t') );
|
|
end++;
|
|
*end = 0;
|
|
}
|
|
|
|
return start;
|
|
}
|
|
|
|
int
|
|
ParsePartition (
|
|
char *String,
|
|
char *Partition
|
|
)
|
|
{
|
|
char buffer[MAXLINESIZE];
|
|
char *multi;
|
|
char *scsi;
|
|
char *disk;
|
|
char *part;
|
|
char *dot;
|
|
|
|
strcpy( buffer, String );
|
|
|
|
if ( _strnicmp(buffer, "scsi.", 5) != 0 ) {
|
|
return FALSE;
|
|
}
|
|
multi = "0";
|
|
scsi = "0";
|
|
disk = &buffer[5];
|
|
dot = strchr( disk, '.' );
|
|
if ( dot == NULL ) {
|
|
return FALSE;
|
|
}
|
|
*dot = 0;
|
|
part = dot + 1;
|
|
dot = strchr( part, '.' );
|
|
if ( dot != NULL ) {
|
|
scsi = disk;
|
|
disk = part;
|
|
*dot = 0;
|
|
part = dot + 1;
|
|
dot = strchr( part, '.' );
|
|
if ( dot != NULL ) {
|
|
multi = scsi;
|
|
scsi = disk;
|
|
disk = part;
|
|
*dot = 0;
|
|
part = dot + 1;
|
|
}
|
|
}
|
|
|
|
#if !defined(_PPC_)
|
|
strcpy( Partition, "scsi()disk(" );
|
|
#else
|
|
strcpy( Partition, "multi(" );
|
|
strcat( Partition, multi );
|
|
strcat( Partition, ")scsi(" );
|
|
strcat( Partition, scsi );
|
|
strcat( Partition, ")disk(" );
|
|
#endif
|
|
strcat( Partition, disk );
|
|
#if !defined(_PPC_)
|
|
strcat( Partition, ")rdisk()partition(" );
|
|
#else
|
|
strcat( Partition, ")rdisk(0)partition(" );
|
|
#endif
|
|
strcat( Partition, part );
|
|
strcat( Partition, ")" );
|
|
|
|
return TRUE;
|
|
}
|
|
|
|
int
|
|
main (
|
|
int argc,
|
|
char *argv[]
|
|
)
|
|
{
|
|
FILE *file = stdin;
|
|
|
|
char *build;
|
|
int len;
|
|
int linenum;
|
|
|
|
char *ident;
|
|
char *token;
|
|
char *sysdir;
|
|
char *osdir;
|
|
char *options;
|
|
char *syspart;
|
|
char *ospart;
|
|
char *loader;
|
|
|
|
char options1[MAXLINESIZE];
|
|
char syspart1[MAXLINESIZE];
|
|
char ospart1[MAXLINESIZE];
|
|
|
|
if ( argc > 1 ) {
|
|
#if 1
|
|
if ( argc > 2 ) {
|
|
#endif
|
|
fprintf( stderr, "This program accepts no arguments\n" );
|
|
fprintf( stderr, "Redirect stdin to build data file\n" );
|
|
fprintf( stderr, "Redirect stdout to nvram.exe input file\n" );
|
|
return 1;
|
|
#if 1
|
|
} else {
|
|
file = fopen( argv[1], "r" );
|
|
if ( file == NULL ) {
|
|
fprintf( stderr, "Can't open input file %s\n", argv[1] );
|
|
return 1;
|
|
}
|
|
}
|
|
#endif
|
|
}
|
|
|
|
Countdown[0] = 0;
|
|
|
|
LoadIdentifier[0] = 0;
|
|
SystemPartition[0] = 0;
|
|
OsLoader[0] = 0;
|
|
OsLoadPartition[0] = 0;
|
|
OsLoadFilename[0] = 0;
|
|
OsLoadOptions[0] = 0;
|
|
|
|
DefaultOsLoadOptions[0] = 0;
|
|
DefaultOsLoadPartition[0] = 0;
|
|
DefaultSystemPartition[0] = 0;
|
|
|
|
linenum = 0;
|
|
|
|
while ( TRUE ) {
|
|
|
|
//
|
|
// Get the next line from the input stream.
|
|
//
|
|
|
|
linenum++;
|
|
|
|
build = fgets( Line, MAXLINESIZE, file );
|
|
if ( build == NULL ) {
|
|
if ( feof(file) ) break;
|
|
fprintf( stderr, "Error %d reading input at line %d\n", ferror(file), linenum );
|
|
return ferror(file);
|
|
}
|
|
|
|
build = Trim( build );
|
|
len = strlen( build );
|
|
|
|
//
|
|
// Ignore blank lines and lines that start with //.
|
|
//
|
|
|
|
if ( len == 0 ) continue;
|
|
if ( (build[0] == '/') && (build[1] == '/') ) continue;
|
|
if ( build[len-1] != '\n' ) {
|
|
fprintf( stderr, "Line %d is too long; %d characters max\n", linenum, MAXLINESIZE-2 );
|
|
return 1;
|
|
}
|
|
if ( len == 1 ) continue;
|
|
build[len-1] = 0;
|
|
|
|
//
|
|
// Check for the special "countdown" line. If found, save the countdown value.
|
|
//
|
|
|
|
if ( strstr(build,"countdown=") == build ) {
|
|
strcpy( Countdown, strchr(build,'=') + 1 );
|
|
continue;
|
|
}
|
|
|
|
//
|
|
// Check for the special "default systempartition" line. If found, save the
|
|
// default string.
|
|
//
|
|
|
|
if ( strstr(build,"default systempartition=") == build ) {
|
|
strcpy( DefaultSystemPartition, Trim( strchr(build,'=') + 1 ) );
|
|
continue;
|
|
}
|
|
|
|
//
|
|
// Check for the special "default osloadpartition" line. If found, save the
|
|
// default string.
|
|
//
|
|
|
|
if ( strstr(build,"default osloadpartition=") == build ) {
|
|
strcpy( DefaultOsLoadPartition, Trim( strchr(build,'=') + 1 ) );
|
|
continue;
|
|
}
|
|
|
|
//
|
|
// Check for the special "default options" line. If found, save the
|
|
// default string.
|
|
//
|
|
|
|
if ( strstr(build,"default options=") == build ) {
|
|
strcpy( DefaultOsLoadOptions, Trim( strchr(build,'=') + 1 ) );
|
|
strcat( DefaultOsLoadOptions, " " );
|
|
continue;
|
|
}
|
|
|
|
//
|
|
// OK, we should have an OS load line. Required format is:
|
|
//
|
|
// <ident>[|<sys-dir>][|<os-dir>][<dir>][|<options>][|<sys-part>][|<os-part>][|<loader>]
|
|
//
|
|
// Everything after <ident> is optional and may be specified in any order.
|
|
//
|
|
// <sys-dir> defines the directory path to the osloader/hal directory.
|
|
// <os-dir> defines the directory path to the OS directory.
|
|
// The default value for both of these fields is <ident>.
|
|
// <dir> sets both <sys-dir> and <os-dir>.
|
|
//
|
|
// <sys-part> and <os-part> are optional only if the corresponding defaults
|
|
// have been specified.
|
|
//
|
|
// <loader> is used to override the selection of osloader.exe as the OS loader.
|
|
//
|
|
// <sys-dir> format is sysdir=<directory path (no leading \)>
|
|
// <os-dir> format is osdir=<directory path (no leading \)>
|
|
// <dir> format is dir=<directory path (no leading \)>
|
|
// <options> format is options=<text of options>
|
|
// <sys-part> format is syspart=<partition specification>
|
|
// <os-part> format is ospart=<partition specification>
|
|
// <loader> format is loader=<filename>
|
|
//
|
|
|
|
//
|
|
// Get the load-identifier.
|
|
//
|
|
|
|
ident = Trim( strtok( build, SEPARATOR ) );
|
|
|
|
//
|
|
// Set defaults for optional fields.
|
|
//
|
|
|
|
osdir = ident;
|
|
sysdir = ident;
|
|
options = DefaultOsLoadOptions;
|
|
syspart = DefaultSystemPartition;
|
|
ospart = DefaultOsLoadPartition;
|
|
loader = "osloader.exe";
|
|
|
|
//
|
|
// Get optional fields.
|
|
//
|
|
|
|
while ( (token = strtok( NULL, SEPARATOR )) != NULL ) {
|
|
|
|
token = Trim( token );
|
|
|
|
if ( strstr(token,"sysdir=") == token ) {
|
|
|
|
sysdir = Trim( strchr(token,'=') + 1 );
|
|
|
|
} else if ( strstr(token,"osdir=") == token ) {
|
|
|
|
osdir = Trim( strchr(token,'=') + 1 );
|
|
|
|
} else if ( strstr(token,"dir=") == token ) {
|
|
|
|
sysdir = Trim( strchr(token,'=') + 1 );
|
|
osdir = sysdir;
|
|
|
|
} else if ( strstr(token,"options=") == token ) {
|
|
|
|
//
|
|
// If the options do not start with "nodef", preface the
|
|
// default options (if any) to the specified options.
|
|
//
|
|
|
|
options = Trim( strchr(token,'=') + 1 );
|
|
if ( _strnicmp(options,"nodef",5) == 0 ) {
|
|
options = options+5;
|
|
} else {
|
|
strcpy( options1, DefaultOsLoadOptions );
|
|
strcat( options1, options );
|
|
options = options1;
|
|
}
|
|
|
|
} else if ( strstr(token,"syspart=") == token ) {
|
|
|
|
syspart = Trim( strchr(token,'=') + 1 );
|
|
|
|
} else if ( strstr(token,"ospart=") == token ) {
|
|
|
|
ospart = Trim( strchr(token,'=') + 1 );
|
|
|
|
} else if ( strstr(token,"loader=") == token ) {
|
|
|
|
loader = Trim( strchr(token,'=') + 1 );
|
|
|
|
} else {
|
|
|
|
//
|
|
// Unrecognized optional field.
|
|
//
|
|
|
|
fprintf( stderr, "Unreconized optional field at line %d\n", linenum );
|
|
return 1;
|
|
|
|
}
|
|
|
|
} // while
|
|
|
|
//
|
|
// Verify the validity of the input fields.
|
|
//
|
|
|
|
if ( strlen(ident) == 0 ) {
|
|
fprintf( stderr, "Bad <load-identifier> at line %d\n", linenum );
|
|
return 1;
|
|
}
|
|
if ( strlen(sysdir) == 0 ) {
|
|
fprintf( stderr, "Bad <system-directory> at line %d\n", linenum );
|
|
return 1;
|
|
}
|
|
if ( strlen(osdir) == 0 ) {
|
|
fprintf( stderr, "Bad <os-directory> at line %d\n", linenum );
|
|
return 1;
|
|
}
|
|
if ( strlen(syspart) == 0 ) {
|
|
fprintf( stderr, "Missing <system-partition> (no default) at line %d\n", linenum );
|
|
return 1;
|
|
}
|
|
if ( strlen(ospart) == 0 ) {
|
|
fprintf( stderr, "Missing <os-partition> (no default) at line %d\n", linenum );
|
|
return 1;
|
|
}
|
|
if ( !ParsePartition(syspart, syspart1) ) {
|
|
fprintf( stderr, "Bad <system-partition> at line %d\n", linenum );
|
|
return 1;
|
|
}
|
|
if ( !ParsePartition(ospart, ospart1) ) {
|
|
fprintf( stderr, "Bad <os-partition> at line %d\n", linenum );
|
|
return 1;
|
|
}
|
|
if ( strlen(loader) == 0 ) {
|
|
fprintf( stderr, "Bad <loader> at line %d\n", linenum );
|
|
return 1;
|
|
}
|
|
|
|
//
|
|
// If this is not the first load line, append ';' to all of the NVRAM strings.
|
|
//
|
|
|
|
if ( strlen(LoadIdentifier) != 0 ) {
|
|
strcat( LoadIdentifier, ";" );
|
|
strcat( SystemPartition, ";" );
|
|
strcat( OsLoader, ";" );
|
|
strcat( OsLoadPartition, ";" );
|
|
strcat( OsLoadFilename, ";" );
|
|
strcat( OsLoadOptions, ";" );
|
|
}
|
|
|
|
//
|
|
// Append this load line to the NVRAM strings.
|
|
//
|
|
|
|
strcat( LoadIdentifier, ident );
|
|
|
|
strcat( SystemPartition, syspart1 );
|
|
|
|
strcat( OsLoader, syspart1 );
|
|
if ( loader[0] != '\\' ) {
|
|
strcat( OsLoader, "\\" );
|
|
strcat( OsLoader, sysdir );
|
|
strcat( OsLoader, "\\" );
|
|
}
|
|
strcat( OsLoader, loader );
|
|
|
|
strcat( OsLoadPartition, ospart1 );
|
|
|
|
strcat( OsLoadFilename, "\\" );
|
|
strcat( OsLoadFilename, osdir );
|
|
|
|
strcat( OsLoadOptions, options );
|
|
Trim( OsLoadOptions );
|
|
|
|
}
|
|
|
|
//
|
|
// Write the necessary nvram.exe commands to the output stream.
|
|
//
|
|
|
|
if ( Countdown[0] != 0 ) {
|
|
fprintf( stdout, "nvram /set COUNTDOWN = \"%s\"\n", Countdown );
|
|
}
|
|
fprintf( stdout, "nvram /set LOADIDENTIFIER = \"%s\"\n", LoadIdentifier );
|
|
fprintf( stdout, "nvram /set SYSTEMPARTITION = \"%s\"\n", SystemPartition );
|
|
fprintf( stdout, "nvram /set OSLOADER = \"%s\"\n", OsLoader );
|
|
fprintf( stdout, "nvram /set OSLOADPARTITION = \"%s\"\n", OsLoadPartition );
|
|
fprintf( stdout, "nvram /set OSLOADFILENAME = \"%s\"\n", OsLoadFilename );
|
|
fprintf( stdout, "nvram /set OSLOADOPTIONS = \"%s\"\n", OsLoadOptions );
|
|
|
|
return 0;
|
|
}
|