xref: /haiku/src/tools/fixup_amiga_boot_checksum/fixup_amiga_boot_checksum.c (revision 3c6e2dd68577c34d93e17f19711f6245bf6d0915)
1 #include <stdio.h>
2 #include <stdint.h>
3 #include <fcntl.h>
4 #include <unistd.h>
5 #include <netinet/in.h>
6 
7 #define BB_SIZE (2*512)
8 
9 int main(int argc, char **argv)
10 {
11 	int fd, i;
12 	uint32_t sum;
13 	uint8_t bootblock[BB_SIZE];
14 	uint32_t *p = (uint32_t *)bootblock;
15 	fd = open(argv[1], O_RDWR);
16 	if (fd < 0) {
17 		return 1;
18 	}
19 	if (read(fd, bootblock, BB_SIZE) < BB_SIZE) {
20 		perror("read");
21 		return 1;
22 	}
23 	if (ntohl(p[0]) != 'DOS\0') {
24 		fprintf(stderr, "bad bootblock signature!\n");
25 		return 1;
26 	}
27 	p[1] = 0;
28 	for (sum = 0, i = 0; i < (BB_SIZE)/sizeof(uint32_t); i++) {
29 		uint32_t old = sum;
30 		// big endian
31 		sum += ntohl(*p++);
32 		// overflow
33 		if (sum < old)
34 			sum++;
35 	}
36 	sum = ~sum;
37 	fprintf(stderr, "checksum: %lu\n", sum);
38 	// big endian
39 	((uint32_t *)bootblock)[1] = htonl(sum);
40 	lseek(fd, 0LL, SEEK_SET);
41 	write(fd, bootblock, BB_SIZE);
42 	return 0;
43 }
44