annotate packages/redboot/current/src/load.c @ 132:0ae0bc38e387 ecos-sw-2000-10-31

Merge from eCos master repository on 2000-10-31-00:30:36-GMT
author jlarmour
date Tue, 31 Oct 2000 20:53:09 +0000
parents 518f42066aba
children 6b5f480c6929
Ignore whitespace changes - Everywhere: Within whitespace: At end of lines:
rev   line source
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
1 //==========================================================================
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
2 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
3 // load.c
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
4 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
5 // RedBoot file/image loader
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
6 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
7 //==========================================================================
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
8 //####COPYRIGHTBEGIN####
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
9 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
10 // -------------------------------------------
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
11 // The contents of this file are subject to the Red Hat eCos Public License
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
12 // Version 1.1 (the "License"); you may not use this file except in
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
13 // compliance with the License. You may obtain a copy of the License at
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
14 // http://www.redhat.com/
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
15 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
16 // Software distributed under the License is distributed on an "AS IS"
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
17 // basis, WITHOUT WARRANTY OF ANY KIND, either express or implied. See the
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
18 // License for the specific language governing rights and limitations under
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
19 // the License.
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
20 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
21 // The Original Code is eCos - Embedded Configurable Operating System,
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
22 // released September 30, 1998.
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
23 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
24 // The Initial Developer of the Original Code is Red Hat.
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
25 // Portions created by Red Hat are
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
26 // Copyright (C) 1998, 1999, 2000 Red Hat, Inc.
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
27 // All Rights Reserved.
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
28 // -------------------------------------------
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
29 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
30 //####COPYRIGHTEND####
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
31 //==========================================================================
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
32 //#####DESCRIPTIONBEGIN####
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
33 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
34 // Author(s): gthomas
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
35 // Contributors: gthomas
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
36 // Date: 2000-07-14
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
37 // Purpose:
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
38 // Description:
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
39 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
40 // This code is part of RedBoot (tm).
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
41 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
42 //####DESCRIPTIONEND####
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
43 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
44 //==========================================================================
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
45
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
46 #include <redboot.h>
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
47 #include <xyzModem.h>
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
48
124
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
49 // Buffer used by redboot_getc
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
50 getc_info_t getc_info;
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
51
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
52 static char usage[] = "[-r] [-v] [-h <host>] [-m {TFTP | xyzMODEM}] [-b <base_address>] <file_name>";
124
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
53
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
54 // Exported CLI function
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
55 RedBoot_cmd("load",
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
56 "Load a file",
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
57 usage,
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
58 do_load
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
59 );
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
60
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
61 static void
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
62 load_elf_image(int (*getc)(void))
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
63 {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
64 printf("ELF images not supported\n");
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
65 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
66
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
67 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
68 // Scan a string of hex bytes and update the checksum
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
69 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
70 static long
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
71 _hex2(int (*getc)(void), int len, long *sum)
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
72 {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
73 int val, byte;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
74 char c1, c2;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
75
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
76 val = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
77 while (len-- > 0) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
78 c1 = (*getc)();
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
79 c2 = (*getc)();
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
80 if (_is_hex(c1) && _is_hex(c2)) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
81 val <<= 8;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
82 byte = (_from_hex(c1)<<4) | _from_hex(c2);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
83 val |= byte;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
84 if (sum) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
85 *sum += byte;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
86 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
87 } else {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
88 return (-1);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
89 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
90 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
91 return (val);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
92 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
93
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
94 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
95 // Process a set of S-records, loading the contents into memory.
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
96 // Note: if a "base" value is provided, the data will be relocated
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
97 // relative to that location. Of course, this can only work for
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
98 // the first section of the data, so if there are non-contiguous
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
99 // pieces of data, they will end up relocated in the same fashion.
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
100 // Because of this, "base" probably only makes sense for a set of
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
101 // data which has only one section, e.g. a ROM image.
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
102 //
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
103 #define MAX_LINE 80
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
104 static void
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
105 load_srec_image(int (*getc)(void), unsigned long base)
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
106 {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
107 char line[MAX_LINE];
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
108 char *lp;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
109 int c, len;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
110 long offset = 0, count, sum, val, cksum;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
111 unsigned char *addr, *base_addr;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
112 char type;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
113 bool first_addr = true;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
114 unsigned long addr_offset = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
115 unsigned long highest_address = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
116 unsigned long lowest_address = 0xFFFFFFFF;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
117
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
118 while ((c = (*getc)()) > 0) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
119 lp = line; len = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
120 // Start of line
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
121 if (c != 'S') {
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
122 printf("Invalid S-record at offset %p, input: %c\n",
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
123 (void *)offset, c);
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
124 return;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
125 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
126 type = (*getc)();
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
127 offset += 2;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
128 sum = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
129 if ((count = _hex2(getc, 1, &sum)) < 0) {
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
130 printf("Bad S-record count at offset %p\n", (void *)offset);
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
131 return;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
132 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
133 offset += 1;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
134 switch (type) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
135 case '0':
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
136 break;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
137 case '1':
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
138 case '2':
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
139 case '3':
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
140 base_addr = addr = (unsigned char *)_hex2(getc, (type-'1'+2), &sum);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
141 offset += (type-'1'+2);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
142 if (first_addr) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
143 if (base) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
144 addr_offset = (unsigned long)base - (unsigned long)addr;
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
145 printf("Address offset = %p\n", (void *)addr_offset);
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
146 } else {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
147 addr_offset = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
148 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
149 first_addr = false;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
150 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
151 addr += addr_offset;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
152 if ((unsigned long)(addr-addr_offset) < lowest_address) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
153 lowest_address = (unsigned long)(addr - addr_offset);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
154 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
155 if ((addr < ram_start) || (addr > ram_end)) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
156 printf("Attempt to load S-record data to address: %p [not in RAM]\n", addr);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
157 return;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
158 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
159 count -= ((type-'1'+2)+1);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
160 offset += count;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
161 while (count-- > 0) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
162 val = _hex2(getc, 1, &sum);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
163 *addr++ = val;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
164 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
165 cksum = _hex2(getc, 1, 0);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
166 offset += 1;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
167 sum = sum & 0xFF;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
168 cksum = (~cksum & 0xFF);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
169 if (cksum != sum) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
170 printf("*** Warning! Checksum failure - Addr: %lx, %02lX <> %02lX\n",
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
171 (unsigned long)base_addr, sum, cksum);
126
518f42066aba Merge from eCos master repository on 2000-09-19-06:25:26-BST
jlarmour
parents: 124
diff changeset
172 return;
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
173 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
174 if ((unsigned long)(addr-addr_offset) > highest_address) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
175 highest_address = (unsigned long)(addr - addr_offset);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
176 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
177 break;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
178 case '7':
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
179 case '8':
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
180 case '9':
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
181 addr = (unsigned char *)_hex2(getc, ('9'-type+2), &sum);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
182 offset += ('9'-type+2);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
183 entry_address = (unsigned long *)addr;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
184 printf("Entry point: %p, address range: %p-%p\n",
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
185 entry_address, (void *)lowest_address, (void *)highest_address);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
186 return;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
187 default:
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
188 printf("Invalid S-record at offset 0x%lx, type: %x\n",
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
189 (unsigned long)offset, type);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
190 return;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
191 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
192 while ((c = (*getc)()) != '\n') offset++;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
193 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
194 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
195
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
196
124
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
197 int
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
198 redboot_getc(void)
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
199 {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
200 static char spin[] = "|/-\\|-";
124
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
201 if (getc_info.avail < 0) {
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
202 return -1;
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
203 }
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
204 if (getc_info.avail == 0) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
205 if (getc_info.verbose) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
206 printf("%c\b", spin[getc_info.tick++]);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
207 if (getc_info.tick >= sizeof(spin)) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
208 getc_info.tick = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
209 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
210 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
211 if (getc_info.len < BUF_SIZE) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
212 // No more data available
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
213 if (getc_info.verbose) printf("\n");
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
214 return -1;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
215 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
216 getc_info.bufp = getc_info.buf;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
217 getc_info.len = (*getc_info.fun)(getc_info.bufp, BUF_SIZE, &getc_info.err);
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
218 if ((getc_info.avail = getc_info.len) <= 0) {
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
219 if (getc_info.verbose) printf("\n");
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
220 return -1;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
221 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
222 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
223 getc_info.avail--;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
224 return *getc_info.bufp++;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
225 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
226
124
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
227 void
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
228 redboot_getc_init(int (*fun)(char *, int, int *), int verbose)
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
229 {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
230 getc_info.avail = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
231 getc_info.len = BUF_SIZE;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
232 getc_info.fun = fun;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
233 getc_info.verbose = verbose;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
234 getc_info.tick = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
235 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
236
124
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
237 void
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
238 redboot_getc_rewind(void)
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
239 {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
240 getc_info.bufp = getc_info.buf;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
241 getc_info.avail = getc_info.len;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
242 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
243
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
244 #define MODE_TFTP 0
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
245 #define MODE_XMODEM xyzModem_xmodem
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
246 #define MODE_YMODEM xyzModem_ymodem
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
247 #define MODE_ZMODEM xyzModem_zmodem
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
248
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
249 void
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
250 do_load(int argc, char *argv[])
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
251 {
126
518f42066aba Merge from eCos master repository on 2000-09-19-06:25:26-BST
jlarmour
parents: 124
diff changeset
252 int res, num_options;
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
253 int i, err, mode;
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
254 bool verbose, raw;
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
255 bool base_addr_set, mode_str_set;
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
256 char *mode_str;
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
257 #ifdef CYGPKG_REDBOOT_NETWORKING
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
258 struct sockaddr_in host;
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
259 bool hostname_set;
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
260 char *hostname;
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
261 #endif
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
262 unsigned long base = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
263 char type[4];
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
264 char *filename = 0;
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
265 struct option_info opts[5];
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
266
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
267 #ifdef CYGPKG_REDBOOT_NETWORKING
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
268 memset((char *)&host, 0, sizeof(host));
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
269 host.sin_len = sizeof(host);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
270 host.sin_family = AF_INET;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
271 host.sin_addr = my_bootp_info.bp_siaddr;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
272 host.sin_port = 0;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
273 #endif
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
274 #ifdef CYGPKG_REDBOOT_NETWORKING
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
275 mode = MODE_TFTP;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
276 #else
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
277 mode = MODE_YMODEM;
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
278 #endif
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
279
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
280 init_opts(&opts[0], 'v', false, OPTION_ARG_TYPE_FLG,
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
281 (void **)&verbose, 0, "verbose");
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
282 init_opts(&opts[1], 'r', false, OPTION_ARG_TYPE_FLG,
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
283 (void **)&raw, 0, "load raw data");
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
284 init_opts(&opts[2], 'b', true, OPTION_ARG_TYPE_NUM,
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
285 (void **)&base, (bool *)&base_addr_set, "load address");
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
286 init_opts(&opts[3], 'm', true, OPTION_ARG_TYPE_STR,
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
287 (void **)&mode_str, (bool *)&mode_str_set, "download mode (TFTP or xyzMODEM)");
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
288 num_options = 4;
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
289 #ifdef CYGPKG_REDBOOT_NETWORKING
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
290 init_opts(&opts[4], 'h', true, OPTION_ARG_TYPE_STR,
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
291 (void **)&hostname, (bool *)&hostname_set, "host name (IP address)");
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
292 num_options = 5;
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
293 #endif
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
294 if (!scan_opts(argc, argv, 1, opts, num_options, (void *)&filename, OPTION_ARG_TYPE_STR, "file name"))
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
295 {
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
296 return;
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
297 }
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
298 #ifdef CYGPKG_REDBOOT_NETWORKING
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
299 if (hostname_set) {
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
300 if (!inet_aton(hostname, (in_addr_t *)&host)) {
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
301 printf("Invalid IP address: %s\n", hostname);
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
302 return;
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
303 }
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
304 }
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
305 #endif
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
306 if (mode_str_set) {
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
307 if (strncmpci(&mode_str[1], "modem", strlen(&mode_str[1])) == 0) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
308 switch (tolower(mode_str[0])) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
309 case 'x':
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
310 mode = MODE_XMODEM;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
311 break;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
312 case 'y':
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
313 mode = MODE_YMODEM;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
314 break;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
315 case 'z':
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
316 mode = MODE_ZMODEM;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
317 break;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
318 default:
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
319 printf("Invalid 'mode': %s\n", mode_str);
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
320 return;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
321 }
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
322 #ifdef CYGPKG_REDBOOT_NETWORKING
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
323 } else if (strcmpci(mode_str, "tftp") == 0) {
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
324 mode = MODE_TFTP;
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
325 if (!have_net) {
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
326 printf("TFTP mode requires a working network\n");
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
327 return;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
328 }
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
329 #endif
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
330 } else {
117
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
331 printf("Invalid 'mode': %s\n", mode_str);
bd1a71e3e476 Merge from eCos master repository on 2000-08-25-19:22:58-BST
jlarmour
parents: 115
diff changeset
332 return;
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
333 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
334 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
335 if ((mode == MODE_TFTP) && !filename) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
336 printf("File name missing\n");
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
337 printf("usage: load %s\n", usage);
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
338 return;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
339 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
340 #ifdef CYGPKG_REDBOOT_NETWORKING
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
341 if (mode == MODE_TFTP) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
342 res = tftp_stream_open(filename, &host, TFTP_OCTET, &err);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
343 if (res < 0) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
344 printf("Can't load '%s': %s\n", filename, tftp_error(err));
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
345 return;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
346 }
124
0ec04793409a Merge from eCos master repository on 2000-09-11-03:00:13-BST
jlarmour
parents: 117
diff changeset
347 redboot_getc_init(tftp_stream_read, verbose);
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
348 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
349 #endif
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
350 else {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
351 res = xyzModem_stream_open(filename, mode, &err);
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
352 if (res < 0) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
353 printf("Can't load '%s': %s\n", filename, xyzModem_error(err));
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
354 return;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
355 }
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
356 redboot_getc_init(xyzModem_stream_read, verbose);
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
357 }
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
358 // Read initial header - to determine file [image] type
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
359 for (i = 0; i < sizeof(type); i++) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
360 if ((res = redboot_getc()) < 0) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
361 err = getc_info.err;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
362 break;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
363 }
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
364 type[i] = res;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
365 }
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
366 if (res >= 0) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
367 redboot_getc_rewind(); // Restore header to stream
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
368 if (raw) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
369 if (!base_addr_set) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
370 printf("Raw load requires a memory address\n");
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
371 } else {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
372 unsigned char *mp = (unsigned char *)base;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
373 while ((res = redboot_getc()) >= 0) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
374 *mp++ = res;
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
375 }
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
376 printf("Raw file loaded %p-%p\n", (void *)base, (void *)mp);
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
377 }
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
378 } else {
132
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
379 // Treat data as some sort of executable image
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
380 if (strncmp(&type[1], "ELF", 3) == 0) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
381 load_elf_image(redboot_getc);
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
382 } else if ((type[0] == 'S') &&
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
383 ((type[1] >= '0') && (type[1] <= '9'))) {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
384 load_srec_image(redboot_getc, base);
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
385 } else {
0ae0bc38e387 Merge from eCos master repository on 2000-10-31-00:30:36-GMT
jlarmour
parents: 126
diff changeset
386 printf("Unrecognized image type: %lx\n", *(unsigned long *)type);
115
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
387 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
388 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
389 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
390 #ifdef CYGPKG_REDBOOT_NETWORKING
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
391 if (mode == MODE_TFTP) {
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
392 tftp_stream_close(&err);
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
393 }
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
394 #endif
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
395 return;
6ed91473a1cd Merge from eCos master repository on 2000-08-21-22:40:54-BST
jlarmour
parents:
diff changeset
396 }