Ultrix-3.1/src/libape/shift.c

Compare this file to the similar file:
Show the results in this format:


/**********************************************************************
 *   Copyright (c) Digital Equipment Corporation 1984, 1985, 1986.    *
 *   All Rights Reserved. 					      *
 *   Reference "/usr/src/COPYRIGHT" for applicable restrictions.      *
 **********************************************************************/

/*	SCCSID: @(#)shift.c	3.0	4/22/86	*/
/*	(2.9BSD)		*/

#include "lint.h"
#include <stdio.h>
#include <ape.h>

#define odd(n)		((n)&01)
#define even(n)		!odd(n)

lshift(a,amount)	/* left shift a by amount words --
			 * i.e., multiply by 2^(15*amount) */
PMINT a;
int amount;
{
	short *temp;
	int i, negative, alen;
	char *realloc();

	negative = ( a->len < 0 );
	if (negative) a->len = -a->len;
	alen = a->len+amount;
	fmout(a,stderr);
	fputc('\n',stderr);
	temp = (short *) realloc ((char *)a->val, (unsigned) alen * sizeof(short) );
	fmout(a,stderr);
	fputc('\n',stderr);
	for (i = alen - 1; i >= amount; --i)
		temp[i] = temp[i-amount];
	for (i=0; i < amount; ++ i)
		temp[i] = 0;
	xfree(a);
	a->len = negative ? -alen : alen;
	a->val = temp;
}

mshift(a,answer,amount) /* same as lshift, except puts answer in answer */
PMINT a, answer;
int amount;
{
	short *temp;
	int i, negative, alen;

	negative = ( a->len < 0 );
	if (negative) 
		alen = amount - a->len;
	else
		alen = a->len+amount;
	temp =  xalloc (alen, "mshift");
	for (i = alen - 1; i >= amount; --i)
		temp[i] = a->val[i-amount];
	for (i=0; i < amount; ++ i)
		temp[i] = 0;
	xfree(answer);
	answer->len = negative ? -alen : alen;
	answer->val = temp;
}
rshift(a,amount)	/* right shift a by amount words --
			 * i.e., divide by 2^(15*amount) */
PMINT a;
int amount;
{
	char *realloc();
	int i, negative, alen;

	negative = ( a->len < 0 );
	if (negative) a->len = -a->len;
	alen = a->len-amount;
	if (alen <= 0) {
		xfree(a);
		return;
		}
	for (i=amount; i < a->len; ++i)
		a->val[i-amount] = a->val[i];
	a->val = (short *) realloc ((char *)a->val, (unsigned) alen * sizeof(short));
	a->len = negative ? -alen : alen;
}

powerof2(a,n)		/* a = a*2^n */
PMINT a;
int n;
{
	int wordshift, negative, bitshift, right,  i, oldcarry, newcarry;
	short mask;

	negative = a->len < 0;
	if (negative) a->len = -a->len;
	right = ( n < 0 );
	if (right) n = -n;
	wordshift = n/WORDLENGTH;
	bitshift = n%WORDLENGTH;
	if (right) {
		rshift(a, wordshift);
		mask = ~(~0 << bitshift);
		oldcarry = 0;
		for (i=a->len-1; i >= 0 ; --i) {
			newcarry = (a->val[i] & mask) << (WORDLENGTH-bitshift);
			a->val[i] = oldcarry + (a->val[i]>>bitshift);
			oldcarry = newcarry;
			}
		if (a->val[a->len-1] == 0)
			--a->len;
		}
	else {
		lshift(a, wordshift);
		mask = (~0 << WORDLENGTH-bitshift);
		oldcarry = 0;
		for (i=0; i < a->len; ++i) {
			newcarry = (a->val[i] & mask) >> (WORDLENGTH-bitshift);
			a->val[i] = oldcarry + (a->val[i]<<bitshift);
			oldcarry = newcarry;
			}
		if (oldcarry) {	/* rely on extra space given by xalloc */
			a->len += 1;
			a->val[a->len-1] = oldcarry;
			}
		}
	if (negative) a->len = -a->len;
	return;
}

oddpart(a)	/* replace a by its odd part, returning the no. of
		 * 2's in it */
PMINT a;
{
	int zerowords, zerobits;
	short nonzero;

	mcan(a);
	if (a->len == 0) return(0);
	for (zerowords=0; a->val[zerowords] == 0; ++zerowords)
		;
	nonzero = a->val[zerowords];
	zerobits = WORDLENGTH*zerowords;
	while (even(nonzero)) {
		++zerobits;
		nonzero <<= 1;
		}
	powerof2(a,zerobits);
	return(zerobits);
}