lzss.c 1.8 KB

123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657
  1. /**************************************************************
  2. LZSS.C -- A Data Compression Program
  3. (tab = 4 spaces)
  4. ***************************************************************
  5. 4/6/1989 Haruhiko Okumura
  6. Use, distribute, and modify this program freely.
  7. Please send me your improved versions.
  8. PC-VAN SCIENCE
  9. NIFTY-Serve PAF01022
  10. CompuServe 74050,1022
  11. **************************************************************/
  12. #include <grub/types.h>
  13. #include <grub/macho.h>
  14. #define N 4096 /* size of ring buffer */
  15. #define F 18 /* upper limit for match_length */
  16. #define THRESHOLD 2 /* encode string into position and length
  17. if match_length is greater than this */
  18. #define NIL N /* index for root of binary search trees */
  19. #define EOF -1
  20. #define getc(file) ((src < srcend) ? *src++ : EOF)
  21. #define putc(c, file) (dst < dstend) ? (*dst++ = (c)) : 0;
  22. grub_size_t
  23. grub_decompress_lzss (grub_uint8_t *dst, grub_uint8_t *dstend,
  24. grub_uint8_t *src, grub_uint8_t *srcend)
  25. {
  26. int i, j, k, r, c;
  27. unsigned int flags;
  28. static unsigned char text_buf[N + F - 1];
  29. grub_uint8_t *dst0 = dst;
  30. for (i = 0; i < N - F; i++) text_buf[i] = ' ';
  31. r = N - F; flags = 0;
  32. for ( ; ; ) {
  33. if (((flags >>= 1) & 256) == 0) {
  34. if ((c = getc(infile)) == EOF) break;
  35. flags = c | 0xff00; /* uses higher byte cleverly */
  36. } /* to count eight */
  37. if (flags & 1) {
  38. if ((c = getc(infile)) == EOF) break;
  39. putc(c, outfile); text_buf[r++] = c; r &= (N - 1);
  40. } else {
  41. if ((i = getc(infile)) == EOF) break;
  42. if ((j = getc(infile)) == EOF) break;
  43. i |= ((j & 0xf0) << 4); j = (j & 0x0f) + THRESHOLD;
  44. for (k = 0; k <= j; k++) {
  45. c = text_buf[(i + k) & (N - 1)];
  46. putc(c, outfile); text_buf[r++] = c; r &= (N - 1);
  47. }
  48. }
  49. }
  50. return dst - dst0;
  51. }