OpenCores
URL https://opencores.org/ocsvn/or1k/or1k/trunk

Subversion Repositories or1k

[/] [or1k/] [trunk/] [rc203soc/] [sw/] [uClinux/] [arch/] [ppc/] [boot/] [compressed/] [misc.c] - Blame information for rev 1765

Details | Compare with Previous | View Log

Line No. Rev Author Line
1 1624 jcastillo
/*
2
 * misc.c
3
 *
4
 * This is a collection of several routines from gzip-1.0.3
5
 * adapted for Linux.
6
 *
7
 * malloc by Hannu Savolainen 1993 and Matthias Urlichs 1994
8
 * puts by Nick Holloway 1993
9
 */
10
 
11
#include "gzip.h"
12
#include "lzw.h"
13
 
14
 
15
#define EOF -1
16
 
17
DECLARE(uch, inbuf, INBUFSIZ);
18
DECLARE(uch, outbuf, OUTBUFSIZ+OUTBUF_EXTRA);
19
DECLARE(uch, window, WSIZE);
20
 
21
unsigned outcnt;
22
unsigned insize;
23
unsigned inptr;
24
 
25
extern char input_data[];
26
extern int input_len;
27
 
28
int input_ptr;
29
 
30
int method, exit_code, part_nb, last_member;
31
int test = 0;
32
int force = 0;
33
int verbose = 1;
34
long bytes_in, bytes_out;
35
 
36
char *output_data;
37
unsigned long output_ptr;
38
 
39
extern int end;
40
long free_mem_ptr = (long)&end;
41
 
42
int to_stdout = 0;
43
int hard_math = 0;
44
 
45
void (*work)(int inf, int outf);
46
void makecrc(void);
47
 
48
local int get_method(int);
49
 
50
char *vidmem = (char *)0xC00B8000;
51
int lines, cols;
52
int orig_x, orig_y;
53
 
54
void puts(const char *);
55
 
56
void *malloc(int size)
57
{
58
        void *p;
59
 
60
        if (size <0) error("Malloc error\n");
61
        if (free_mem_ptr <= 0) error("Memory error\n");
62
 
63
   while(1) {
64
        free_mem_ptr = (free_mem_ptr + 3) & ~3; /* Align */
65
 
66
        p = (void *)free_mem_ptr;
67
        free_mem_ptr += size;
68
 
69
        /*
70
         * The part of the compressed kernel which has already been expanded
71
         * is no longer needed. Therefore we can reuse it for malloc.
72
         * With bigger kernels, this is necessary.
73
         */
74
 
75
        if (free_mem_ptr < (long)&end) {
76
                if (free_mem_ptr > (long)&input_data[input_ptr])
77
                        error("\nOut of memory\n");
78
 
79
                return p;
80
        }
81
#if 0   
82
        if (free_mem_ptr < 0x90000)
83
#endif  
84
        return p;
85
        puts("large kernel, low 1M tight...");
86
        free_mem_ptr = (long)input_data;
87
        }
88
}
89
 
90
void free(void *where)
91
{       /* Don't care */
92
}
93
 
94
static void scroll()
95
{
96
        int i;
97
 
98
        memcpy ( vidmem, vidmem + cols * 2, ( lines - 1 ) * cols * 2 );
99
        for ( i = ( lines - 1 ) * cols * 2; i < lines * cols * 2; i += 2 )
100
                vidmem[i] = ' ';
101
}
102
 
103
void puts(const char *s)
104
{
105
        int x,y;
106
        char c;
107
 
108
#if 0   
109
        x = SCREEN_INFO.orig_x;
110
        y = SCREEN_INFO.orig_y;
111
#else
112
        x = orig_x;
113
        y = orig_y;
114
#endif  
115
 
116
        while ( ( c = *s++ ) != '\0' ) {
117
                if ( c == '\n' ) {
118
                        x = 0;
119
                        if ( ++y >= lines ) {
120
                                scroll();
121
                                y--;
122
                        }
123
                } else {
124
                        vidmem [ ( x + cols * y ) * 2 ] = c;
125
                        if ( ++x >= cols ) {
126
                                x = 0;
127
                                if ( ++y >= lines ) {
128
                                        scroll();
129
                                        y--;
130
                                }
131
                        }
132
                }
133
        }
134
 
135
#if 0   
136
        SCREEN_INFO.orig_x = x;
137
        SCREEN_INFO.orig_y = y;
138
#else
139
        orig_x = x;
140
        orig_y = y;
141
#endif  
142
}
143
 
144
__ptr_t memset(__ptr_t s, int c, size_t n)
145
{
146
        int i;
147
        char *ss = (char*)s;
148
 
149
        for (i=0;i<n;i++) ss[i] = c;
150
}
151
 
152
__ptr_t memcpy(__ptr_t __dest, __const __ptr_t __src,
153
                            size_t __n)
154
{
155
        int i;
156
        char *d = (char *)__dest, *s = (char *)__src;
157
 
158
        for (i=0;i<__n;i++) d[i] = s[i];
159
}
160
 
161
int memcmp(__ptr_t __dest, __const __ptr_t __src,
162
                            size_t __n)
163
{
164
        int i;
165
        char *d = (char *)__dest, *s = (char *)__src;
166
 
167
        for (i=0;i<__n;i++, d++, s++)
168
        {
169
                if (*d != *s)
170
                {
171
                        return (*s - *d);
172
                }
173
        }
174
        return (0);
175
}
176
 
177
extern ulg crc_32_tab[];   /* crc table, defined below */
178
 
179
/* ===========================================================================
180
 * Run a set of bytes through the crc shift register.  If s is a NULL
181
 * pointer, then initialize the crc shift register contents instead.
182
 * Return the current crc in either case.
183
 */
184
ulg updcrc(s, n)
185
    uch *s;                 /* pointer to bytes to pump through */
186
    unsigned n;             /* number of bytes in s[] */
187
{
188
    register ulg c;         /* temporary variable */
189
 
190
    static ulg crc = (ulg)0xffffffffL; /* shift register contents */
191
 
192
    if (s == NULL) {
193
        c = 0xffffffffL;
194
    } else {
195
        c = crc;
196
        while (n--) {
197
            c = crc_32_tab[((int)c ^ (*s++)) & 0xff] ^ (c >> 8);
198
        }
199
    }
200
    crc = c;
201
    return c ^ 0xffffffffL;       /* (instead of ~c for 64-bit machines) */
202
}
203
 
204
/* ===========================================================================
205
 * Clear input and output buffers
206
 */
207
void clear_bufs()
208
{
209
    outcnt = 0;
210
    insize = inptr = 0;
211
    bytes_in = bytes_out = 0L;
212
}
213
 
214
/* ===========================================================================
215
 * Fill the input buffer. This is called only when the buffer is empty
216
 * and at least one byte is really needed.
217
 */
218
int fill_inbuf()
219
{
220
    int len, i;
221
 
222
    /* Read as much as possible */
223
puts("*");
224
    insize = 0;
225
    do {
226
        len = INBUFSIZ-insize;
227
        if (len > (input_len-input_ptr+1)) len=input_len-input_ptr+1;
228
        if (len == 0 || len == EOF) break;
229
 
230
        for (i=0;i<len;i++) inbuf[insize+i] = input_data[input_ptr+i];
231
        insize += len;
232
        input_ptr += len;
233
    } while (insize < INBUFSIZ);
234
 
235
    if (insize == 0) {
236
        error("unable to fill buffer\n");
237
    }
238
    bytes_in += (ulg)insize;
239
    inptr = 1;
240
    return inbuf[0];
241
}
242
 
243
/* ===========================================================================
244
 * Write the output window window[0..outcnt-1] and update crc and bytes_out.
245
 * (Used for the decompressed data only.)
246
 */
247
void flush_window()
248
{
249
    if (outcnt == 0) return;
250
    updcrc(window, outcnt);
251
 
252
    memcpy(&output_data[output_ptr], (char *)window, outcnt);
253
 
254
    bytes_out += (ulg)outcnt;
255
    output_ptr += (ulg)outcnt;
256
    outcnt = 0;
257
}
258
 
259
/*
260
 * Code to compute the CRC-32 table. Borrowed from
261
 * gzip-1.0.3/makecrc.c.
262
 */
263
 
264
ulg crc_32_tab[256];
265
 
266
void
267
makecrc(void)
268
{
269
/* Not copyrighted 1990 Mark Adler      */
270
 
271
  unsigned long c;      /* crc shift register */
272
  unsigned long e;      /* polynomial exclusive-or pattern */
273
  int i;                /* counter for all possible eight bit values */
274
  int k;                /* byte being shifted into crc apparatus */
275
 
276
  /* terms of polynomial defining this crc (except x^32): */
277
  static int p[] = {0,1,2,4,5,7,8,10,11,12,16,22,23,26};
278
 
279
  /* Make exclusive-or pattern from polynomial */
280
  e = 0;
281
  for (i = 0; i < sizeof(p)/sizeof(int); i++)
282
    e |= 1L << (31 - p[i]);
283
 
284
  crc_32_tab[0] = 0;
285
 
286
  for (i = 1; i < 256; i++)
287
  {
288
    c = 0;
289
    for (k = i | 256; k != 1; k >>= 1)
290
    {
291
      c = c & 1 ? (c >> 1) ^ e : c >> 1;
292
      if (k & 1)
293
        c ^= e;
294
    }
295
    crc_32_tab[i] = c;
296
  }
297
}
298
 
299
void error(char *x)
300
{
301
        puts("\n\n");
302
        puts(x);
303
        puts("\n\n -- System halted");
304
 
305
        while(1);       /* Halt */
306
}
307
 
308
#if 0
309
#define STACK_SIZE (4096)
310
 
311
long user_stack [STACK_SIZE];
312
 
313
struct {
314
        long * a;
315
        short b;
316
        } stack_start = { & user_stack [STACK_SIZE] , KERNEL_DS };
317
#endif
318
 
319
void decompress_kernel()
320
{
321
#if 0   
322
        if (SCREEN_INFO.orig_video_mode == 7)
323
                vidmem = (char *) 0xb0000;
324
        else
325
                vidmem = (char *) 0xb8000;
326
 
327
        lines = SCREEN_INFO.orig_video_lines;
328
        cols = SCREEN_INFO.orig_video_cols;
329
 
330
        if (EXT_MEM_K < 1024) error("<2M of mem\n");
331
        output_data = (char *)0x100000; /* Points to 1M */
332
#else
333
        output_data = (char *)0x0;      /* Points to 0 */
334
        lines = 25;
335
        cols = 80;
336
        orig_x = 0;
337
        orig_y = 24;
338
#endif  
339
 
340
        output_ptr = 0;
341
 
342
        exit_code = 0;
343
        test = 0;
344
        input_ptr = 0;
345
        part_nb = 0;
346
 
347
        clear_bufs();
348
        makecrc();
349
 
350
        puts("Uncompressing Linux...");
351
 
352
        method = get_method(0);
353
 
354
        work(0, 0);
355
 
356
        puts("done.\n");
357
 
358
        puts("Now booting the kernel\n");
359
}
360
 
361
/* ========================================================================
362
 * Check the magic number of the input file and update ofname if an
363
 * original name was given and to_stdout is not set.
364
 * Return the compression method, -1 for error, -2 for warning.
365
 * Set inptr to the offset of the next byte to be processed.
366
 * This function may be called repeatedly for an input file consisting
367
 * of several contiguous gzip'ed members.
368
 * IN assertions: there is at least one remaining compressed member.
369
 *   If the member is a zip file, it must be the only one.
370
 */
371
local int get_method(in)
372
    int in;        /* input file descriptor */
373
{
374
    uch flags;
375
    char magic[2]; /* magic header */
376
 
377
    magic[0] = (char)get_byte();
378
    magic[1] = (char)get_byte();
379
 
380
    method = -1;                 /* unknown yet */
381
    part_nb++;                   /* number of parts in gzip file */
382
    last_member = 0;
383
    /* assume multiple members in gzip file except for record oriented I/O */
384
 
385
    if (memcmp(magic, GZIP_MAGIC, 2) == 0
386
        || memcmp(magic, OLD_GZIP_MAGIC, 2) == 0) {
387
 
388
        work = unzip;
389
        method = (int)get_byte();
390
        flags  = (uch)get_byte();
391
        if ((flags & ENCRYPTED) != 0)
392
            error("Input is encrypted\n");
393
        if ((flags & CONTINUATION) != 0)
394
               error("Multi part input\n");
395
        if ((flags & RESERVED) != 0) {
396
            error("Input has invalid flags\n");
397
            exit_code = ERROR;
398
            if (force <= 1) return -1;
399
        }
400
        (ulg)get_byte();        /* Get timestamp */
401
        ((ulg)get_byte()) << 8;
402
        ((ulg)get_byte()) << 16;
403
        ((ulg)get_byte()) << 24;
404
 
405
        (void)get_byte();  /* Ignore extra flags for the moment */
406
        (void)get_byte();  /* Ignore OS type for the moment */
407
 
408
        if ((flags & EXTRA_FIELD) != 0) {
409
            unsigned len = (unsigned)get_byte();
410
            len |= ((unsigned)get_byte())<<8;
411
            while (len--) (void)get_byte();
412
        }
413
 
414
        /* Get original file name if it was truncated */
415
        if ((flags & ORIG_NAME) != 0) {
416
            if (to_stdout || part_nb > 1) {
417
                /* Discard the old name */
418
                while (get_byte() != 0) /* null */ ;
419
            } else {
420
            } /* to_stdout */
421
        } /* orig_name */
422
 
423
        /* Discard file comment if any */
424
        if ((flags & COMMENT) != 0) {
425
            while (get_byte() != 0) /* null */ ;
426
        }
427
    } else
428
        error("unknown compression method");
429
    return method;
430
}

powered by: WebSVN 2.1.0

© copyright 1999-2024 OpenCores.org, equivalent to Oliscience, all rights reserved. OpenCores®, registered trademark.