diff options
author | Al Viro <viro@ftp.linux.org.uk> | 2006-09-22 20:37:41 -0400 |
---|---|---|
committer | Paul Mackerras <paulus@samba.org> | 2006-09-26 01:41:02 -0400 |
commit | c32527a14049130eb29103b8da27520f07092371 (patch) | |
tree | 7b99a321bc489d5e774b20ee456021f15fa151b0 | |
parent | 8c42ec2c99502f8a81076f24f57775b9c646351a (diff) |
[POWERPC] rewrite mkprep and mkbugboot in sane C
Signed-off-by: Al Viro <viro@zeniv.linux.org.uk>
Signed-off-by: Paul Mackerras <paulus@samba.org>
-rw-r--r-- | arch/ppc/boot/utils/mkbugboot.c | 208 | ||||
-rw-r--r-- | arch/ppc/boot/utils/mkprep.c | 416 |
2 files changed, 267 insertions, 357 deletions
diff --git a/arch/ppc/boot/utils/mkbugboot.c b/arch/ppc/boot/utils/mkbugboot.c index 29115e01f60a..1640c4199ca6 100644 --- a/arch/ppc/boot/utils/mkbugboot.c +++ b/arch/ppc/boot/utils/mkbugboot.c | |||
@@ -19,36 +19,13 @@ | |||
19 | #include <stdlib.h> | 19 | #include <stdlib.h> |
20 | #include <errno.h> | 20 | #include <errno.h> |
21 | #include <fcntl.h> | 21 | #include <fcntl.h> |
22 | #include <netinet/in.h> | ||
22 | #ifdef __sun__ | 23 | #ifdef __sun__ |
23 | #include <inttypes.h> | 24 | #include <inttypes.h> |
24 | #else | 25 | #else |
25 | #include <stdint.h> | 26 | #include <stdint.h> |
26 | #endif | 27 | #endif |
27 | 28 | ||
28 | #ifdef __i386__ | ||
29 | #define cpu_to_be32(x) le32_to_cpu(x) | ||
30 | #define cpu_to_be16(x) le16_to_cpu(x) | ||
31 | #else | ||
32 | #define cpu_to_be32(x) (x) | ||
33 | #define cpu_to_be16(x) (x) | ||
34 | #endif | ||
35 | |||
36 | #define cpu_to_le32(x) le32_to_cpu((x)) | ||
37 | unsigned long le32_to_cpu(unsigned long x) | ||
38 | { | ||
39 | return (((x & 0x000000ffU) << 24) | | ||
40 | ((x & 0x0000ff00U) << 8) | | ||
41 | ((x & 0x00ff0000U) >> 8) | | ||
42 | ((x & 0xff000000U) >> 24)); | ||
43 | } | ||
44 | |||
45 | #define cpu_to_le16(x) le16_to_cpu((x)) | ||
46 | unsigned short le16_to_cpu(unsigned short x) | ||
47 | { | ||
48 | return (((x & 0x00ff) << 8) | | ||
49 | ((x & 0xff00) >> 8)); | ||
50 | } | ||
51 | |||
52 | /* size of read buffer */ | 29 | /* size of read buffer */ |
53 | #define SIZE 0x1000 | 30 | #define SIZE 0x1000 |
54 | 31 | ||
@@ -62,124 +39,109 @@ typedef struct bug_boot_header { | |||
62 | 39 | ||
63 | #define HEADER_SIZE sizeof(bug_boot_header_t) | 40 | #define HEADER_SIZE sizeof(bug_boot_header_t) |
64 | 41 | ||
65 | uint32_t copy_image(int32_t in_fd, int32_t out_fd) | 42 | void update_checksum(void *buf, size_t size, uint16_t *sum) |
66 | { | 43 | { |
67 | uint8_t buf[SIZE]; | 44 | uint32_t csum = *sum; |
68 | int n; | 45 | |
69 | uint32_t image_size = 0; | 46 | while (size) { |
70 | uint8_t zero = 0; | 47 | csum += *(uint16_t *)buf; |
71 | 48 | if (csum > 0xffff) | |
72 | lseek(in_fd, ELF_HEADER_SIZE, SEEK_SET); | 49 | csum -= 0xffff; |
73 | 50 | buf = (uint16_t *)buf + 1; | |
74 | /* Copy an image while recording its size */ | 51 | size -= 2; |
75 | while ( (n = read(in_fd, buf, SIZE)) > 0 ) | 52 | } |
76 | { | 53 | *sum = csum; |
77 | image_size = image_size + n; | ||
78 | write(out_fd, buf, n); | ||
79 | } | ||
80 | |||
81 | /* BUG romboot requires that our size is divisible by 2 */ | ||
82 | /* align image to 2 byte boundary */ | ||
83 | if (image_size % 2) | ||
84 | { | ||
85 | image_size++; | ||
86 | write(out_fd, &zero, 1); | ||
87 | } | ||
88 | |||
89 | return image_size; | ||
90 | } | 54 | } |
91 | 55 | ||
92 | void write_bugboot_header(int32_t out_fd, uint32_t boot_size) | 56 | uint32_t copy_image(int in_fd, int out_fd, uint16_t *sum) |
93 | { | 57 | { |
94 | uint8_t header_block[HEADER_SIZE]; | 58 | uint8_t buf[SIZE]; |
95 | bug_boot_header_t *bbh = (bug_boot_header_t *)&header_block[0]; | 59 | int offset = 0; |
96 | 60 | int n; | |
97 | memset(header_block, 0, HEADER_SIZE); | 61 | uint32_t image_size = 0; |
98 | 62 | ||
99 | /* Fill in the PPCBUG ROM boot header */ | 63 | lseek(in_fd, ELF_HEADER_SIZE, SEEK_SET); |
100 | strncpy(bbh->magic_word, "BOOT", 4); /* PPCBUG magic word */ | 64 | |
101 | bbh->entry_offset = cpu_to_be32(HEADER_SIZE); /* Entry address */ | 65 | /* Copy an image while recording its size */ |
102 | bbh->routine_length= cpu_to_be32(HEADER_SIZE+boot_size+2); /* Routine length */ | 66 | while ( (n = read(in_fd, buf + offset, SIZE - offset)) > 0 ) { |
103 | strncpy(bbh->routine_name, "LINUXROM", 8); /* Routine name */ | 67 | n += offset; |
104 | 68 | offset = n & 1; | |
105 | /* Output the header and bootloader to the file */ | 69 | n -= offset; |
106 | write(out_fd, header_block, HEADER_SIZE); | 70 | image_size = image_size + n; |
71 | /* who's going to deal with short writes? */ | ||
72 | write(out_fd, buf, n); | ||
73 | update_checksum(buf, n, sum); | ||
74 | if (offset) | ||
75 | buf[0] = buf[n]; | ||
76 | } | ||
77 | |||
78 | /* BUG romboot requires that our size is divisible by 2 */ | ||
79 | /* align image to 2 byte boundary */ | ||
80 | if (offset) { | ||
81 | image_size += 2; | ||
82 | buf[1] = '\0'; | ||
83 | write(out_fd, buf, 2); | ||
84 | update_checksum(buf, 2, sum); | ||
85 | } | ||
86 | return image_size; | ||
107 | } | 87 | } |
108 | 88 | ||
109 | uint16_t calc_checksum(int32_t bug_fd) | 89 | void write_bugboot_header(int out_fd, uint32_t boot_size, uint16_t *sum) |
110 | { | 90 | { |
111 | uint32_t checksum_var = 0; | 91 | static bug_boot_header_t bbh = { |
112 | uint8_t buf[2]; | 92 | .magic_word = "BOOT", |
113 | int n; | 93 | .routine_name = "LINUXROM" |
114 | 94 | }; | |
115 | /* Checksum loop */ | 95 | |
116 | while ( (n = read(bug_fd, buf, 2) ) ) | 96 | /* Fill in the PPCBUG ROM boot header */ |
117 | { | 97 | bbh.entry_offset = htonl(HEADER_SIZE); /* Entry address */ |
118 | checksum_var = checksum_var + *(uint16_t *)buf; | 98 | bbh.routine_length= htonl(HEADER_SIZE+boot_size+2); /* Routine length */ |
119 | 99 | ||
120 | /* If we carry out, mask it and add one to the checksum */ | 100 | /* Output the header and bootloader to the file */ |
121 | if (checksum_var >> 16) | 101 | write(out_fd, &bbh, sizeof(bug_boot_header_t)); |
122 | checksum_var = (checksum_var & 0x0000ffff) + 1; | 102 | update_checksum(&bbh, sizeof(bug_boot_header_t), sum); |
123 | } | ||
124 | |||
125 | return checksum_var; | ||
126 | } | 103 | } |
127 | 104 | ||
128 | int main(int argc, char *argv[]) | 105 | int main(int argc, char *argv[]) |
129 | { | 106 | { |
130 | int32_t image_fd, bugboot_fd; | 107 | int image_fd, bugboot_fd; |
131 | int argptr = 1; | 108 | uint32_t kernel_size = 0; |
132 | uint32_t kernel_size = 0; | 109 | uint16_t checksum = 0; |
133 | uint16_t checksum = 0; | ||
134 | uint8_t bugbootname[256]; | ||
135 | |||
136 | if ( (argc != 3) ) | ||
137 | { | ||
138 | fprintf(stderr, "usage: %s <kernel_image> <bugboot>\n",argv[0]); | ||
139 | exit(-1); | ||
140 | } | ||
141 | |||
142 | /* Get file args */ | ||
143 | |||
144 | /* kernel image file */ | ||
145 | if ((image_fd = open( argv[argptr] , 0)) < 0) | ||
146 | exit(-1); | ||
147 | argptr++; | ||
148 | 110 | ||
149 | /* bugboot file */ | 111 | if (argc != 3) { |
150 | if ( !strcmp( argv[argptr], "-" ) ) | 112 | fprintf(stderr, "usage: %s <kernel_image> <bugboot>\n",argv[0]); |
151 | bugboot_fd = 1; /* stdout */ | 113 | exit(-1); |
152 | else | 114 | } |
153 | if ((bugboot_fd = creat( argv[argptr] , 0755)) < 0) | ||
154 | exit(-1); | ||
155 | else | ||
156 | strcpy(bugbootname, argv[argptr]); | ||
157 | argptr++; | ||
158 | 115 | ||
159 | /* Set file position after ROM header block where zImage will be written */ | 116 | /* Get file args */ |
160 | lseek(bugboot_fd, HEADER_SIZE, SEEK_SET); | ||
161 | 117 | ||
162 | /* Copy kernel image into bugboot image */ | 118 | /* kernel image file */ |
163 | kernel_size = copy_image(image_fd, bugboot_fd); | 119 | if ((image_fd = open(argv[1] , 0)) < 0) |
164 | close(image_fd); | 120 | exit(-1); |
165 | 121 | ||
166 | /* Set file position to beginning where header/romboot will be written */ | 122 | /* bugboot file */ |
167 | lseek(bugboot_fd, 0, SEEK_SET); | 123 | if (!strcmp(argv[2], "-")) |
124 | bugboot_fd = 1; /* stdout */ | ||
125 | else if ((bugboot_fd = creat(argv[2] , 0755)) < 0) | ||
126 | exit(-1); | ||
168 | 127 | ||
169 | /* Write out BUG header/romboot */ | 128 | /* Set file position after ROM header block where zImage will be written */ |
170 | write_bugboot_header(bugboot_fd, kernel_size); | 129 | lseek(bugboot_fd, HEADER_SIZE, SEEK_SET); |
171 | 130 | ||
172 | /* Close bugboot file */ | 131 | /* Copy kernel image into bugboot image */ |
173 | close(bugboot_fd); | 132 | kernel_size = copy_image(image_fd, bugboot_fd, &checksum); |
174 | 133 | ||
175 | /* Reopen it as read/write */ | 134 | /* Set file position to beginning where header/romboot will be written */ |
176 | bugboot_fd = open(bugbootname, O_RDWR); | 135 | lseek(bugboot_fd, 0, SEEK_SET); |
177 | 136 | ||
178 | /* Calculate checksum */ | 137 | /* Write out BUG header/romboot */ |
179 | checksum = calc_checksum(bugboot_fd); | 138 | write_bugboot_header(bugboot_fd, kernel_size, &checksum); |
180 | 139 | ||
181 | /* Write out the calculated checksum */ | 140 | /* Write out the calculated checksum */ |
182 | write(bugboot_fd, &checksum, 2); | 141 | lseek(bugboot_fd, 0, SEEK_END); |
142 | write(bugboot_fd, &checksum, 2); | ||
183 | 143 | ||
184 | return 0; | 144 | /* Close bugboot file */ |
145 | close(bugboot_fd); | ||
146 | return 0; | ||
185 | } | 147 | } |
diff --git a/arch/ppc/boot/utils/mkprep.c b/arch/ppc/boot/utils/mkprep.c index f6d5a2f2fcf6..192bb397126f 100644 --- a/arch/ppc/boot/utils/mkprep.c +++ b/arch/ppc/boot/utils/mkprep.c | |||
@@ -15,279 +15,227 @@ | |||
15 | * Modified for Sparc hosted builds by Peter Wahl <PeterWahl@web.de> | 15 | * Modified for Sparc hosted builds by Peter Wahl <PeterWahl@web.de> |
16 | */ | 16 | */ |
17 | 17 | ||
18 | #include <fcntl.h> | ||
19 | #include <stdio.h> | 18 | #include <stdio.h> |
20 | #include <stdlib.h> | ||
21 | #include <string.h> | 19 | #include <string.h> |
22 | #include <strings.h> | 20 | #include <stdlib.h> |
23 | #include <sys/stat.h> | ||
24 | #include <unistd.h> | ||
25 | |||
26 | #define cpu_to_le32(x) le32_to_cpu((x)) | ||
27 | unsigned long le32_to_cpu(unsigned long x) | ||
28 | { | ||
29 | return (((x & 0x000000ffU) << 24) | | ||
30 | ((x & 0x0000ff00U) << 8) | | ||
31 | ((x & 0x00ff0000U) >> 8) | | ||
32 | ((x & 0xff000000U) >> 24)); | ||
33 | } | ||
34 | |||
35 | |||
36 | #define cpu_to_le16(x) le16_to_cpu((x)) | ||
37 | unsigned short le16_to_cpu(unsigned short x) | ||
38 | { | ||
39 | return (((x & 0x00ff) << 8) | | ||
40 | ((x & 0xff00) >> 8)); | ||
41 | } | ||
42 | |||
43 | #define cpu_to_be32(x) (x) | ||
44 | #define be32_to_cpu(x) (x) | ||
45 | #define cpu_to_be16(x) (x) | ||
46 | #define be16_to_cpu(x) (x) | ||
47 | 21 | ||
48 | /* size of read buffer */ | 22 | /* size of read buffer */ |
49 | #define SIZE 0x1000 | 23 | #define SIZE 0x1000 |
50 | 24 | ||
51 | |||
52 | typedef unsigned long dword_t; | ||
53 | typedef unsigned short word_t; | ||
54 | typedef unsigned char byte_t; | ||
55 | typedef byte_t block_t[512]; | ||
56 | typedef byte_t page_t[4096]; | ||
57 | |||
58 | |||
59 | /* | 25 | /* |
60 | * Partition table entry | 26 | * Partition table entry |
61 | * - from the PReP spec | 27 | * - from the PReP spec |
62 | */ | 28 | */ |
63 | typedef struct partition_entry { | 29 | typedef struct partition_entry { |
64 | byte_t boot_indicator; | 30 | unsigned char boot_indicator; |
65 | byte_t starting_head; | 31 | unsigned char starting_head; |
66 | byte_t starting_sector; | 32 | unsigned char starting_sector; |
67 | byte_t starting_cylinder; | 33 | unsigned char starting_cylinder; |
68 | 34 | ||
69 | byte_t system_indicator; | 35 | unsigned char system_indicator; |
70 | byte_t ending_head; | 36 | unsigned char ending_head; |
71 | byte_t ending_sector; | 37 | unsigned char ending_sector; |
72 | byte_t ending_cylinder; | 38 | unsigned char ending_cylinder; |
73 | 39 | ||
74 | dword_t beginning_sector; | 40 | unsigned char beginning_sector[4]; |
75 | dword_t number_of_sectors; | 41 | unsigned char number_of_sectors[4]; |
76 | } partition_entry_t; | 42 | } partition_entry_t; |
77 | 43 | ||
78 | #define BootActive 0x80 | 44 | #define BootActive 0x80 |
79 | #define SystemPrep 0x41 | 45 | #define SystemPrep 0x41 |
80 | 46 | ||
81 | void copy_image(int , int); | 47 | void copy_image(FILE *, FILE *); |
82 | void write_prep_partition(int , int ); | 48 | void write_prep_partition(FILE *, FILE *); |
83 | void write_asm_data( int in, int out ); | 49 | void write_asm_data(FILE *, FILE *); |
84 | 50 | ||
85 | unsigned int elfhdr_size = 65536; | 51 | unsigned int elfhdr_size = 65536; |
86 | 52 | ||
87 | int main(int argc, char *argv[]) | 53 | int main(int argc, char *argv[]) |
88 | { | 54 | { |
89 | int in_fd, out_fd; | 55 | FILE *in, *out; |
90 | int argptr = 1; | 56 | int argptr = 1; |
91 | unsigned int prep = 0; | 57 | int prep = 0; |
92 | unsigned int asmoutput = 0; | 58 | int asmoutput = 0; |
93 | 59 | ||
94 | if ( (argc < 3) || (argc > 4) ) | 60 | if (argc < 3 || argc > 4) { |
95 | { | 61 | fprintf(stderr, "usage: %s [-pbp] [-asm] <boot-file> <image>\n", |
96 | fprintf(stderr, "usage: %s [-pbp] [-asm] <boot-file> <image>\n",argv[0]); | 62 | argv[0]); |
97 | exit(-1); | 63 | exit(-1); |
98 | } | 64 | } |
99 | 65 | ||
100 | /* needs to handle args more elegantly -- but this is a small/simple program */ | 66 | /* needs to handle args more elegantly -- but this is a small/simple program */ |
101 | 67 | ||
102 | /* check for -pbp */ | 68 | /* check for -pbp */ |
103 | if ( !strcmp( argv[argptr], "-pbp" ) ) | 69 | if (!strcmp(argv[argptr], "-pbp")) { |
104 | { | 70 | prep = 1; |
105 | prep = 1; | 71 | argptr++; |
106 | argptr++; | 72 | } |
107 | } | 73 | |
108 | 74 | /* check for -asm */ | |
109 | /* check for -asm */ | 75 | if (!strcmp(argv[argptr], "-asm")) { |
110 | if ( !strcmp( argv[argptr], "-asm" ) ) | 76 | asmoutput = 1; |
111 | { | 77 | argptr++; |
112 | asmoutput = 1; | 78 | } |
113 | argptr++; | 79 | |
114 | } | 80 | /* input file */ |
115 | 81 | if (!strcmp(argv[argptr], "-")) | |
116 | /* input file */ | 82 | in = stdin; |
117 | if ( !strcmp( argv[argptr], "-" ) ) | 83 | else if (!(in = fopen(argv[argptr], "r"))) |
118 | in_fd = 0; /* stdin */ | 84 | exit(-1); |
119 | else | 85 | argptr++; |
120 | if ((in_fd = open( argv[argptr] , 0)) < 0) | 86 | |
121 | exit(-1); | 87 | /* output file */ |
122 | argptr++; | 88 | if (!strcmp(argv[argptr], "-")) |
123 | 89 | out = stdout; | |
124 | /* output file */ | 90 | else if (!(out = fopen(argv[argptr], "w"))) |
125 | if ( !strcmp( argv[argptr], "-" ) ) | 91 | exit(-1); |
126 | out_fd = 1; /* stdout */ | 92 | argptr++; |
127 | else | 93 | |
128 | if ((out_fd = creat( argv[argptr] , 0755)) < 0) | 94 | /* skip elf header in input file */ |
129 | exit(-1); | 95 | /*if ( !prep )*/ |
130 | argptr++; | 96 | fseek(in, elfhdr_size, SEEK_SET); |
131 | 97 | ||
132 | /* skip elf header in input file */ | 98 | /* write prep partition if necessary */ |
133 | /*if ( !prep )*/ | 99 | if (prep) |
134 | lseek(in_fd, elfhdr_size, SEEK_SET); | 100 | write_prep_partition(in, out); |
135 | 101 | ||
136 | /* write prep partition if necessary */ | 102 | /* write input image to bootimage */ |
137 | if ( prep ) | 103 | if (asmoutput) |
138 | write_prep_partition( in_fd, out_fd ); | 104 | write_asm_data(in, out); |
139 | 105 | else | |
140 | /* write input image to bootimage */ | 106 | copy_image(in, out); |
141 | if ( asmoutput ) | 107 | |
142 | write_asm_data( in_fd, out_fd ); | 108 | return 0; |
143 | else | ||
144 | copy_image(in_fd, out_fd); | ||
145 | |||
146 | return 0; | ||
147 | } | 109 | } |
148 | 110 | ||
149 | void write_prep_partition(int in, int out) | 111 | void store_le32(unsigned int v, unsigned char *p) |
150 | { | 112 | { |
151 | unsigned char block[512]; | 113 | p[0] = v; |
152 | partition_entry_t pe; | 114 | p[1] = v >>= 8; |
153 | dword_t *entry = (dword_t *)&block[0]; | 115 | p[2] = v >>= 8; |
154 | dword_t *length = (dword_t *)&block[sizeof(long)]; | 116 | p[3] = v >> 8; |
155 | struct stat info; | 117 | } |
156 | 118 | ||
157 | if (fstat(in, &info) < 0) | 119 | void write_prep_partition(FILE *in, FILE *out) |
158 | { | 120 | { |
159 | fprintf(stderr,"info failed\n"); | 121 | unsigned char block[512]; |
160 | exit(-1); | 122 | partition_entry_t pe; |
161 | } | 123 | unsigned char *entry = block; |
162 | 124 | unsigned char *length = block + 4; | |
163 | bzero( block, sizeof block ); | 125 | long pos = ftell(in), size; |
164 | 126 | ||
165 | /* set entry point and boot image size skipping over elf header */ | 127 | if (fseek(in, 0, SEEK_END) < 0) { |
166 | #ifdef __i386__ | 128 | fprintf(stderr,"info failed\n"); |
167 | *entry = 0x400/*+65536*/; | 129 | exit(-1); |
168 | *length = info.st_size-elfhdr_size+0x400; | 130 | } |
169 | #else | 131 | size = ftell(in); |
170 | *entry = cpu_to_le32(0x400/*+65536*/); | 132 | if (fseek(in, pos, SEEK_SET) < 0) { |
171 | *length = cpu_to_le32(info.st_size-elfhdr_size+0x400); | 133 | fprintf(stderr,"info failed\n"); |
172 | #endif /* __i386__ */ | 134 | exit(-1); |
173 | 135 | } | |
174 | /* sets magic number for msdos partition (used by linux) */ | 136 | |
175 | block[510] = 0x55; | 137 | memset(block, '\0', sizeof(block)); |
176 | block[511] = 0xAA; | 138 | |
177 | 139 | /* set entry point and boot image size skipping over elf header */ | |
178 | /* | 140 | store_le32(0x400/*+65536*/, entry); |
179 | * Build a "PReP" partition table entry in the boot record | 141 | store_le32(size-elfhdr_size+0x400, length); |
180 | * - "PReP" may only look at the system_indicator | 142 | |
181 | */ | 143 | /* sets magic number for msdos partition (used by linux) */ |
182 | pe.boot_indicator = BootActive; | 144 | block[510] = 0x55; |
183 | pe.system_indicator = SystemPrep; | 145 | block[511] = 0xAA; |
184 | /* | 146 | |
185 | * The first block of the diskette is used by this "boot record" which | 147 | /* |
186 | * actually contains the partition table. (The first block of the | 148 | * Build a "PReP" partition table entry in the boot record |
187 | * partition contains the boot image, but I digress...) We'll set up | 149 | * - "PReP" may only look at the system_indicator |
188 | * one partition on the diskette and it shall contain the rest of the | 150 | */ |
189 | * diskette. | 151 | pe.boot_indicator = BootActive; |
190 | */ | 152 | pe.system_indicator = SystemPrep; |
191 | pe.starting_head = 0; /* zero-based */ | 153 | /* |
192 | pe.starting_sector = 2; /* one-based */ | 154 | * The first block of the diskette is used by this "boot record" which |
193 | pe.starting_cylinder = 0; /* zero-based */ | 155 | * actually contains the partition table. (The first block of the |
194 | pe.ending_head = 1; /* assumes two heads */ | 156 | * partition contains the boot image, but I digress...) We'll set up |
195 | pe.ending_sector = 18; /* assumes 18 sectors/track */ | 157 | * one partition on the diskette and it shall contain the rest of the |
196 | pe.ending_cylinder = 79; /* assumes 80 cylinders/diskette */ | 158 | * diskette. |
197 | 159 | */ | |
198 | /* | 160 | pe.starting_head = 0; /* zero-based */ |
199 | * The "PReP" software ignores the above fields and just looks at | 161 | pe.starting_sector = 2; /* one-based */ |
200 | * the next two. | 162 | pe.starting_cylinder = 0; /* zero-based */ |
201 | * - size of the diskette is (assumed to be) | 163 | pe.ending_head = 1; /* assumes two heads */ |
202 | * (2 tracks/cylinder)(18 sectors/tracks)(80 cylinders/diskette) | 164 | pe.ending_sector = 18; /* assumes 18 sectors/track */ |
203 | * - unlike the above sector numbers, the beginning sector is zero-based! | 165 | pe.ending_cylinder = 79; /* assumes 80 cylinders/diskette */ |
204 | */ | 166 | |
167 | /* | ||
168 | * The "PReP" software ignores the above fields and just looks at | ||
169 | * the next two. | ||
170 | * - size of the diskette is (assumed to be) | ||
171 | * (2 tracks/cylinder)(18 sectors/tracks)(80 cylinders/diskette) | ||
172 | * - unlike the above sector numbers, the beginning sector is zero-based! | ||
173 | */ | ||
205 | #if 0 | 174 | #if 0 |
206 | pe.beginning_sector = cpu_to_le32(1); | 175 | store_le32(1, pe.beginning_sector); |
207 | #else | ||
208 | /* This has to be 0 on the PowerStack? */ | ||
209 | #ifdef __i386__ | ||
210 | pe.beginning_sector = 0; | ||
211 | #else | 176 | #else |
212 | pe.beginning_sector = cpu_to_le32(0); | 177 | /* This has to be 0 on the PowerStack? */ |
213 | #endif /* __i386__ */ | 178 | store_le32(0, pe.beginning_sector); |
214 | #endif | 179 | #endif |
215 | 180 | ||
216 | #ifdef __i386__ | 181 | store_le32(2*18*80-1, pe.number_of_sectors); |
217 | pe.number_of_sectors = 2*18*80-1; | ||
218 | #else | ||
219 | pe.number_of_sectors = cpu_to_le32(2*18*80-1); | ||
220 | #endif /* __i386__ */ | ||
221 | 182 | ||
222 | memcpy(&block[0x1BE], &pe, sizeof(pe)); | 183 | memcpy(&block[0x1BE], &pe, sizeof(pe)); |
223 | 184 | ||
224 | write( out, block, sizeof(block) ); | 185 | fwrite(block, sizeof(block), 1, out); |
225 | write( out, entry, sizeof(*entry) ); | 186 | fwrite(entry, 4, 1, out); |
226 | write( out, length, sizeof(*length) ); | 187 | fwrite(length, 4, 1, out); |
227 | /* set file position to 2nd sector where image will be written */ | 188 | /* set file position to 2nd sector where image will be written */ |
228 | lseek( out, 0x400, SEEK_SET ); | 189 | fseek( out, 0x400, SEEK_SET ); |
229 | } | 190 | } |
230 | 191 | ||
231 | 192 | ||
232 | 193 | ||
233 | void | 194 | void copy_image(FILE *in, FILE *out) |
234 | copy_image(int in, int out) | ||
235 | { | 195 | { |
236 | char buf[SIZE]; | 196 | char buf[SIZE]; |
237 | int n; | 197 | int n; |
238 | 198 | ||
239 | while ( (n = read(in, buf, SIZE)) > 0 ) | 199 | while ( (n = fread(buf, 1, SIZE, in)) > 0 ) |
240 | write(out, buf, n); | 200 | fwrite(buf, 1, n, out); |
241 | } | 201 | } |
242 | 202 | ||
243 | 203 | ||
244 | void | 204 | void |
245 | write_asm_data( int in, int out ) | 205 | write_asm_data(FILE *in, FILE *out) |
246 | { | 206 | { |
247 | int i, cnt, pos, len; | 207 | int i, cnt, pos = 0; |
248 | unsigned int cksum, val; | 208 | unsigned int cksum = 0, val; |
249 | unsigned char *lp; | 209 | unsigned char *lp; |
250 | unsigned char buf[SIZE]; | 210 | unsigned char buf[SIZE]; |
251 | unsigned char str[256]; | 211 | size_t len; |
252 | 212 | ||
253 | write( out, "\t.data\n\t.globl input_data\ninput_data:\n", | 213 | fputs("\t.data\n\t.globl input_data\ninput_data:\n", out); |
254 | strlen( "\t.data\n\t.globl input_data\ninput_data:\n" ) ); | 214 | while ((len = fread(buf, 1, sizeof(buf), in)) > 0) { |
255 | pos = 0; | 215 | cnt = 0; |
256 | cksum = 0; | 216 | lp = buf; |
257 | while ((len = read(in, buf, sizeof(buf))) > 0) | 217 | /* Round up to longwords */ |
258 | { | 218 | while (len & 3) |
259 | cnt = 0; | 219 | buf[len++] = '\0'; |
260 | lp = (unsigned char *)buf; | 220 | for (i = 0; i < len; i += 4) { |
261 | len = (len + 3) & ~3; /* Round up to longwords */ | 221 | if (cnt == 0) |
262 | for (i = 0; i < len; i += 4) | 222 | fputs("\t.long\t", out); |
263 | { | 223 | fprintf(out, "0x%02X%02X%02X%02X", |
264 | if (cnt == 0) | 224 | lp[0], lp[1], lp[2], lp[3]); |
265 | { | 225 | val = *(unsigned long *)lp; |
266 | write( out, "\t.long\t", strlen( "\t.long\t" ) ); | 226 | cksum ^= val; |
267 | } | 227 | lp += 4; |
268 | sprintf( str, "0x%02X%02X%02X%02X", lp[0], lp[1], lp[2], lp[3]); | 228 | if (++cnt == 4) { |
269 | write( out, str, strlen(str) ); | 229 | cnt = 0; |
270 | val = *(unsigned long *)lp; | 230 | fprintf(out, " # %x \n", pos+i-12); |
271 | cksum ^= val; | 231 | } else { |
272 | lp += 4; | 232 | fputs(",", out); |
273 | if (++cnt == 4) | 233 | } |
274 | { | 234 | } |
275 | cnt = 0; | 235 | if (cnt) |
276 | sprintf( str, " # %x \n", pos+i-12); | 236 | fputs("0\n", out); |
277 | write( out, str, strlen(str) ); | 237 | pos += len; |
278 | } else | 238 | } |
279 | { | 239 | fprintf(out, "\t.globl input_len\ninput_len:\t.long\t0x%x\n", pos); |
280 | write( out, ",", 1 ); | 240 | fprintf(stderr, "cksum = %x\n", cksum); |
281 | } | ||
282 | } | ||
283 | if (cnt) | ||
284 | { | ||
285 | write( out, "0\n", 2 ); | ||
286 | } | ||
287 | pos += len; | ||
288 | } | ||
289 | sprintf(str, "\t.globl input_len\ninput_len:\t.long\t0x%x\n", pos); | ||
290 | write( out, str, strlen(str) ); | ||
291 | |||
292 | fprintf(stderr, "cksum = %x\n", cksum); | ||
293 | } | 241 | } |