- #include <avr/io.h> 
- #include <avr/pgmspace.h> 
-   
- #include "mytypes.h" 
- #include "main.h" 
- #include "depacker_dirty.h" 
-   
-   
- UWORD dbpos; // current position in buffer (wrappable) 
-   
- UBYTE bitstream; 
- UBYTE bitcount; 
-   
- void depacker_dirty(void) 
- { 
-         UBYTE j; 
-   
-         UBYTE bits; 
-         WORD disp; 
-   
-   
-         dbpos=0; 
-   
-         // get first byte of packed file and write to output 
-         put_byte(NEXT_BYTE); 
-   
-   
-         // second byte goes to bitstream 
-         bitstream=NEXT_BYTE; 
-         bitcount=8; 
-   
-   
-         // actual depacking loop! 
-         do 
-         { 
-                 j=0; 
-   
-                 // get 1st bit - either OUTBYTE or beginning of LZ code 
-                 if( get_bits_dirty(1) ) 
-                 { // OUTBYTE 
-                         put_byte(NEXT_BYTE); 
-                 } 
-                 else 
-                 { // LZ code 
-                         switch( get_bits_dirty(2) ) 
-                         { 
-                         case 0: // 000 
-                                 repeat( 0xFFF8|get_bits_dirty(3) ,1); 
-                                 break; 
-                         case 1: // 001 
-                                 repeat( 0xFF00|NEXT_BYTE ,2); 
-                                 break; 
-                         case 2: // 010 
-                                 repeat(get_bigdisp_dirty(),3); 
-                                 break; 
-                         case 3: // 011 
-                                 // extract num of length bits 
-                                 do j++; while( !get_bits_dirty(1) ); 
-   
-                                 if( j<8 ) // check for exit code 
-                                 { 
-                                         // get length bits itself 
-                                         bits=get_bits_dirty(j); 
-                                         disp=get_bigdisp_dirty(); 
-                                         repeat(disp,2+(1<<j)+bits); 
-                                 } 
-                                 break; 
-                         } 
-                 } 
-   
-         } while( j<8 ); 
-   
-   
-         if( (DBMASK&dbpos) ) 
-         { 
-                 put_buffer(DBMASK&dbpos); 
-         } 
-   
- } 
-   
-   
-   
-   
- void repeat(WORD disp,UBYTE len) 
- { // repeat len bytes with disp displacement (negative) 
-   // uses dbpos & dbuf 
-   
-         UBYTE i; // since length is no more than 255 
-   
-         for(i=0;i<len;i++) 
-         { 
-                 put_byte(dbuf[DBMASK&(dbpos+disp)]); 
-         } 
- } 
-   
-   
-   
-   
- void put_byte(UBYTE byte) 
- { 
-         dbuf[dbpos]=byte; 
-         dbpos = DBMASK & (dbpos+1); 
-   
-         if( !dbpos ) 
-         { 
-                 put_buffer(DBSIZE); 
-         } 
- } 
-   
-   
- UBYTE get_bits_dirty(UBYTE numbits) 
- { // gets bits in a byte-wise style, no checks 
-   // numbits must be >0 
-   
-         UBYTE bits; 
-   
-         bits=0; 
-   
-         do 
-         { 
-                 if( !(bitcount--) ) 
-                 { 
-                         bitcount=7; 
-                         bitstream=NEXT_BYTE; 
-                 } 
-   
-                 bits = (bits<<1)|(bitstream>>7); // all shifts byte-wise 
-                 bitstream<<=1; 
-   
-         } while (--numbits); 
-   
-         return bits; 
- } 
-   
- WORD get_bigdisp_dirty(void) 
- { // fetches 'big' displacement (-1..-4352) 
-   // returns negative displacement 
-   
-         UBYTE bits; 
-   
-         if( get_bits_dirty(1) ) 
-         { // longer displacement 
-                 bits=get_bits_dirty(4); 
-                 return (((0xF0|bits)-1)<<8)|NEXT_BYTE; 
-         } 
-         else 
-         { // shorter displacement 
-                 return 0xFF00|NEXT_BYTE; 
-         } 
- } 
-   
-