* Marc Singer <[EMAIL PROTECTED]> [2006-07-28 18:06]:
> So, what exactly do you want it to be able to do?

Sorry for the delay.  Thank you for working on this - I've played with
it now and it's working great.

> What I'm thinking is that we should be a little more explicit about
> what we're doing.
>   1) We *must* put the second stage, whatever it is, at the same
>      address in flash, 0x60000.

Yes, that's right.  In addition to this requirement, it seems that the
FIS entry at 0x60000 has to be 8 blocks in size.  I tried putting APEX
there as a "Loader" partition with 1 block and then RedBoot crashes
while loading it:

copy kernel code from flash to RAM
copy ramdisk file from flash to RAM
$T0a0f:00020650;0d:0003ddc0;#a4

However, it works after changing the size to 8 blocks.

Given that the loader/APEX partition has to be 8 blocks (1048576
bytes), it might be a good idea to put the APEX environment in there
as well.

>   2) We would like to be able to add a partition for the second stage
>      loader, in this case APEX.
> 
> I can see that we need or may need the following:
> 
>   1) A new option, -L | --loader to add a second stage loader.

Yes, I've implemented this now and have successfully flashed an image
with APEX, Linux and a ramdisk.  I've attached the patch.

Rod, can you please review the patch.
Mark, what do you think of moving the APEX environment?

Anything else?

-- 
Martin Michlmayr
http://www.cyrius.com/
--- slugimage~  2006-08-04 22:52:24.000000000 +0200
+++ slugimage   2006-08-05 00:34:09.000000000 +0200
@@ -725,9 +725,11 @@
     } @partitions;
 }
 
-sub defaultPartitions {
+sub defaultPartitions($) {
+    my($loader) = @_;
 
-    return ({'name'=>'RedBoot',           'file'=>'RedBoot',
+    my @partitions =
+           ({'name'=>'RedBoot',           'file'=>'RedBoot',
             'offset'=>0x00000000,        'size'=>0x00040000,
             'variable'=>0, 'header'=>0,  'pseudo'=>0, 'data'=>undef, 
'byteswap'=>0},
            {'name'=>'EthAddr',           'file'=>undef,
@@ -735,12 +737,22 @@
             'variable'=>0, 'header'=>0,  'pseudo'=>1, 'data'=>undef, 
'byteswap'=>0},
            {'name'=>'SysConf',           'file'=>'SysConf',
             'offset'=>0x00040000,        'size'=>0x00020000,
-            'variable'=>0, 'header'=>0,  'pseudo'=>0, 'data'=>undef, 
'byteswap'=>0},
-           {'name'=>'Kernel',            'file'=>'vmlinuz',
-            'offset'=>0x00060000,        'size'=>0x00100000,
-            'variable'=>0, 'header'=>16, 'pseudo'=>0, 'data'=>undef, 
'byteswap'=>0},
+            'variable'=>0, 'header'=>0,  'pseudo'=>0, 'data'=>undef, 
'byteswap'=>0});
+
+    my $loader_size = 0;
+    if ($loader) {
+       $loader_size = 0x00100000;
+       push @partitions,
+           ({'name'=>'Loader',           'file'=>'loader',
+            'offset'=>0x00060000,        'size'=>$loader_size,
+            'variable'=>0, 'header'=>16, 'pseudo'=>0, 'data'=>undef, 
'byteswap'=>0});
+    }
+
+    push @partitions,
+           ({'name'=>'Kernel',            'file'=>'vmlinuz',
+            'offset'=>(0x00060000+$loader_size),
+            'variable'=>1, 'header'=>16, 'pseudo'=>0, 'data'=>undef, 
'byteswap'=>0},
            {'name'=>'Ramdisk',           'file'=>'ramdisk.gz',
-            'offset'=>0x00160000,        'size'=>0x006a0000,
             'variable'=>1, 'header'=>16, 'pseudo'=>0, 'data'=>undef, 
'byteswap'=>0},
            {'name'=>'FIS directory',     'file'=>undef,
             'offset'=>0x007e0000,        'size'=>0x00020000,
@@ -750,16 +762,13 @@
             'variable'=>1, 'header'=>16, 'pseudo'=>1, 'data'=>undef, 
'byteswap'=>0},
            {'name'=>'Trailer',           'file'=>'Trailer',
             'offset'=>0x007ffff0,        'size'=>0x00000010,
-            'variable'=>0, 'header'=>0,  'pseudo'=>1, 'data'=>undef, 
'byteswap'=>0},
-           );
-
+            'variable'=>0, 'header'=>0,  'pseudo'=>1, 'data'=>undef, 
'byteswap'=>0});
+       return @partitions;
 }
 
 # Main routine starts here ...
 
-my(@partitions) = defaultPartitions();
-
-my($unpack, $pack, $little, $input, $output, $redboot, $kernel, $sysconf, 
$ramdisk, $fisdir, $payload, $trailer, $ethaddr);
+my($unpack, $pack, $little, $input, $output, $redboot, $kernel, $sysconf, 
$ramdisk, $fisdir, $payload, $trailer, $ethaddr, $loader);
 my (@cleanup);
 
 END {
@@ -784,6 +793,7 @@
                "y|payload=s"  => \$payload,
                "t|trailer=s"  => \$trailer,
                "e|ethaddr=s"  => \$ethaddr,
+               "L|loader=s"   => \$loader,
                ) or (not defined $pack and not defined $unpack)) {
     print "Usage: slugimage <options>\n";
     print "\n";
@@ -801,6 +811,7 @@
     print "  [-f|--fisdir]   <file>            Input/Output FIS directory 
filename\n";
     print "  [-y|--payload]  <file>            Input/Output Payload 
filename\n";
     print "  [-t|--trailer]  <file>            Input/Output Trailer 
filename\n";
+    print "  [-L|--loader]   <file>            Second stage boot loader 
filename\n";
     print "  [-e|--ethaddr]  <AABBCCDDEEFF>    Set the Ethernet address\n";
 
     # TODO: document --ramdisk syntax
@@ -808,6 +819,19 @@
     exit 1;
 }
 
+my(@partitions) = defaultPartitions($loader);
+# If we don't use our own second stage boot loader, we need to follow the
+# layout assumed by the NSLU2 firmware.
+if (!$loader) {
+    map { ($_->{'name'} eq 'Kernel') && ($_->{'offset'} = 0x00060000);  } 
@partitions;
+    map { ($_->{'name'} eq 'Kernel') && ($_->{'size'} = 0x00100000);  } 
@partitions;
+    map { ($_->{'name'} eq 'Ramdisk') && ($_->{'offset'} = 0x00160000);  } 
@partitions;
+    map { ($_->{'name'} eq 'Ramdisk') && ($_->{'size'} = 0x006a0000);  } 
@partitions;
+    if ($pack) {
+       map { ($_->{'name'} eq 'Kernel') && ($_->{'variable'} = 0);  } 
@partitions;
+    }
+}
+
 if ($pack) {
     die "Output filename must be specified\n" unless defined $output;
 
@@ -849,6 +873,7 @@
 
 # Go through the partition options, and set the names and files in @partitions
 if (defined $redboot) { map { ($_->{'name'} eq 'RedBoot')      && 
($_->{'file'} = $redboot); } @partitions; }
+if (defined $loader)  { map { ($_->{'name'} eq 'Loader')       && 
($_->{'file'} = $loader);  } @partitions; }
 if (defined $kernel)  { map { ($_->{'name'} eq 'Kernel')       && 
($_->{'file'} = $kernel);  } @partitions; }
 if (defined $sysconf) { map { ($_->{'name'} eq 'SysConf')      && 
($_->{'file'} = $sysconf); } @partitions; }
 if (defined $fisdir)  { map { ($_->{'name'} eq 'FIS directory') && 
($_->{'file'} = $fisdir);  } @partitions; }
@@ -857,7 +882,8 @@
 
 if (defined $little)  {
     map {
-       if (($_->{'name'} eq 'Kernel') or
+       if (($_->{'name'} eq 'Loader') or
+           ($_->{'name'} eq 'Kernel') or
            ($_->{'name'} eq 'Ramdisk')) {
            $_->{'byteswap'} = 1;
        }

Reply via email to