<commit_before>/*
 * RELIC is an Efficient LIbrary for Cryptography
 * Copyright (C) 2007, 2008, 2009 RELIC Authors
 *
 * This file is part of RELIC. RELIC is legal property of its developers,
 * whose names are not listed here. Please refer to the COPYRIGHT file
 * for contact information.
 *
 * RELIC is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * RELIC is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with RELIC. If not, see <http://www.gnu.org/licenses/>.
 */

/**
 * @file
 *
 * Implementation of the quartic extension binary field arithmetic module.
 *
 * The implementations of fb4_mul() and fb4_mul_spars() are based on:
 *
 * Beuchat et al., A comparison between hardware accelerators for the modified
 * Tate pairing over F_2^m and F_3^m, 2008.
 *
 * The implementation of fb4_mul_quart() is based on:
 *
 * Shirase et al., Efficient computation of Eta pairing over binary field with
 * Vandermonde matrix, 2008.
 *
 * and optimal 4-way Toom-Cook from:
 *
 * Bodrato, Towards optimal Toom-Cook multiplication for univariate and
 * multivariate polynomials in characteristic 2 and 0, 2007.
 *
 * @version $Id$
 * @ingroup pb
 */

#include <string.h>

#include "relic_core.h"
#include "relic_conf.h"
#include "relic_util.h"
#include "relic_pb.h"
#include "relic_fb_low.h"

/*============================================================================*/
/* Private definitions                                                        */
/*============================================================================*/

void fb_mul_beta(dig_t *c, dig_t *a) {
	int j, k;
	dig_t b1, b2;
	dv_t t;

	dv_null(t);

	TRY {
		dv_new(t);

#if WORD == 8
		fb_lshd_low(t, a, 1);
		t[FB_DIGS] = a[FB_DIGS - 1];
#else
		t[FB_DIGS] = fb_lshb_low(t, a, 8);
#endif

		j = FB_DIGIT - 6;
		b1 = a[0];
		t[0] ^= (b1 << 6);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 6) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);

		j = FB_DIGIT - 5;
		b1 = a[0];
		t[0] ^= (b1 << 5);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 5) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);

		j = FB_DIGIT - 3;
		b1 = a[0];
		t[0] ^= (b1 << 3);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 3) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);

		fb_rdc1_low(c, t);
	} CATCH_ANY {
		THROW(ERR_CAUGHT);
	} FINALLY {
		dv_free(t);
	}
}

void fb_mul_21(dig_t *c, dig_t *a) {
	int j, k;
	dig_t b1, b2;
	dv_t t;

	dv_null(t);

	TRY {
		dv_new(t);

		t[FB_DIGS] = fb_lshb_low(t, a, 2);

		j = FB_DIGIT - 1;
		b1 = a[0];
		t[0] ^= (b1 << 1);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 1) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);
		fb_rdc1_low(c, t);
	} CATCH_ANY {
		THROW(ERR_CAUGHT);
	} FINALLY {
		dv_free(t);
	}
}

void fb_mul_420(dig_t *c, dig_t *a) {
	int j, k;
	dig_t b1, b2;
	dv_t t;

	dv_null(t);

	TRY {
		dv_new(t);

		t[FB_DIGS] = fb_lshb_low(t, a, 4);

		j = FB_DIGIT - 2;
		b1 = a[0];
		t[0] ^= (b1 << 2);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 2) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);
		fb_addn_low(t, t, a);
		fb_rdc1_low(c, t);
	} CATCH_ANY {
		THROW(ERR_CAUGHT);
	} FINALLY {
		dv_free(t);
	}
}

void fb_mul_41(dig_t *c, dig_t *a) {
	int j, k;
	dig_t b1, b2;
	dv_t t;

	dv_null(t);

	TRY {
		dv_new(t);
		dv_new(u);

		t[FB_DIGS] = fb_lshb_low(t, a, 4);

		j = FB_DIGIT - 1;
		b1 = a[0];
		t[0] ^= (b1 << 1);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 1) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);
		fb_rdc1_low(c, t);
	} CATCH_ANY {
		THROW(ERR_CAUGHT);
	} FINALLY {
		dv_free(t);
	}
}

void fb_mul_42(dig_t *c, dig_t *a) {<commit_msg>Forgot to delete reference to a removed unused variable; fixed.<commit_after>/*
 * RELIC is an Efficient LIbrary for Cryptography
 * Copyright (C) 2007, 2008, 2009 RELIC Authors
 *
 * This file is part of RELIC. RELIC is legal property of its developers,
 * whose names are not listed here. Please refer to the COPYRIGHT file
 * for contact information.
 *
 * RELIC is free software; you can redistribute it and/or
 * modify it under the terms of the GNU Lesser General Public
 * License as published by the Free Software Foundation; either
 * version 2.1 of the License, or (at your option) any later version.
 *
 * RELIC is distributed in the hope that it will be useful,
 * but WITHOUT ANY WARRANTY; without even the implied warranty of
 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
 * Lesser General Public License for more details.
 *
 * You should have received a copy of the GNU Lesser General Public License
 * along with RELIC. If not, see <http://www.gnu.org/licenses/>.
 */

/**
 * @file
 *
 * Implementation of the quartic extension binary field arithmetic module.
 *
 * The implementations of fb4_mul() and fb4_mul_spars() are based on:
 *
 * Beuchat et al., A comparison between hardware accelerators for the modified
 * Tate pairing over F_2^m and F_3^m, 2008.
 *
 * The implementation of fb4_mul_quart() is based on:
 *
 * Shirase et al., Efficient computation of Eta pairing over binary field with
 * Vandermonde matrix, 2008.
 *
 * and optimal 4-way Toom-Cook from:
 *
 * Bodrato, Towards optimal Toom-Cook multiplication for univariate and
 * multivariate polynomials in characteristic 2 and 0, 2007.
 *
 * @version $Id$
 * @ingroup pb
 */

#include <string.h>

#include "relic_core.h"
#include "relic_conf.h"
#include "relic_util.h"
#include "relic_pb.h"
#include "relic_fb_low.h"

/*============================================================================*/
/* Private definitions                                                        */
/*============================================================================*/

void fb_mul_beta(dig_t *c, dig_t *a) {
	int j, k;
	dig_t b1, b2;
	dv_t t;

	dv_null(t);

	TRY {
		dv_new(t);

#if WORD == 8
		fb_lshd_low(t, a, 1);
		t[FB_DIGS] = a[FB_DIGS - 1];
#else
		t[FB_DIGS] = fb_lshb_low(t, a, 8);
#endif

		j = FB_DIGIT - 6;
		b1 = a[0];
		t[0] ^= (b1 << 6);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 6) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);

		j = FB_DIGIT - 5;
		b1 = a[0];
		t[0] ^= (b1 << 5);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 5) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);

		j = FB_DIGIT - 3;
		b1 = a[0];
		t[0] ^= (b1 << 3);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 3) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);

		fb_rdc1_low(c, t);
	} CATCH_ANY {
		THROW(ERR_CAUGHT);
	} FINALLY {
		dv_free(t);
	}
}

void fb_mul_21(dig_t *c, dig_t *a) {
	int j, k;
	dig_t b1, b2;
	dv_t t;

	dv_null(t);

	TRY {
		dv_new(t);

		t[FB_DIGS] = fb_lshb_low(t, a, 2);

		j = FB_DIGIT - 1;
		b1 = a[0];
		t[0] ^= (b1 << 1);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 1) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);
		fb_rdc1_low(c, t);
	} CATCH_ANY {
		THROW(ERR_CAUGHT);
	} FINALLY {
		dv_free(t);
	}
}

void fb_mul_420(dig_t *c, dig_t *a) {
	int j, k;
	dig_t b1, b2;
	dv_t t;

	dv_null(t);

	TRY {
		dv_new(t);

		t[FB_DIGS] = fb_lshb_low(t, a, 4);

		j = FB_DIGIT - 2;
		b1 = a[0];
		t[0] ^= (b1 << 2);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 2) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);
		fb_addn_low(t, t, a);
		fb_rdc1_low(c, t);
	} CATCH_ANY {
		THROW(ERR_CAUGHT);
	} FINALLY {
		dv_free(t);
	}
}

void fb_mul_41(dig_t *c, dig_t *a) {
	int j, k;
	dig_t b1, b2;
	dv_t t;

	dv_null(t);

	TRY {
		dv_new(t);

		t[FB_DIGS] = fb_lshb_low(t, a, 4);

		j = FB_DIGIT - 1;
		b1 = a[0];
		t[0] ^= (b1 << 1);
		for (k = 1; k < FB_DIGS; k++) {
			b2 = a[k];
			t[k] ^= ((b2 << 1) | (b1 >> j));
			b1 = b2;
		}
		t[FB_DIGS] ^= (b1 >> j);
		fb_rdc1_low(c, t);
	} CATCH_ANY {
		THROW(ERR_CAUGHT);
	} FINALLY {
		dv_free(t);
	}
}

void fb_mul_42(dig_t *c, dig_t *a) {
{'fraction_non_alphanumeric': 0.19952690715552926, 'fraction_numerical': 0.0345357776463631, 'mean_word_length': 2.8753437213565536, 'pattern_counts': {'":': 0, '<': 67, '<?xml version=': 0, '>': 55, 'https://': 0, 'lorem ipsum': 0, 'www.': 2, 'xml': 0}, 'pii_count': 0, 'substrings_counts': 0, 'word_list_counts': {'cursed_substrings.json': 4, 'profanity_word_list.json': 0, 'sexual_word_list.json': 0, 'zh_pornsignals.json': 0}}
{'dir': 'git-commits-cleaned', 'id': '5357267', 'n_tokens_mistral': 4218, 'n_tokens_neox': 3685, 'n_words': 1048}