

/**-----------------------------------------------------------------------
  *   Bloque de includes, por fin me ocupan menos de una pagina de
  * impresisn, lo que hay que hacer para tener todos los prototipos..
  *
  **/

#include <stdlib.h>
#include <string.h>
#include <ctype.h>

#define NO_SUB_PRAGMAS
#include <libraries/xpksub.h>

#include "ilzr.h"

/**-----------------------------------------------------------------------
  *   Prototipos para todas estas paridas necesarias para compilar.
  *
  **/

long __saveds __asm XpksUnpackChunk( REG __a0 XPARAMS* xpar )
{
    /*  variables para input - output   */
  
register  CHARS       *inpb       = xpar->InBuf;
register  CHARS       *outb       = xpar->OutBuf;
register  CHARS       *bumpcode;
register  CHARS       *outbstart  = xpar->OutBuf;
register  signed char  shift      = 0;
          UBYTE        bitcount;
register  signed long  outbsize;
          ULONG        matchpos;
          ULONG        matchlen;      
          

  outbsize = *((unsigned short *)inpb);
  inpb    += 2;     /* short leido */

  bitcount = INIT_BIT_BUMP;
  bumpcode = &outb[ 1<<INIT_BIT_BUMP ]; 
  
  if( outbsize > xpar->OutBufLen )
    return( XPKERR_SMALLBUF );
  
  xpar->OutBufLen = outbsize; 
    
  while( outbsize > 0 )
    {
    if( *inpb & (0x80>>shift) )
      {
      if( (++shift) > 7 )
        {
        shift=0;
        inpb++;
        }
          
      *outb = ( ((ULONG *)inpb)[0] )>>(24-shift);
      outb++;
      inpb++;
      outbsize--;
      }
    else
      {
      if( ++shift > 7 )
        {
        shift=0;
        inpb++;
        }
      
      if( bumpcode <  outb )
        {
        bitcount++;
        bumpcode = &outbstart[ 1<<bitcount ];
        }

      matchpos = (( ((ULONG *)inpb)[0] ) >> ( 32 - bitcount - shift ) ) & ((1<<bitcount)-1);
      
      shift   = shift + bitcount - 8;    /* ALWAYS bitccount >= 8 */
      inpb++;
      if( shift > 7 )
        {
        shift-=8;
        inpb++;
        }
      
      matchlen = (( ((ULONG *)inpb)[0] ) >> ( 32 - BITS_LOOKAHEAD - shift ) ) & ((1<<BITS_LOOKAHEAD)-1);
      
      shift   += BITS_LOOKAHEAD;
      if( shift > 7 )
        {
        shift-=8;
        inpb++;
        }
        
      matchlen += MIN_MATCH;

      memcpy( outb , &outbstart[ matchpos ] , (size_t)matchlen );
      outb     += matchlen;

      outbsize -= matchlen;
      }
    }
  return( 0 );
}

/************************** End of ILZR.C *************************/
