#include "attack.h"
/* iff sq is attacked by side^1 return true */
int
attacked_by_white (int sq)
{
	register int    i, j;
	if (distance[128 + sq - kingsq[WHITE]] == 1)
		return 1;
	if (board[sq + 15] == WP)
		return 1;
	if (board[sq + 17] == WP)
		return 1;
	if (types[WN]) {
		for (i = 0; i < 8; ++i) {
			if (board[sq + dlta[i]] == WN)
				return 1;
		}
	}
	if (types[WB] || types[WQ]) {
		for (i = 8; i < 12; ++i) {
			j = sq;
			while (board[j += dlta[i]] == MT);
			if (board[j] == WB)
				return 1;
			if (board[j] == WQ)
				return 1;
		}
	}
	if (types[WR] || types[WQ]) {
		for (i = 12; i < 16; ++i) {
			j = sq;
			while (board[j += dlta[i]] == MT);
			if (board[j] == WR)
				return 1;
			if (board[j] == WQ)
				return 1;
		}
	}
	return 0;
}
int
attacked_by_black (int sq)
{
	register int    i, j;
	if (distance[128 + sq - kingsq[BLACK]] == 1)
		return 1;
	if (board[sq - 15] == BP)
		return 1;
	if (board[sq - 17] == BP)
		return 1;
	if (types[BN]) {
		for (i = 0; i < 8; ++i) {
			if (board[sq + dlta[i]] == BN)
				return 1;
		}
	}
	if (types[BB] || types[BQ]) {
		for (i = 8; i < 12; ++i) {
			j = sq;
			while (board[j += dlta[i]] == MT);
			if (board[j] == BB)
				return 1;
			if (board[j] == BQ)
				return 1;
		}
	}
	if (types[BR] || types[BQ]) {
		for (i = 12; i < 16; ++i) {
			j = sq;
			while (board[j += dlta[i]] == MT);
			if (board[j] == BR)
				return 1;
			if (board[j] == BQ)
				return 1;
		}
	}
	return 0;
}
int
attacked (int side, int sq)
{
	register int    i, j;
	assert (side == 0 || side == 1);
	assert (((sq - A1) & 0x88) == 0);
	if (side) {
		if (board[sq - 17] == BP)
			return 1;
		if (board[sq - 15] == BP)
			return 1;
		if (types[BN]) {
			for (i = 0; i < 8; ++i)
				if (board[sq + dlta[i]] == BN)
					return 1;
		}
		if (types[BB] || types[BQ]) {
			for (i = 8; i < 12; ++i) {
				j = sq;
				while (board[j += dlta[i]] == MT);
				if ((board[j] & 11) == 10)
					return 1;
			}
		}
		if (types[BR] || types[BQ]) {
			for (i = 12; i < 16; ++i) {
				j = sq;
				while (board[j += dlta[i]] == MT);
				if ((board[j] & 13) == 12)
					return 1;
			}
		}
		if (distance[128 + sq - kingsq[0]] == 1)
			return 1;
		return 0;
	} else {
		if (board[sq + 17] == WP)
			return 1;
		if (board[sq + 15] == WP)
			return 1;
		if (types[WN]) {
			for (i = 0; i < 8; ++i)
				if (board[sq + dlta[i]] == WN)
					return 1;
		}
		if (types[WB] || types[WQ]) {
			for (i = 8; i < 12; ++i) {
				j = sq;
				while (board[j += dlta[i]] == MT);
				if ((board[j] & 11) == 11)
					return 1;
			}
		}
		if (types[WR] || types[WQ]) {
			for (i = 12; i < 16; ++i) {
				j = sq;
				while (board[j += dlta[i]] == MT);
				if ((board[j] & 13) == 13)
					return 1;
			}
		}
		if (distance[128 + sq - kingsq[1]] == 1)
			return 1;
		return 0;
	}
}

int
inCheck (int c)
{
assert(pieces[1][0] == kingsq[1] && pieces[0][0] == kingsq[0]);
	return (c) ? attacked_by_black (kingsq[1]) : attacked_by_white (kingsq[0]);
}


int
raytrace (int vs)
{
	int             dest, delta, snm, offender, p;
	snm = stm ^ 1;
	delta = -vectors[136 + vs - kingsq[snm]];
	if (delta == 0) {
		return 0;
	}
	offender = (abs (delta) == 15 || abs (delta) == 17) ? (BB | stm) : (BR | stm);
	dest = kingsq[snm] + delta;
	while (board[dest] == MT)
		dest += delta;
	p = board[dest];
	if (p == offender || p == (BQ | stm)) {
		return 1;
	}
	return 0;
}
