Esempio n. 1
0
/* get_next_code()
 * - gets the next code from the GIF file.  Returns the code, or else
 * a negative number in case of file errors...
 */
static short get_next_code()
{
  short i, x;
  ULONG ret;

  if (nbits_left == 0)
    {
    if (navail_bytes <= 0)
      {

      /* Out of bytes in current block, so read next block
          */
      pbytes = byte_buff;
      if ((navail_bytes = gif_get_byte()) < 0)
        return(navail_bytes);
      else if (navail_bytes)
        {
        for (i = 0; i < navail_bytes; ++i)
          {
          if ((x = gif_get_byte()) < 0)
            return(x);
          byte_buff[i] = (UTINY) x;
          }
        }
      }
    b1 = *pbytes++;
    nbits_left = 8;
    --navail_bytes;
    }

  ret = b1 >> (8 - nbits_left);
  while (curr_size > nbits_left)
    {
    if (navail_bytes <= 0)
      {

      /* Out of bytes in current block, so read next block
          */
      pbytes = byte_buff;
      if ((navail_bytes = gif_get_byte()) < 0)
        return(navail_bytes);
      else if (navail_bytes)
        {
        for (i = 0; i < navail_bytes; ++i)
          {
          if ((x = gif_get_byte()) < 0)
            return(x);
          byte_buff[i] = (UTINY) x;
          }
        }
      }
    b1 = *pbytes++;
    ret |= b1 << nbits_left;
    nbits_left += 8;
    --navail_bytes;
    }
  nbits_left -= curr_size;
  ret &= code_mask[curr_size];
  return((short)(ret));
  }
Esempio n. 2
0
static short decoder(
		      short linewidth,
		      unsigned char far * buf,
		      unsigned char far * stack,
		      unsigned char far * suffix,
		      unsigned short far * prefix)
{
	unsigned char far *sp;
	unsigned char far *bufptr;
	register short code, fc, oc, bufcnt;
	short c, size, ret;

	/*
	 * Initialize for decoding a new image...
	 */
	if ((size = gif_get_byte()) < 0)
		return (size);
	if (size < 2 || 9 < size)
		return (BAD_CODE_SIZE);
	init_exp(size);

	/*
	 * Initialize in case they forgot to put in a clear code. (This
	 * shouldn't happen, but we'll try and decode it anyway...)
	 */
	oc = fc = 0;


	/*
	 * Set up the stack pointer and decode buffer pointer
	 */
	sp = stack;
	bufptr = buf;
	bufcnt = linewidth;

	/*
	 * This is the main loop.  For each code we get we pass through the
	 * linked list of prefix codes, pushing the corresponding "character"
	 * for each code onto the stack.  When the list reaches a single
	 * "character" we push that on the stack too, and then start
	 * unstacking each character for output in the correct order. Special
	 * handling is included for the clear code, and the whole thing ends
	 * when we get an ending code.
	 */
	while ((c = get_next_code()) != ending)
	{

		/*
		 * If we had a file error, return without completing the
		 * decode
		 */
		if (c < 0)
		{
			return (c);
		}

		/*
		 * If the code is a clear code, reinitialize all necessary
		 * items.
		 */
		if (c == clear)
		{
			curr_size = size + 1;
			slot = newcodes;
			top_slot = 1 << curr_size;

			/*
			 * Continue reading codes until we get a non-clear
			 * code (Another unlikely, but possible case...)
			 */
			while ((c = get_next_code()) == clear)
				;

			/*
			 * If we get an ending code immediately after a clear
			 * code (Yet another unlikely case), then break out
			 * of the loop.
			 */
			if (c == ending)
				break;

			/*
			 * Finally, if the code is beyond the range of
			 * already set codes, (This one had better NOT
			 * happen...  I have no idea what will result from
			 * this, but I doubt it will look good...) then set
			 * it to color zero.
			 */
			if (c >= slot)
				c = 0;

			oc = fc = c;

			/*
			 * And let us not forget to put the char into the
			 * buffer... And if, on the off chance, we were
			 * exactly one pixel from the end of the line, we
			 * have to send the buffer to the gif_out_line()
			 * routine...
			 */
			*bufptr++ = c;
			if (--bufcnt == 0)
			{
				if ((ret = gif_out_line(buf, linewidth)) < 0)
				{
					return (ret);
				}
				bufptr = buf;
				bufcnt = linewidth;
			}
		}
		else
		{

			/*
			 * In this case, it's not a clear code or an ending
			 * code, so it must be a code code...  So we can now
			 * decode the code into a stack of character codes.
			 * (Clear as mud, right?)
			 */
			code = c;

			/*
			 * Here we go again with one of those off chances...
			 * If, on the off chance, the code we got is beyond
			 * the range of those already set up (Another thing
			 * which had better NOT happen...) we trick the
			 * decoder into thinking it actually got the last
			 * code read. (Hmmn... I'm not sure why this works...
			 * But it does...)
			 */
			if (code >= slot)
			{
				if (code > slot)
					++bad_code_count;
				code = oc;
				*sp++ = fc;
			}

			/*
			 * Here we scan back along the linked list of
			 * prefixes, pushing helpless characters (ie.
			 * suffixes) onto the stack as we do so.
			 */
			while (code >= newcodes)
			{
				*sp++ = suffix[code];
				code = prefix[code];
			}

			/*
			 * Push the last character on the stack, and set up
			 * the new prefix and suffix, and if the required
			 * slot number is greater than that allowed by the
			 * current bit size, increase the bit size.  (NOTE -
			 * If we are all full, we *don't* save the new suffix
			 * and prefix...  I'm not certain if this is
			 * correct... it might be more proper to overwrite
			 * the last code...
			 */
			*sp++ = code;
			if (slot < top_slot)
			{
				suffix[slot] = fc = code;
				prefix[slot++] = oc;
				oc = c;
			}
			if (slot >= top_slot)
				if (curr_size < 12)
				{
					top_slot <<= 1;
					++curr_size;
				}

			/*
			 * Now that we've pushed the decoded string (in
			 * reverse order) onto the stack, lets pop it off and
			 * put it into our decode buffer...  And when the
			 * decode buffer is full, write another line...
			 */
			while (sp > stack)
			{
				*bufptr++ = *(--sp);
				if (--bufcnt == 0)
				{
					if ((ret = gif_out_line(buf, linewidth)) < 0)
					{
						return (ret);
					}
					bufptr = buf;
					bufcnt = linewidth;
				}
			}
		}
	}
	ret = 0;
	if (bufcnt != linewidth)
		ret = gif_out_line(buf, (linewidth - bufcnt));
	return (ret);
}
Esempio n. 3
0
short decoder (int i_linewidth)
{
  short linewidth;
  FAST UTINY *sp, *bufptr;
  UTINY *buf;
  FAST short code, fc, oc, bufcnt;
  short c, size, ret;

  linewidth = (short)i_linewidth;

  /* Initialize for decoding a new image...
    */
  if ((size = gif_get_byte()) < 0)
    return(size);
  if (size < 2 || 9 < size)
    return(BAD_CODE_SIZE);
  init_exp((int)size);        /* changed param to int */

  dstack = (UTINY *)POV_MALLOC((MAX_CODES + 1)*sizeof(UTINY), "GIF dstack");
  suffix = (UTINY *)POV_MALLOC((MAX_CODES + 1)*sizeof(UTINY), "GIF suffix");
  prefix = (UWORD *)POV_MALLOC((MAX_CODES + 1)*sizeof(UWORD), "GIF prefix");

  /* Initialize in case they forgot to put in a clear code.
    * (This shouldn't happen, but we'll try and decode it anyway...)
    */
  oc = fc = 0;

  buf = decoderline;

  bad_code_count = 0;

  /* Set up the stack pointer and decode buffer pointer
    */
  sp = dstack;
  bufptr = buf;
  bufcnt = linewidth;

  /* This is the main loop.  For each code we get we pass through the
    * linked list of prefix codes, pushing the corresponding "character" for
    * each code onto the stack.  When the list reaches a single "character"
    * we push that on the stack too, and then start unstacking each
    * character for output in the correct order.  Special handling is
    * included for the clear code, and the whole thing ends when we get
    * an ending code.
    */
  while ((c = get_next_code()) != ending)
    {

    Do_Cooperate(0);

    /* If we had a file error, return without completing the decode
       */
    if (c < 0) 
      {
      cleanup_gif_decoder();
      return(0);
      }

    /* If the code is a clear code, reinitialize all necessary items.
       */
    if (c == clear_code)
      {
      curr_size = size + 1;
      slot = newcodes;
      top_slot = 1 << curr_size;

      /* Continue reading codes until we get a non-clear code
          * (Another unlikely, but possible case...)
          */
      while ((c = get_next_code()) == clear_code)
        ;

      /* If we get an ending code immediately after a clear code
          * (Yet another unlikely case), then break out of the loop.
          */
      if (c == ending)
        break;

      /* Finally, if the code is beyond the range of already set codes,
          * (This one had better NOT happen...  I have no idea what will
          * result from this, but I doubt it will look good...) then set it
          * to color zero.
          */
      if (c >= slot)
        c = 0;

      oc = fc = c;

      /* And let us not forget to put the char into the buffer... And
          * if, on the off chance, we were exactly one pixel from the end
          * of the line, we have to send the buffer to the out_line()
          * routine...
          */
      *bufptr++ = (UTINY) c;
      if (--bufcnt == 0)
        {
        Do_Cooperate(1);
        if ((ret = out_line(buf, linewidth)) < 0) 
          {
          cleanup_gif_decoder();
          return(ret);
          }

        bufptr = buf;
        bufcnt = linewidth;
        }
      }
    else
      {

      /* In this case, it's not a clear code or an ending code, so
          * it must be a code code...  So we can now decode the code into
          * a stack of character codes. (Clear as mud, right?)
          */
      code = c;

      /* Here we go again with one of those off chances...  If, on the
          * off chance, the code we got is beyond the range of those already
          * set up (Another thing which had better NOT happen...) we trick
          * the decoder into thinking it actually got the last code read.
          * (Hmmn... I'm not sure why this works...  But it does...)
          */
      if (code >= slot)
        {
        if (code > slot)
          ++bad_code_count;
        code = oc;
        *sp++ = (UTINY) fc;
        }

      /* Here we scan back along the linked list of prefixes, pushing
          * helpless characters (ie. suffixes) onto the stack as we do so.
          */
      while (code >= newcodes)
        {
        *sp++ = suffix[code];
        code = prefix[code];
        }

      /* Push the last character on the stack, and set up the new
          * prefix and suffix, and if the required slot number is greater
          * than that allowed by the current bit size, increase the bit
          * size.  (NOTE - If we are all full, we *don't* save the new
          * suffix and prefix...  I'm not certain if this is correct...
          * it might be more proper to overwrite the last code...
          */
      *sp++ = (UTINY) code;
      if (slot < top_slot)
        {
        fc = code;
        suffix[slot] = (UTINY) fc;
        prefix[slot++] = oc;
        oc = c;
        }
      if (slot >= top_slot)
        if (curr_size < 12)
          {
          top_slot <<= 1;
          ++curr_size;
          }

      /* Now that we've pushed the decoded string (in reverse order)
          * onto the stack, lets pop it off and put it into our decode
          * buffer...  And when the decode buffer is full, write another
          * line...
          */
      while (sp > dstack)
        {
        *bufptr++ = *(--sp);
        if (--bufcnt == 0)
          {
          Do_Cooperate(1);
          if ((ret = out_line(buf, linewidth)) < 0) 
            {
            cleanup_gif_decoder();
            return(ret);
            }
          bufptr = buf;
          bufcnt = linewidth;
          }
        }
      }
    }
  ret = 0;
  if (bufcnt != linewidth)
    ret = out_line(buf, (linewidth - bufcnt));

  cleanup_gif_decoder();
  return(ret);
}