Skip to content
This repository

HTTPS clone URL

Subversion checkout URL

You can clone with HTTPS or Subversion.

Download ZIP
Browse code

software: shell from original BIOS

  • Loading branch information...
commit 73fce596315df530d7ce04f34319f62058882886 1 parent ef0667d
Sébastien Bourdeauducq authored
3  software/bios/Makefile
@@ -18,11 +18,12 @@ bios.elf: linker.ld $(OBJECTS) libs
18 18
 bios-rescue.elf: linker-rescue.ld $(OBJECTS) libs
19 19
 
20 20
 %.elf:
21  
-	$(LD) $(LDFLAGS) -T $< -N -o $@ $(OBJECTS) -L$(M2DIR)/software/libbase -lbase
  21
+	$(LD) $(LDFLAGS) -T $< -N -o $@ $(OBJECTS) -L$(M2DIR)/software/libbase -L$(M2DIR)/software/libextra -lbase -lextra
22 22
 	chmod -x $@
23 23
 
24 24
 libs:
25 25
 	make -C $(M2DIR)/software/libbase
  26
+	make -C $(M2DIR)/software/libextra
26 27
 
27 28
 .PHONY: clean libs
28 29
 
453  software/bios/main.c
... ...
@@ -1,19 +1,454 @@
  1
+/*
  2
+ * Milkymist SoC (Software)
  3
+ * Copyright (C) 2007, 2008, 2009, 2010, 2011, 2012 Sebastien Bourdeauducq
  4
+ *
  5
+ * This program is free software: you can redistribute it and/or modify
  6
+ * it under the terms of the GNU General Public License as published by
  7
+ * the Free Software Foundation, version 3 of the License.
  8
+ *
  9
+ * This program is distributed in the hope that it will be useful,
  10
+ * but WITHOUT ANY WARRANTY; without even the implied warranty of
  11
+ * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
  12
+ * GNU General Public License for more details.
  13
+ *
  14
+ * You should have received a copy of the GNU General Public License
  15
+ * along with this program.  If not, see <http://www.gnu.org/licenses/>.
  16
+ */
  17
+
1 18
 #include <stdio.h>
2  
-#include <irq.h>
  19
+#include <console.h>
  20
+#include <string.h>
3 21
 #include <uart.h>
  22
+#include <system.h>
  23
+#include <board.h>
  24
+#include <irq.h>
  25
+#include <version.h>
  26
+#include <extra/crc.h>
  27
+
  28
+#include <hw/flash.h>
  29
+
  30
+enum {
  31
+	CSR_IE = 1, CSR_IM, CSR_IP, CSR_ICC, CSR_DCC, CSR_CC, CSR_CFG, CSR_EBA,
  32
+	CSR_DC, CSR_DEBA, CSR_JTX, CSR_JRX, CSR_BP0, CSR_BP1, CSR_BP2, CSR_BP3,
  33
+	CSR_WP0, CSR_WP1, CSR_WP2, CSR_WP3,
  34
+};
  35
+
  36
+/* General address space functions */
  37
+
  38
+#define NUMBER_OF_BYTES_ON_A_LINE 16
  39
+static void dump_bytes(unsigned int *ptr, int count, unsigned addr)
  40
+{
  41
+	char *data = (char *)ptr;
  42
+	int line_bytes = 0, i = 0;
  43
+
  44
+	putsnonl("Memory dump:");
  45
+	while(count > 0){
  46
+		line_bytes =
  47
+			(count > NUMBER_OF_BYTES_ON_A_LINE)?
  48
+				NUMBER_OF_BYTES_ON_A_LINE : count;
  49
+
  50
+		printf("\n0x%08x  ", addr);
  51
+		for(i=0;i<line_bytes;i++)
  52
+			printf("%02x ", *(unsigned char *)(data+i));
  53
+
  54
+		for(;i<NUMBER_OF_BYTES_ON_A_LINE;i++)
  55
+			printf("   ");
  56
+
  57
+		printf(" ");
  58
+
  59
+		for(i=0;i<line_bytes;i++) {
  60
+			if((*(data+i) < 0x20) || (*(data+i) > 0x7e))
  61
+				printf(".");
  62
+			else
  63
+				printf("%c", *(data+i));
  64
+		}
  65
+
  66
+		for(;i<NUMBER_OF_BYTES_ON_A_LINE;i++)
  67
+			printf(" ");
  68
+
  69
+		data += (char)line_bytes;
  70
+		count -= line_bytes;
  71
+		addr += line_bytes;
  72
+	}
  73
+	printf("\n");
  74
+}
  75
+
  76
+static void mr(char *startaddr, char *len)
  77
+{
  78
+	char *c;
  79
+	unsigned int *addr;
  80
+	unsigned int length;
  81
+
  82
+	if(*startaddr == 0) {
  83
+		printf("mr <address> [length]\n");
  84
+		return;
  85
+	}
  86
+	addr = (unsigned *)strtoul(startaddr, &c, 0);
  87
+	if(*c != 0) {
  88
+		printf("incorrect address\n");
  89
+		return;
  90
+	}
  91
+	if(*len == 0) {
  92
+		length = 1;
  93
+	} else {
  94
+		length = strtoul(len, &c, 0);
  95
+		if(*c != 0) {
  96
+			printf("incorrect length\n");
  97
+			return;
  98
+		}
  99
+	}
  100
+
  101
+	dump_bytes(addr, length, (unsigned)addr);
  102
+}
  103
+
  104
+static void mw(char *addr, char *value, char *count)
  105
+{
  106
+	char *c;
  107
+	unsigned int *addr2;
  108
+	unsigned int value2;
  109
+	unsigned int count2;
  110
+	unsigned int i;
  111
+
  112
+	if((*addr == 0) || (*value == 0)) {
  113
+		printf("mw <address> <value> [count]\n");
  114
+		return;
  115
+	}
  116
+	addr2 = (unsigned int *)strtoul(addr, &c, 0);
  117
+	if(*c != 0) {
  118
+		printf("incorrect address\n");
  119
+		return;
  120
+	}
  121
+	value2 = strtoul(value, &c, 0);
  122
+	if(*c != 0) {
  123
+		printf("incorrect value\n");
  124
+		return;
  125
+	}
  126
+	if(*count == 0) {
  127
+		count2 = 1;
  128
+	} else {
  129
+		count2 = strtoul(count, &c, 0);
  130
+		if(*c != 0) {
  131
+			printf("incorrect count\n");
  132
+			return;
  133
+		}
  134
+	}
  135
+	for (i=0;i<count2;i++) *addr2++ = value2;
  136
+}
  137
+
  138
+static void mc(char *dstaddr, char *srcaddr, char *count)
  139
+{
  140
+	char *c;
  141
+	unsigned int *dstaddr2;
  142
+	unsigned int *srcaddr2;
  143
+	unsigned int count2;
  144
+	unsigned int i;
  145
+
  146
+	if((*dstaddr == 0) || (*srcaddr == 0)) {
  147
+		printf("mc <dst> <src> [count]\n");
  148
+		return;
  149
+	}
  150
+	dstaddr2 = (unsigned int *)strtoul(dstaddr, &c, 0);
  151
+	if(*c != 0) {
  152
+		printf("incorrect destination address\n");
  153
+		return;
  154
+	}
  155
+	srcaddr2 = (unsigned int *)strtoul(srcaddr, &c, 0);
  156
+	if(*c != 0) {
  157
+		printf("incorrect source address\n");
  158
+		return;
  159
+	}
  160
+	if(*count == 0) {
  161
+		count2 = 1;
  162
+	} else {
  163
+		count2 = strtoul(count, &c, 0);
  164
+		if(*c != 0) {
  165
+			printf("incorrect count\n");
  166
+			return;
  167
+		}
  168
+	}
  169
+	for (i=0;i<count2;i++) *dstaddr2++ = *srcaddr2++;
  170
+}
  171
+
  172
+static void crc(char *startaddr, char *len)
  173
+{
  174
+	char *c;
  175
+	char *addr;
  176
+	unsigned int length;
  177
+
  178
+	if((*startaddr == 0)||(*len == 0)) {
  179
+		printf("crc <address> <length>\n");
  180
+		return;
  181
+	}
  182
+	addr = (char *)strtoul(startaddr, &c, 0);
  183
+	if(*c != 0) {
  184
+		printf("incorrect address\n");
  185
+		return;
  186
+	}
  187
+	length = strtoul(len, &c, 0);
  188
+	if(*c != 0) {
  189
+		printf("incorrect length\n");
  190
+		return;
  191
+	}
  192
+
  193
+	printf("CRC32: %08x\n", crc32((unsigned char *)addr, length));
  194
+}
  195
+
  196
+/* processor registers */
  197
+static int parse_csr(const char *csr)
  198
+{
  199
+	if(!strcmp(csr, "ie"))   return CSR_IE;
  200
+	if(!strcmp(csr, "im"))   return CSR_IM;
  201
+	if(!strcmp(csr, "ip"))   return CSR_IP;
  202
+	if(!strcmp(csr, "icc"))  return CSR_ICC;
  203
+	if(!strcmp(csr, "dcc"))  return CSR_DCC;
  204
+	if(!strcmp(csr, "cc"))   return CSR_CC;
  205
+	if(!strcmp(csr, "cfg"))  return CSR_CFG;
  206
+	if(!strcmp(csr, "eba"))  return CSR_EBA;
  207
+	if(!strcmp(csr, "dc"))   return CSR_DC;
  208
+	if(!strcmp(csr, "deba")) return CSR_DEBA;
  209
+	if(!strcmp(csr, "jtx"))  return CSR_JTX;
  210
+	if(!strcmp(csr, "jrx"))  return CSR_JRX;
  211
+	if(!strcmp(csr, "bp0"))  return CSR_BP0;
  212
+	if(!strcmp(csr, "bp1"))  return CSR_BP1;
  213
+	if(!strcmp(csr, "bp2"))  return CSR_BP2;
  214
+	if(!strcmp(csr, "bp3"))  return CSR_BP3;
  215
+	if(!strcmp(csr, "wp0"))  return CSR_WP0;
  216
+	if(!strcmp(csr, "wp1"))  return CSR_WP1;
  217
+	if(!strcmp(csr, "wp2"))  return CSR_WP2;
  218
+	if(!strcmp(csr, "wp3"))  return CSR_WP3;
  219
+
  220
+	return 0;
  221
+}
  222
+
  223
+static void rcsr(char *csr)
  224
+{
  225
+	unsigned int csr2;
  226
+	register unsigned int value;
  227
+
  228
+	if(*csr == 0) {
  229
+		printf("rcsr <csr>\n");
  230
+		return;
  231
+	}
  232
+
  233
+	csr2 = parse_csr(csr);
  234
+	if(csr2 == 0) {
  235
+		printf("incorrect csr\n");
  236
+		return;
  237
+	}
  238
+
  239
+	switch(csr2) {
  240
+		case CSR_IE:   asm volatile ("rcsr %0,ie":"=r"(value)); break;
  241
+		case CSR_IM:   asm volatile ("rcsr %0,im":"=r"(value)); break;
  242
+		case CSR_IP:   asm volatile ("rcsr %0,ip":"=r"(value)); break;
  243
+		case CSR_CC:   asm volatile ("rcsr %0,cc":"=r"(value)); break;
  244
+		case CSR_CFG:  asm volatile ("rcsr %0,cfg":"=r"(value)); break;
  245
+		case CSR_EBA:  asm volatile ("rcsr %0,eba":"=r"(value)); break;
  246
+		case CSR_DEBA: asm volatile ("rcsr %0,deba":"=r"(value)); break;
  247
+		case CSR_JTX:  asm volatile ("rcsr %0,jtx":"=r"(value)); break;
  248
+		case CSR_JRX:  asm volatile ("rcsr %0,jrx":"=r"(value)); break;
  249
+		default: printf("csr write only\n"); return;
  250
+	}
  251
+
  252
+	printf("%08x\n", value);
  253
+}
  254
+
  255
+static void wcsr(char *csr, char *value)
  256
+{
  257
+	char *c;
  258
+	unsigned int csr2;
  259
+	register unsigned int value2;
  260
+
  261
+	if((*csr == 0) || (*value == 0)) {
  262
+		printf("wcsr <csr> <address>\n");
  263
+		return;
  264
+	}
  265
+
  266
+	csr2 = parse_csr(csr);
  267
+	if(csr2 == 0) {
  268
+		printf("incorrect csr\n");
  269
+		return;
  270
+	}
  271
+	value2 = strtoul(value, &c, 0);
  272
+	if(*c != 0) {
  273
+		printf("incorrect value\n");
  274
+		return;
  275
+	}
  276
+
  277
+	switch(csr2) {
  278
+		case CSR_IE:   asm volatile ("wcsr ie,%0"::"r"(value2)); break;
  279
+		case CSR_IM:   asm volatile ("wcsr im,%0"::"r"(value2)); break;
  280
+		case CSR_ICC:  asm volatile ("wcsr icc,%0"::"r"(value2)); break;
  281
+		case CSR_DCC:  asm volatile ("wcsr dcc,%0"::"r"(value2)); break;
  282
+		case CSR_EBA:  asm volatile ("wcsr eba,%0"::"r"(value2)); break;
  283
+		case CSR_DC:   asm volatile ("wcsr dcc,%0"::"r"(value2)); break;
  284
+		case CSR_DEBA: asm volatile ("wcsr deba,%0"::"r"(value2)); break;
  285
+		case CSR_JTX:  asm volatile ("wcsr jtx,%0"::"r"(value2)); break;
  286
+		case CSR_JRX:  asm volatile ("wcsr jrx,%0"::"r"(value2)); break;
  287
+		case CSR_BP0:  asm volatile ("wcsr bp0,%0"::"r"(value2)); break;
  288
+		case CSR_BP1:  asm volatile ("wcsr bp1,%0"::"r"(value2)); break;
  289
+		case CSR_BP2:  asm volatile ("wcsr bp2,%0"::"r"(value2)); break;
  290
+		case CSR_BP3:  asm volatile ("wcsr bp3,%0"::"r"(value2)); break;
  291
+		case CSR_WP0:  asm volatile ("wcsr wp0,%0"::"r"(value2)); break;
  292
+		case CSR_WP1:  asm volatile ("wcsr wp1,%0"::"r"(value2)); break;
  293
+		case CSR_WP2:  asm volatile ("wcsr wp2,%0"::"r"(value2)); break;
  294
+		case CSR_WP3:  asm volatile ("wcsr wp3,%0"::"r"(value2)); break;
  295
+		default: printf("csr read only\n"); return;
  296
+	}
  297
+}
  298
+
  299
+/* Init + command line */
  300
+
  301
+static void help()
  302
+{
  303
+	puts("Milkymist(tm) BIOS");
  304
+	puts("Don't know what to do? Try 'flashboot'.\n");
  305
+	puts("Available commands:");
  306
+	puts("mr         - read address space");
  307
+	puts("mw         - write address space");
  308
+	puts("mc         - copy address space");
  309
+	puts("crc        - compute CRC32 of a part of the address space");
  310
+	puts("rcsr       - read processor CSR");
  311
+	puts("wcsr       - write processor CSR");
  312
+	puts("version    - display version");
  313
+	puts("reboot     - system reset");
  314
+	puts("reconf     - reload FPGA configuration");
  315
+}
  316
+
  317
+static char *get_token(char **str)
  318
+{
  319
+	char *c, *d;
  320
+
  321
+	c = (char *)strchr(*str, ' ');
  322
+	if(c == NULL) {
  323
+		d = *str;
  324
+		*str = *str+strlen(*str);
  325
+		return d;
  326
+	}
  327
+	*c = 0;
  328
+	d = *str;
  329
+	*str = c+1;
  330
+	return d;
  331
+}
  332
+
  333
+static void do_command(char *c)
  334
+{
  335
+	char *token;
4 336
 
5  
-int main(void)
  337
+	token = get_token(&c);
  338
+
  339
+	if(strcmp(token, "mr") == 0) mr(get_token(&c), get_token(&c));
  340
+	else if(strcmp(token, "mw") == 0) mw(get_token(&c), get_token(&c), get_token(&c));
  341
+	else if(strcmp(token, "mc") == 0) mc(get_token(&c), get_token(&c), get_token(&c));
  342
+	else if(strcmp(token, "crc") == 0) crc(get_token(&c), get_token(&c));
  343
+
  344
+	else if(strcmp(token, "version") == 0) puts(VERSION);
  345
+	else if(strcmp(token, "reboot") == 0) reboot();
  346
+	else if(strcmp(token, "reconf") == 0) reconf();
  347
+
  348
+	else if(strcmp(token, "help") == 0) help();
  349
+
  350
+	else if(strcmp(token, "rcsr") == 0) rcsr(get_token(&c));
  351
+	else if(strcmp(token, "wcsr") == 0) wcsr(get_token(&c), get_token(&c));
  352
+
  353
+	else if(strcmp(token, "") != 0)
  354
+		printf("Command not found\n");
  355
+}
  356
+
  357
+int rescue;
  358
+extern unsigned int _edata;
  359
+
  360
+static void crcbios()
  361
+{
  362
+	unsigned int offset_bios;
  363
+	unsigned int length;
  364
+	unsigned int expected_crc;
  365
+	unsigned int actual_crc;
  366
+
  367
+	/*
  368
+	 * _edata is located right after the end of the flat
  369
+	 * binary image. The CRC tool writes the 32-bit CRC here.
  370
+	 * We also use the address of _edata to know the length
  371
+	 * of our code.
  372
+	 */
  373
+	offset_bios = rescue ? FLASH_OFFSET_RESCUE_BIOS : FLASH_OFFSET_REGULAR_BIOS;
  374
+	expected_crc = _edata;
  375
+	length = (unsigned int)&_edata - offset_bios;
  376
+	actual_crc = crc32((unsigned char *)offset_bios, length);
  377
+	if(expected_crc == actual_crc)
  378
+		printf("I: BIOS CRC passed (%08x)\n", actual_crc);
  379
+	else {
  380
+		printf("W: BIOS CRC failed (expected %08x, got %08x)\n", expected_crc, actual_crc);
  381
+		printf("W: The system will continue, but expect problems.\n");
  382
+	}
  383
+}
  384
+
  385
+static void print_mac()
  386
+{
  387
+	unsigned char *macadr = (unsigned char *)FLASH_OFFSET_MAC_ADDRESS;
  388
+
  389
+	printf("I: MAC address: %02x:%02x:%02x:%02x:%02x:%02x\n", macadr[0], macadr[1], macadr[2], macadr[3], macadr[4], macadr[5]);
  390
+}
  391
+
  392
+static const char banner[] =
  393
+	"\nMILKYMIST(tm) v"VERSION" BIOS   http://www.milkymist.org\n"
  394
+	"(c) Copyright 2007-2012 Sebastien Bourdeauducq\n\n"
  395
+	"This program is free software: you can redistribute it and/or modify\n"
  396
+	"it under the terms of the GNU General Public License as published by\n"
  397
+	"the Free Software Foundation, version 3 of the License.\n";
  398
+
  399
+static void readstr(char *s, int size)
  400
+{
  401
+	char c[2];
  402
+	int ptr;
  403
+
  404
+	c[1] = 0;
  405
+	ptr = 0;
  406
+	while(1) {
  407
+		c[0] = readchar();
  408
+		switch(c[0]) {
  409
+			case 0x7f:
  410
+			case 0x08:
  411
+				if(ptr > 0) {
  412
+					ptr--;
  413
+					putsnonl("\x08 \x08");
  414
+				}
  415
+				break;
  416
+			case 0x07:
  417
+				break;
  418
+			case '\r':
  419
+			case '\n':
  420
+				s[ptr] = 0x00;
  421
+				putsnonl("\n");
  422
+				return;
  423
+			default:
  424
+				putsnonl(c);
  425
+				s[ptr] = c[0];
  426
+				ptr++;
  427
+				break;
  428
+		}
  429
+	}
  430
+}
  431
+
  432
+int main(int i, char **c)
6 433
 {
7  
-	char c;
8  
-	
  434
+	char buffer[64];
  435
+
  436
+	rescue = !((unsigned int)main > FLASH_OFFSET_REGULAR_BIOS);
  437
+
9 438
 	irq_setmask(0);
10 439
 	irq_setie(1);
11 440
 	uart_init();
12  
-	
13  
-	printf("Hello World with IRQs\n");
14  
-	
  441
+	printf(banner);
  442
+	crcbios();
  443
+
  444
+	if(rescue)
  445
+		printf("I: Booting in rescue mode\n");
  446
+
  447
+	print_mac();
15 448
 	while(1) {
16  
-		c = uart_read();
17  
-		printf("You typed: %c\n", c);
  449
+		putsnonl("\e[1mBIOS>\e[0m ");
  450
+		readstr(buffer, 64);
  451
+		do_command(buffer);
18 452
 	}
  453
+	return 0;
19 454
 }
1  software/include/base/console.h
@@ -28,7 +28,6 @@ void console_set_read_hook(console_read_hook r, console_read_nonblock_hook rn);
28 28
 char readchar(void);
29 29
 int readchar_nonblock(void);
30 30
 
31  
-int puts(const char *s);
32 31
 void putsnonl(const char *s);
33 32
 
34 33
 #endif /* __CONSOLE_H */
3  software/include/base/stdio.h
@@ -20,6 +20,9 @@
20 20
 
21 21
 #include <stdlib.h>
22 22
 
  23
+int putchar(int c);
  24
+int puts(const char *s);
  25
+
23 26
 int snprintf(char *buf, size_t size, const char *fmt, ...);
24 27
 int scnprintf(char *buf, size_t size, const char *fmt, ...);
25 28
 int sprintf(char *buf, const char *fmt, ...);
25  software/libbase/console.c
@@ -19,8 +19,6 @@
19 19
 #include <console.h>
20 20
 #include <stdio.h>
21 21
 #include <stdarg.h>
22  
-#include <irq.h>
23  
-#include <hw/interrupts.h>
24 22
 
25 23
 static console_write_hook write_hook;
26 24
 static console_read_hook read_hook;
@@ -37,11 +35,12 @@ void console_set_read_hook(console_read_hook r, console_read_nonblock_hook rn)
37 35
 	read_nonblock_hook = rn;
38 36
 }
39 37
 
40  
-static void writechar(char c)
  38
+int putchar(int c)
41 39
 {
42 40
 	uart_write(c);
43 41
 	if(write_hook != NULL)
44 42
 		write_hook(c);
  43
+	return c;
45 44
 }
46 45
 
47 46
 char readchar(void)
@@ -62,34 +61,20 @@ int readchar_nonblock(void)
62 61
 
63 62
 int puts(const char *s)
64 63
 {
65  
-	unsigned int oldmask;
66  
-
67  
-	oldmask = irq_getmask();
68  
-	irq_setmask(IRQ_UART); // HACK: prevent UART data loss
69  
-
70 64
 	while(*s) {
71  
-		writechar(*s);
  65
+		putchar(*s);
72 66
 		s++;
73 67
 	}
74  
-	writechar('\n');
75  
-	
76  
-	irq_setmask(oldmask);
  68
+	putchar('\n');
77 69
 	return 1;
78 70
 }
79 71
 
80 72
 void putsnonl(const char *s)
81 73
 {
82  
-	unsigned int oldmask;
83  
-
84  
-	oldmask = irq_getmask();
85  
-	irq_setmask(IRQ_UART); // HACK: prevent UART data loss
86  
-	
87 74
 	while(*s) {
88  
-		writechar(*s);
  75
+		putchar(*s);
89 76
 		s++;
90 77
 	}
91  
-	
92  
-	irq_setmask(oldmask);
93 78
 }
94 79
 
95 80
 int printf(const char *fmt, ...)
18  software/libextra/Makefile
... ...
@@ -0,0 +1,18 @@
  1
+M2DIR=../..
  2
+include $(M2DIR)/software/include.mak
  3
+
  4
+OBJECTS=crc16.o crc32.o
  5
+
  6
+all: libextra.a
  7
+
  8
+# pull in dependency info for *existing* .o files
  9
+-include $(OBJECTS:.o=.d)
  10
+
  11
+libextra.a: $(OBJECTS)
  12
+	$(AR) clr libextra.a $(OBJECTS)
  13
+	$(RANLIB) libextra.a
  14
+
  15
+.PHONY: clean
  16
+
  17
+clean:
  18
+	rm -f $(OBJECTS) $(OBJECTS:.o=.d) libextra.a .*~ *~
2  software/libextra/crc16.c
... ...
@@ -1,4 +1,4 @@
1  
-#include <crc.h>
  1
+#include <extra/crc.h>
2 2
 
3 3
 static const unsigned int crc16_table[256] = {
4 4
 	0x0000, 0x1021, 0x2042, 0x3063, 0x4084, 0x50A5, 0x60C6, 0x70E7,
2  software/libextra/crc32.c
@@ -3,7 +3,7 @@
3 3
  * For conditions of distribution and use, see copyright notice in zlib.h
4 4
  */
5 5
 
6  
-#include <crc.h>
  6
+#include <extra/crc.h>
7 7
 
8 8
 static const unsigned int crc_table[256] = {
9 9
 	0x00000000L, 0x77073096L, 0xee0e612cL, 0x990951baL, 0x076dc419L,

0 notes on commit 73fce59

Please sign in to comment.
Something went wrong with that request. Please try again.