Пример #1
0
long MP_modi(T x, long y) {
	assert(x);
	if (y == 0)
		RAISE(MP_Dividebyzero);
	else if (-BASE < y && y < BASE) {
		T z = tmp[2];
		int r;
		int sx = sign(x), sy = y < 0;
		if (sx) {
			XP_neg(nbytes, tmp[0], x, 1);
			x = tmp[0];
			x[nbytes-1] &= msb;
		}
		r = XP_quotient(nbytes, z, x, sy ? -y : y);
		if (sx != sy) {
			XP_neg(nbytes, z, z, 1);
			if (r != 0) {
				XP_diff(nbytes, z, z, 1);
				r = y - r;
			}
			z[nbytes-1] &= msb;
		} else if (sx && sign(z))
			RAISE(MP_Overflow);
		if (nbits < 8
		&& (y < -(1<<(nbits-1)) || y >= (1<<(nbits-1))))
			RAISE(MP_Overflow);
		return r;
	} else if (apply(MP_mod, tmp[2], x, y))
		RAISE(MP_Overflow);
	return MP_toint(tmp[2]);
}
Пример #2
0
T MP_div(T z, T x, T y) {
	int sx, sy;
	assert(x); assert(y); assert(z);
	sx = sign(x);
	sy = sign(y);
	if (sx) {
		XP_neg(nbytes, tmp[0], x, 1);
		x = tmp[0];
		x[nbytes-1] &= msb;
	}
	if (sy) {
		XP_neg(nbytes, tmp[1], y, 1);
		y = tmp[1];
		y[nbytes-1] &= msb;
	} else {
    	memcpy(tmp[1], y, nbytes);
    	y = tmp[1];
    }
	if (!XP_div(nbytes, z, x, nbytes, y, tmp[2], tmp[3]))
		RAISE(MP_Dividebyzero);
	if (sx != sy) {
		XP_neg(nbytes, z, z, 1);
		if (!iszero(tmp[2]))
			XP_diff(nbytes, z, z, 1);
		z[nbytes-1] &= msb;
	} else if (sx && sign(z))
		RAISE(MP_Overflow);
	return z;
}
Пример #3
0
static T sub(T z, T x, T y) {
    int borrow, n = y->ndigits;
    borrow = XP_sub(n, z->digits, x->digits,
                    y->digits, 0);
    if (x->ndigits > n)
        borrow = XP_diff(x->ndigits - n, &z->digits[n],
                         &x->digits[n], borrow);
    assert(borrow == 0);
    return normalize(z, z->size);
}
Пример #4
0
T MP_subui(T z, T x, unsigned long y) {
	assert(x); assert(z);
	if (y < BASE) {
		int borrow = XP_diff(nbytes, z, x, y);
		borrow |= z[nbytes-1]&~msb;
		z[nbytes-1] &= msb;
		if (borrow)
			RAISE(MP_Overflow);
	} else if (applyu(MP_subu, z, x, y))
		RAISE(MP_Overflow);
	return z;
}
Пример #5
0
T MP_subi(T z, T x, long y) {
	assert(x); assert(z);
	if (-BASE < y && y < BASE) {
		int sx = sign(x), sy = y < 0;
		if (sy)
			XP_sum (nbytes, z, x, -y);
		else
			XP_diff(nbytes, z, x,  y);
		z[nbytes-1] &= msb;
		if (sx != sy && sy == sign(z))
			RAISE(MP_Overflow);
		if (nbits < 8
		&& (y < -(1<<(nbits-1)) || y >= (1<<(nbits-1))))
			RAISE(MP_Overflow);
	} else if (apply(MP_sub, z, x, y))
		RAISE(MP_Overflow);
	return z;
}