Hi,
I've been working with Daniel Ankers on getting a dual bootloader
working on the Sansa (and also on the H10). In doing so, it was
necessary to make some changes to crt0-pp.S (patch attached). The
purpose of the changes was to:

* Make sure only the CPU clears the BSS (not the COP)
* Give the CPU and COP separate stacks
* Make the bootloader run from IRAM so it's not overwriting the SDRAM
* Flushing the cache as appropriate (before waking up the COP)
* Remove the unused DEBUG and STUB code (which was only ever used for
the iFP port afaik)

I'm told that the current crt0-pp.S in CVS is very very multiprocessor
unsafe because of the reasons fixed in this patch, so it's quite
possible that some random behaviour in iPods may also be fixed by
this, particularly things related to the COP.

I've tested on my own H10 and Sansa with great results - dual booting
works now where it didn't before. However, I don't have an iPod to
test on so I'm asking for people to help with testing it. Both
bootloader and normal builds need testing and it would also be good to
know if a new bootloader works with an old build of Rockbox and vice
versa (this wasn't the case with my H10 but was with the Sansa). It
needs to be tested to see if Rockbox loads OK and if playback, etc.
still works as it did previously.

Thanks,
Barry
Index: bootloader/e200.c
===================================================================
RCS file: /cvsroot/rockbox/bootloader/e200.c,v
retrieving revision 1.5
diff -u -r1.5 e200.c
--- bootloader/e200.c	16 Oct 2006 17:21:30 -0000	1.5
+++ bootloader/e200.c	5 Dec 2006 01:27:21 -0000
@@ -5,9 +5,12 @@
  *   Jukebox    |    |   (  <_> )  \___|    < | \_\ (  <_> > <  <
  *   Firmware   |____|_  /\____/ \___  >__|_ \|___  /\____/__/\_ \
  *                     \/            \/     \/    \/            \/
- * $Id: e200.c,v 1.5 2006-10-16 17:21:30 dan_a Exp $
+ * $Id: h10.c,v 1.4 2006-08-28 08:11:32 barrywardell Exp $
  *
- * Copyright (C) 2006 Daniel Stenberg
+ * Copyright (C) 2006 by Barry Wardell
+ *
+ * Based on Rockbox iriver bootloader by Linus Nielsen Feltzing
+ * and the ipodlinux bootloader by Daniel Palffy and Bernard Leach
  *
  * All files in this archive are subject to the GNU General Public License.
  * See the file COPYING in the source tree root for full license agreement.
@@ -32,63 +35,202 @@
 #include "font.h"
 #include "adc.h"
 #include "backlight.h"
+#include "button.h"
 #include "panic.h"
 #include "power.h"
 #include "file.h"
 
-static inline void blink(void)
+/* Size of the buffer to store the loaded Rockbox/Sansa image */
+#define MAX_LOADSIZE (10*1024*1024)
+
+/* A buffer to load the iriver firmware or Rockbox into */
+unsigned char loadbuffer[MAX_LOADSIZE];
+
+char version[] = APPSVERSION;
+
+#define DRAM_START              0x10000000
+
+int line=0;
+
+/* Load original Sandisk firmware. This function expects a file called
+   "/.rockbox/OF.bin" on the player. It should be decrypted
+   and have the header stripped using mi4code. It reads the file in to a memory
+   buffer called buf. The rest of the loading is done in main() and crt0.S
+*/
+int load_sandisk(unsigned char* buf)
 {
-    volatile unsigned int* ptr;
+    int fd;
+    int rc;
+    int len;
+
+    fd = open("/.rockbox/OF.bin", O_RDONLY);
+
+    len = filesize(fd);
+
+    if (len > MAX_LOADSIZE)
+        return -6;
+
+    rc = read(fd, buf, len);
+    if(rc < len)
+        return -4;
+
+    close(fd);
+    return len;
+}
+
+/* Load Rockbox firmware (rockbox.e200) */
+int load_rockbox(unsigned char* buf)
+{
+    int fd;
+    int rc;
+    int len;
+    unsigned long chksum;
+    char model[5];
+    unsigned long sum;
     int i;
-    ptr = (volatile unsigned int*)0x70000020;
+    char str[80];
 
-    *ptr &= ~(1 << 13);
-    for(i = 0; i < 0xfffff; i++)
+    fd = open("/.rockbox/" BOOTFILE, O_RDONLY);
+    if(fd < 0)
     {
+        fd = open("/" BOOTFILE, O_RDONLY);
+        if(fd < 0)
+            return -1;
     }
-    *ptr |= (1 << 13);
-    for(i = 0; i < 0xfffff; i++)
-    {
+
+    len = filesize(fd) - 8;
+
+    snprintf(str, sizeof(str), "Length: %x", len);
+    lcd_puts(0, line++ ,str);
+    lcd_update();
+
+    if (len > MAX_LOADSIZE)
+        return -6;
+
+    lseek(fd, FIRMWARE_OFFSET_FILE_CRC, SEEK_SET);
+
+    rc = read(fd, &chksum, 4);
+    chksum=betoh32(chksum); /* Rockbox checksums are big-endian */
+    if(rc < 4)
+        return -2;
+
+    snprintf(str, sizeof(str), "Checksum: %x", chksum);
+    lcd_puts(0, line++ ,str);
+    lcd_update();
+
+    rc = read(fd, model, 4);
+    if(rc < 4)
+        return -3;
+
+    model[4] = 0;
+
+    snprintf(str, sizeof(str), "Model name: %s", model);
+    lcd_puts(0, line++ ,str);
+    lcd_update();
+
+    lseek(fd, FIRMWARE_OFFSET_FILE_DATA, SEEK_SET);
+
+    rc = read(fd, buf, len);
+    if(rc < len)
+        return -4;
+
+    close(fd);
+
+    sum = MODEL_NUMBER;
+
+    for(i = 0;i < len;i++) {
+        sum += buf[i];
     }
+
+    snprintf(str, sizeof(str), "Sum: %x", sum);
+    lcd_puts(0, line++ ,str);
+    lcd_update();
+
+    if(sum != chksum)
+        return -5;
+
+    return len;
 }
 
-static inline void slow_blink(void)
+void* main(void)
 {
-    volatile unsigned int* ptr;
+    char buf[256];
     int i;
-    ptr = (volatile unsigned int*)0x70000020;
+    int rc;
+    unsigned short* identify_info;
+    struct partinfo* pinfo;
 
-    *ptr &= ~(1 << 13);
-    for(i = 0; i < (0xfffff); i++)
-    {
-    }
-    for(i = 0; i < (0xfffff); i++)
-    {
-    }
-    for(i = 0; i < (0xfffff); i++)
-    {
-    }
+    system_init();
+    kernel_init();
+    lcd_init();
+    font_init();
 
-    *ptr |= (1 << 13);
-    for(i = 0; i < (0xfffff); i++)
+    line=0;
+
+    lcd_setfont(FONT_SYSFIXED);
+
+    lcd_puts(0, line++, "Rockbox boot loader");
+    snprintf(buf, sizeof(buf), "Version: 20%s", version);
+    lcd_puts(0, line++, buf);
+    snprintf(buf, sizeof(buf), "Sandisk Sansa E200");
+    lcd_puts(0, line++, buf);
+    lcd_update();
+
+    i=ata_init();
+    if (i==0) {
+      identify_info=ata_get_identify();
+      /* Show model */
+      for (i=0; i < 20; i++) {
+        ((unsigned short*)buf)[i]=htobe16(identify_info[i+27]);
+      }
+      buf[40]=0;
+      for (i=39; i && buf[i]==' '; i--) {
+        buf[i]=0;
+      }
+      lcd_puts(0, line++, buf);
+      lcd_update();
+    } else {
+      snprintf(buf, sizeof(buf), "ATA: %d", i);
+      lcd_puts(0, line++, buf);
+      lcd_update();
+    }
+
+    disk_init();
+    rc = disk_mount_all();
+    if (rc<=0)
     {
+        lcd_puts(0, line++, "No partition found");
+        lcd_update();
     }
-    for(i = 0; i < (0xfffff); i++)
+
+    pinfo = disk_partinfo(0);
+    snprintf(buf, sizeof(buf), "Partition 0: 0x%02x %ld MB",
+                  pinfo->type, pinfo->size / 2048);
+    lcd_puts(0, line++, buf);
+    lcd_update();
+
+    i=button_read_device();
+    if(i==BUTTON_LEFT)
     {
+        lcd_puts(0, line, "Loading Sandisk firmware...");
+        lcd_update();
+        rc=load_sandisk(loadbuffer);
+        /* Sandisk firmware doesn't like having the cache enabled */
+    } else {
+        lcd_puts(0, line, "Loading Rockbox...");
+        lcd_update();
+        rc=load_rockbox(loadbuffer);
     }
-    for(i = 0; i < (0xfffff); i++)
-    {
+
+    if (rc < 0) {
+            snprintf(buf, sizeof(buf), "Rockbox error: %d",rc);
+            lcd_puts(0, line++, buf);
+            lcd_update();
+            while(1) {}
     }
-}
 
-static inline unsigned long get_pc(void)
-{
-    unsigned long pc;
-    asm volatile (
-        "mov %0, pc\n"
-        : "=r"(pc)
-    );
-    return pc;
+    memcpy((void*)DRAM_START,loadbuffer,rc);
+    return (void*)DRAM_START;
 }
 
 /* These functions are present in the firmware library, but we reimplement
@@ -100,62 +242,7 @@
 
 int dbg_ports(void)
 {
-    unsigned int gpio_a, gpio_b, gpio_c, gpio_d;
-    unsigned int gpio_e, gpio_f, gpio_g, gpio_h;
-    unsigned int gpio_i, gpio_j, gpio_k, gpio_l;
-
-    char buf[128];
-    int line;
-
-    lcd_setmargins(0, 0);
-    lcd_clear_display();
-    lcd_setfont(FONT_SYSFIXED);
-
-    while(1)
-    {
-        gpio_a = GPIOA_INPUT_VAL;
-        gpio_b = GPIOB_INPUT_VAL;
-        gpio_c = GPIOC_INPUT_VAL;
-
-        gpio_g = GPIOG_INPUT_VAL;
-        gpio_h = GPIOH_INPUT_VAL;
-        gpio_i = GPIOI_INPUT_VAL;
-
-        line = 0;
-        snprintf(buf, sizeof(buf), "GPIO_A: %02x GPIO_G: %02x", gpio_a, gpio_g);
-        lcd_puts(0, line++, buf);
-        snprintf(buf, sizeof(buf), "GPIO_B: %02x GPIO_H: %02x", gpio_b, gpio_h);
-        lcd_puts(0, line++, buf);
-        snprintf(buf, sizeof(buf), "GPIO_C: %02x GPIO_I: %02x", gpio_c, gpio_i);
-        lcd_puts(0, line++, buf);
-        line++;
-
-        gpio_d = GPIOD_INPUT_VAL;
-        gpio_e = GPIOE_INPUT_VAL;
-        gpio_f = GPIOF_INPUT_VAL;
-
-        gpio_j = GPIOJ_INPUT_VAL;
-        gpio_k = GPIOK_INPUT_VAL;
-        gpio_l = GPIOL_INPUT_VAL;
-
-        snprintf(buf, sizeof(buf), "GPIO_D: %02x GPIO_J: %02x", gpio_d, gpio_j);
-        lcd_puts(0, line++, buf);
-        snprintf(buf, sizeof(buf), "GPIO_E: %02x GPIO_K: %02x", gpio_e, gpio_k);
-        lcd_puts(0, line++, buf);
-        snprintf(buf, sizeof(buf), "GPIO_F: %02x GPIO_L: %02x", gpio_f, gpio_l);
-        lcd_puts(0, line++, buf);
-        line++;
-        snprintf(buf, sizeof(buf), "ADC_1: %02x", adc_read(ADC_0));
-        lcd_puts(0, line++, buf);
-        snprintf(buf, sizeof(buf), "ADC_2: %02x", adc_read(ADC_1));
-        lcd_puts(0, line++, buf);
-        snprintf(buf, sizeof(buf), "ADC_3: %02x", adc_read(ADC_2));
-        lcd_puts(0, line++, buf);
-        snprintf(buf, sizeof(buf), "ADC_4: %02x", adc_read(ADC_3));
-        lcd_puts(0, line++, buf);
-        lcd_update();
-    }
-    return 0;
+   return 0;
 }
 
 void mpeg_stop(void)
@@ -173,18 +260,3 @@
 void sys_poweroff(void)
 {
 }
-
-void system_reboot(void)
-{
-
-}
-
-void main(void)
-{
-    kernel_init();
-    adc_init();
-    lcd_init_device();
-
-    dbg_ports();
-}
-
Index: firmware/export/config-e200.h
===================================================================
RCS file: /cvsroot/rockbox/firmware/export/config-e200.h,v
retrieving revision 1.4
diff -u -r1.4 config-e200.h
--- firmware/export/config-e200.h	22 Nov 2006 00:49:15 -0000	1.4
+++ firmware/export/config-e200.h	5 Dec 2006 01:27:24 -0000
@@ -4,7 +4,7 @@
 #define TARGET_TREE /* this target is using the target tree system */
 
 /* For Rolo and boot loader */
-#define MODEL_NUMBER 12
+#define MODEL_NUMBER 16
 
 /* define this if you have recording possibility */
 /*#define HAVE_RECORDING 1*/ /* TODO: add support for this */
Index: firmware/target/arm/crt0-pp.S
===================================================================
RCS file: /cvsroot/rockbox/firmware/target/arm/crt0-pp.S,v
retrieving revision 1.2
diff -u -r1.2 crt0-pp.S
--- firmware/target/arm/crt0-pp.S	22 Nov 2006 00:49:16 -0000	1.2
+++ firmware/target/arm/crt0-pp.S	5 Dec 2006 01:27:24 -0000
@@ -5,7 +5,7 @@
  *   Jukebox    |    |   (  <_> )  \___|    < | \_\ (  <_> > <  <
  *   Firmware   |____|_  /\____/ \___  >__|_ \|___  /\____/__/\_ \
  *                     \/            \/     \/    \/            \/
- * $Id: crt0-pp.S,v 1.2 2006-11-22 00:49:16 dan_a Exp $
+ * $Id: crt0-pp.S,v 1.2 2006/11/22 00:49:16 dan_a Exp $
  *
  * Copyright (C) 2002 by Linus Nielsen Feltzing
  *
@@ -52,17 +52,36 @@
 
     msr    cpsr_c, #0xd3 /* enter supervisor mode, disable IRQ */
 
-#ifndef BOOTLOADER
     b      pad_skip
 
-#if defined(SANSA_E200)
-/* mi4tool writes junk between 0xe0 and 0xeb.  Avoid this. */
-.space 60*4 /* (more than enough) space for exception vectors */
-#else
-.space 50*4
-#endif
+.space 60*4 /* For bootloader builds on targets with mi4 firmware, scramble
+               writes data to 0xe0-0xeb, so jump past that. For normal builds
+               this provides more than enough space for exception vectors */
 
 pad_skip:
+
+#ifdef BOOTLOADER
+/* 1 - Copy the bootloader to IRAM */
+    /* get the high part of our execute address */
+    and    r4, pc, #0xff000000
+
+    /* Copy bootloader to safe area - 0x40000000 */
+    mov    r5, #0x40000000
+    ldr    r6, = _dataend
+    sub    r0, r6, r5       /* length of loader */
+    add    r8, r4, r0       /* r8 points to start of loader */
+1:
+    cmp    r5, r6
+    ldrcc  r2, [r4], #4
+    strcc  r2, [r5], #4
+    bcc    1b
+
+/* 2 - Jump both CPU and COP there */
+    ldr    pc, =start_loc    /* jump to the relocated start_loc:  */
+
+start_loc:
+
+#else /* BOOTLOADER */
 #ifdef SANSA_E200
     /* On the Sansa, copying the vectors fails if the cache is initialised */
     ldr    r1, =CACHE_CTRL
@@ -106,24 +125,63 @@
 L_post_remap: .word remap_end
 remap_end:
 
-    /* After doing the remapping, send the COP to sleep.
-       On wakeup it will go to cop_init */
+#endif
+
+    /* Send the COP to sleep. On wakeup it will go to cop_init */
     ldr    r0, =PROC_ID
     ldr    r0, [r0]
     and    r0, r0, #0xff
     cmp    r0, #0x55
-    beq    1f
+    beq    cpu
     
     /* put us (co-processor) to sleep */
     ldr    r4, =COP_CTRL
     mov    r3, #SLEEP
     str    r3, [r4]
+    ldr    pc, =cop_wake_start
 
-    ldr    pc, =cop_init
+cop_wake_start:
+    /* COP: Invalidate cache */
+    ldr    r0, =0xf000f044
+    ldr    r1, [r0]
+    orr    r1, r1, #0x6
+    str    r1, [r0]
 
+    ldr    r0, =0x6000c000
 1:
+    ldr    r1, [r0]
+    tst    r1, #0x8000
+    bne    1b
+    
+#ifdef BOOTLOADER
+    ldr    r0, =startup_loc
+    ldr    pc, [r0]
+#else
+    /* Setup stack for COP */
+    ldr    sp, =cop_stackend
+    mov    r3, sp
+    ldr    r2, =cop_stackbegin
+    ldr    r4, =0xdeadbeef
+2:
+    cmp    r3, r2
+    strhi  r4, [r2], #4
+    bhi    2b
 
-#ifndef DEBUG
+    ldr    sp, =cop_stackend
+    
+    /* Run cop_main() in apps/main.c */
+    bl     cop_main
+#endif
+
+cpu:
+    /* Wait for COP to be sleeping */
+    ldr    r4, =COP_STATUS
+1:
+    ldr    r3, [r4]
+    ands   r3, r3, #SLEEPING
+    beq    1b
+    
+#ifndef BOOTLOADER
     /* Copy exception handler code to address 0 */
     ldr    r2, =_vectorsstart
     ldr    r3, =_vectorsend
@@ -133,24 +191,18 @@
     ldrhi  r5, [r4], #4
     strhi  r5, [r2], #4
     bhi    1b
-#else
-    ldr    r1, =vectors
-    ldr    r0, =irq_handler
-    str    r0, [r1, #24]
-    ldr    r0, =fiq_handler
-    str    r0, [r1, #28]
 #endif
 
-#ifndef STUB
-    /* Zero out IBSS */
-    ldr    r2, =_iedata
-    ldr    r3, =_iend
+    /* Initialise bss section to zero */
+    ldr    r2, =_edata
+    ldr    r3, =_end
     mov    r4, #0
 1:
     cmp    r3, r2
     strhi  r4, [r2], #4
     bhi    1b
-
+       
+#ifndef BOOTLOADER
     /* Copy the IRAM */
     ldr    r2, =_iramcopy
     ldr    r3, =_iramstart
@@ -160,18 +212,8 @@
     ldrhi  r5, [r2], #4
     strhi  r5, [r3], #4
     bhi    1b
-#endif /* !STUB */
-#endif /* !BOOTLOADER */
+#endif
 
-    /* Initialise bss section to zero */
-    ldr    r2, =_edata
-    ldr    r3, =_end
-    mov    r4, #0
-1:
-    cmp    r3, r2
-    strhi  r4, [r2], #4
-    bhi    1b
-    
     /* Set up some stack and munge it with 0xdeadbeef */
     ldr    sp, =stackend
     mov    r3, sp
@@ -183,76 +225,31 @@
     bhi    1b
 
 #ifdef BOOTLOADER
-    /* TODO: the high part of the address is probably dependent on CONFIG_CPU.
-       Since we tend to use ifdefs for each chipset target
-       anyway, we might as well just hardcode it here.
-     */
-       
-    /* get the high part of our execute address */
-    ldr    r0, =0xff000000
-    and    r8, pc, r0             @ r8 is used later
-
-    /* Find out which processor we are */
-    mov    r0, #PROC_ID
-    ldr    r0, [r0]
-    and    r0, r0, #0xff
-    cmp    r0, #0x55
-    beq    1f
-
-    /* put us (co-processor) to sleep */
-    ldr    r4, =COP_CTRL
-    mov    r3, #SLEEP
-    str    r3, [r4]
-    ldr    pc, =cop_wake_start
-
-cop_wake_start:
-    /* jump the COP to startup */
-    ldr    r0, =startup_loc
-    ldr    pc, [r0]
-
-1:
-    
-    /* get the high part of our execute address */
-    ldr    r2, =0xffffff00
-    and    r4, pc, r2
-
-    /* Copy bootloader to safe area - 0x40000000 */
-    mov    r5, #0x40000000
-    ldr    r6, = _dataend
-    sub    r0, r6, r5       /* length of loader */
-    add    r0, r4, r0     /* r0 points to start of loader */
-1:
-    cmp    r5, r6
-    ldrcc  r2, [r4], #4
-    strcc  r2, [r5], #4
-    bcc    1b
-
-    ldr    pc, =start_loc    /* jump to the relocated start_loc:  */
-    
-start_loc:
+    mov    r0, r8 /* r8 holds the start of the loader - copy this to r0 */
 
     /* execute the loader - this will load an image to 0x10000000 */
     bl     main
 
-    /* Wake up the coprocessor before executing the firmware */
-
-    /* save the startup address for the COP */
     ldr    r1, =startup_loc
     str    r0, [r1]
 
-    /* make sure COP is sleeping */
-    ldr    r4, =COP_STATUS
+    /* Flush cache */
+    ldr    r3, =0xf000f044
+    ldr    r4, [r3]
+    orr    r4, r4, #0x2
+    str    r4, [r3]
+
+    ldr    r3, =0x6000c000
 1:
-    ldr    r3, [r4]
-    ands   r3, r3, #SLEEPING
-    beq    1b
+    ldr    r4, [r3]
+    tst    r4, #0x8000
+    bne    1b
 
-    /* wake up COP */
+    /* Wake up the coprocessor before executing the firmware */
     ldr    r4, =COP_CTRL
     mov    r3, #WAKE
     str    r3, [r4]
 
-    /* jump to start location */
     mov    pc, r0
 
 startup_loc:
@@ -265,7 +262,7 @@
     .space 400
 
 #else /* BOOTLOADER */
-    
+
     /* Set up stack for IRQ mode */ 
     msr    cpsr_c, #0xd2
     ldr    sp, =irq_stack
@@ -288,19 +285,6 @@
     ldr    sp, =stackend
     bl     main
     /* main() should never return */
-
-cop_init:
-    ldr    sp, =cop_stackend
-    mov    r3, sp
-    ldr    r2, =cop_stackbegin
-    ldr    r4, =0xdeadbeef
-2:
-    cmp    r3, r2
-    strhi  r4, [r2], #4
-    bhi    2b
-
-    ldr    sp, =cop_stackend
-    bl     cop_main
     
 /* Exception handlers. Will be copied to address 0 after memory remapping */
     .section .vectors,"aw"
@@ -385,5 +369,4 @@
 /* 256 words of FIQ stack */
     .space 256*4
 fiq_stack:
-
-#endif /* BOOTLOADER */ 
+#endif /* BOOTLOADER */
Index: tools/configure
===================================================================
RCS file: /cvsroot/rockbox/tools/configure,v
retrieving revision 1.245
diff -u -r1.245 configure
--- tools/configure	27 Nov 2006 02:15:39 -0000	1.245
+++ tools/configure	5 Dec 2006 01:27:27 -0000
@@ -1115,10 +1115,10 @@
     target="-DSANSA_E200"
     memory=32 # supposedly
     arm7tdmicc
-    tool="$rootdir/tools/scramble -mi4v3"
+    tool="$rootdir/tools/scramble -add=e200"
     bmp2rb_mono="$rootdir/tools/bmp2rb -f 0"
     bmp2rb_native="$rootdir/tools/bmp2rb -f 4"
-    output="PP5022.mi4"
+    output="rockbox.e200"
     appextra="recorder:gui"
     archosrom=""
     flash=""
Index: tools/scramble.c
===================================================================
RCS file: /cvsroot/rockbox/tools/scramble.c,v
retrieving revision 1.35
diff -u -r1.35 scramble.c
--- tools/scramble.c	31 Aug 2006 19:19:35 -0000	1.35
+++ tools/scramble.c	5 Dec 2006 01:27:28 -0000
@@ -89,7 +89,7 @@
            "\t-mi4v3  PortalPlayer .mi4 format (revision 010301)\n"
            "\t-add=X  Rockbox generic \"add-up\" checksum format\n"
            "\t        (X values: h100, h120, h140, h300, ipco, nano, ipvd\n"
-           "\t                   ip3g, ip4g, mini, x5, h10, h10_5gb)\n"
+           "\t                   ip3g, ip4g, mini, x5, h10, h10_5gb, tpj2, e200)\n"
            "\nNo option results in Archos standard player/recorder format.\n");
 
     exit(1);
@@ -207,6 +207,8 @@
             modelnum = 14;
         else if(!strcmp(&argv[1][5], "tpj2"))
             modelnum = 15;
+        else if(!strcmp(&argv[1][5], "e200"))
+            modelnum = 16;
         else {
             fprintf(stderr, "unsupported model: %s\n", &argv[1][5]);
             return 2;

Reply via email to