/* ec.c -  Elliptic Curve functions
 * Copyright (C) 2007 Free Software Foundation, Inc.
 * Copyright (C) 2013 g10 Code GmbH
 *
 * This file is part of Libgcrypt.
 *
 * Libgcrypt 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.
 *
 * Libgcrypt 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 this program; if not, see <http://www.gnu.org/licenses/>.
 */

#include "mpi-internal.h"
#include "longlong.h"

#define point_init(a)  mpi_point_init((a))
#define point_free(a)  mpi_point_free_parts((a))

#define log_error(fmt, ...) pr_err(fmt, ##__VA_ARGS__)
#define log_fatal(fmt, ...) pr_err(fmt, ##__VA_ARGS__)

#define DIM(v) (sizeof(v)/sizeof((v)[0]))


/* Create a new point option.  NBITS gives the size in bits of one
 * coordinate; it is only used to pre-allocate some resources and
 * might also be passed as 0 to use a default value.
 */
MPI_POINT mpi_point_new(unsigned int nbits)
{
	MPI_POINT p;

	(void)nbits;  /* Currently not used.  */

	p = kmalloc(sizeof(*p), GFP_KERNEL);
	if (p)
		mpi_point_init(p);
	return p;
}
EXPORT_SYMBOL_GPL(mpi_point_new);

/* Release the point object P.  P may be NULL. */
void mpi_point_release(MPI_POINT p)
{
	if (p) {
		mpi_point_free_parts(p);
		kfree(p);
	}
}
EXPORT_SYMBOL_GPL(mpi_point_release);

/* Initialize the fields of a point object.  gcry_mpi_point_free_parts
 * may be used to release the fields.
 */
void mpi_point_init(MPI_POINT p)
{
	p->x = mpi_new(0);
	p->y = mpi_new(0);
	p->z = mpi_new(0);
}
EXPORT_SYMBOL_GPL(mpi_point_init);

/* Release the parts of a point object. */
void mpi_point_free_parts(MPI_POINT p)
{
	mpi_free(p->x); p->x = NULL;
	mpi_free(p->y); p->y = NULL;
	mpi_free(p->z); p->z = NULL;
}
EXPORT_SYMBOL_GPL(mpi_point_free_parts);

/* Set the value from S into D.  */
static void point_set(MPI_POINT d, MPI_POINT s)
{
	mpi_set(d->x, s->x);
	mpi_set(d->y, s->y);
	mpi_set(d->z, s->z);
}

static void point_resize(MPI_POINT p, struct mpi_ec_ctx *ctx)
{
	size_t nlimbs = ctx->p->nlimbs;

	mpi_resize(p->x, nlimbs);
	p->x->nlimbs = nlimbs;
	mpi_resize(p->z, nlimbs);
	p->z->nlimbs = nlimbs;

	if (ctx->model != MPI_EC_MONTGOMERY) {
		mpi_resize(p->y, nlimbs);
		p->y->nlimbs = nlimbs;
	}
}

static void point_swap_cond(MPI_POINT d, MPI_POINT s, unsigned long swap,
		struct mpi_ec_ctx *ctx)
{
	mpi_swap_cond(d->x, s->x, swap);
	if (ctx->model != MPI_EC_MONTGOMERY)
		mpi_swap_cond(d->y, s->y, swap);
	mpi_swap_cond(d->z, s->z, swap);
}


/* W = W mod P.  */
static void ec_mod(MPI w, struct mpi_ec_ctx *ec)
{
	if (ec->t.p_barrett)
		mpi_mod_barrett(w, w, ec->t.p_barrett);
	else
		mpi_mod(w, w, ec->p);
}

static void ec_addm(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx)
{
	mpi_add(w, u, v);
	ec_mod(w, ctx);
}

static void ec_subm(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ec)
{
	mpi_sub(w, u, v);
	while (w->sign)
		mpi_add(w, w, ec->p);
	/*ec_mod(w, ec);*/
}

static void ec_mulm(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx)
{
	mpi_mul(w, u, v);
	ec_mod(w, ctx);
}

/* W = 2 * U mod P.  */
static void ec_mul2(MPI w, MPI u, struct mpi_ec_ctx *ctx)
{
	mpi_lshift(w, u, 1);
	ec_mod(w, ctx);
}

static void ec_powm(MPI w, const MPI b, const MPI e,
		struct mpi_ec_ctx *ctx)
{
	mpi_powm(w, b, e, ctx->p);
	/* mpi_abs(w); */
}

/* Shortcut for
 * ec_powm(B, B, mpi_const(MPI_C_TWO), ctx);
 * for easier optimization.
 */
static void ec_pow2(MPI w, const MPI b, struct mpi_ec_ctx *ctx)
{
	/* Using mpi_mul is slightly faster (at least on amd64).  */
	/* mpi_powm(w, b, mpi_const(MPI_C_TWO), ctx->p); */
	ec_mulm(w, b, b, ctx);
}

/* Shortcut for
 * ec_powm(B, B, mpi_const(MPI_C_THREE), ctx);
 * for easier optimization.
 */
static void ec_pow3(MPI w, const MPI b, struct mpi_ec_ctx *ctx)
{
	mpi_powm(w, b, mpi_const(MPI_C_THREE), ctx->p);
}

static void ec_invm(MPI x, MPI a, struct mpi_ec_ctx *ctx)
{
	if (!mpi_invm(x, a, ctx->p))
		log_error("ec_invm: inverse does not exist:\n");
}

static void mpih_set_cond(mpi_ptr_t wp, mpi_ptr_t up,
		mpi_size_t usize, unsigned long set)
{
	mpi_size_t i;
	mpi_limb_t mask = ((mpi_limb_t)0) - set;
	mpi_limb_t x;

	for (i = 0; i < usize; i++) {
		x = mask & (wp[i] ^ up[i]);
		wp[i] = wp[i] ^ x;
	}
}

/* Routines for 2^255 - 19.  */

#define LIMB_SIZE_25519 ((256+BITS_PER_MPI_LIMB-1)/BITS_PER_MPI_LIMB)

static void ec_addm_25519(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx)
{
	mpi_ptr_t wp, up, vp;
	mpi_size_t wsize = LIMB_SIZE_25519;
	mpi_limb_t n[LIMB_SIZE_25519];
	mpi_limb_t borrow;

	if (w->nlimbs != wsize || u->nlimbs != wsize || v->nlimbs != wsize)
		log_bug("addm_25519: different sizes\n");

	memset(n, 0, sizeof(n));
	up = u->d;
	vp = v->d;
	wp = w->d;

	mpihelp_add_n(wp, up, vp, wsize);
	borrow = mpihelp_sub_n(wp, wp, ctx->p->d, wsize);
	mpih_set_cond(n, ctx->p->d, wsize, (borrow != 0UL));
	mpihelp_add_n(wp, wp, n, wsize);
	wp[LIMB_SIZE_25519-1] &= ~((mpi_limb_t)1 << (255 % BITS_PER_MPI_LIMB));
}

static void ec_subm_25519(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx)
{
	mpi_ptr_t wp, up, vp;
	mpi_size_t wsize = LIMB_SIZE_25519;
	mpi_limb_t n[LIMB_SIZE_25519];
	mpi_limb_t borrow;

	if (w->nlimbs != wsize || u->nlimbs != wsize || v->nlimbs != wsize)
		log_bug("subm_25519: different sizes\n");

	memset(n, 0, sizeof(n));
	up = u->d;
	vp = v->d;
	wp = w->d;

	borrow = mpihelp_sub_n(wp, up, vp, wsize);
	mpih_set_cond(n, ctx->p->d, wsize, (borrow != 0UL));
	mpihelp_add_n(wp, wp, n, wsize);
	wp[LIMB_SIZE_25519-1] &= ~((mpi_limb_t)1 << (255 % BITS_PER_MPI_LIMB));
}

static void ec_mulm_25519(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx)
{
	mpi_ptr_t wp, up, vp;
	mpi_size_t wsize = LIMB_SIZE_25519;
	mpi_limb_t n[LIMB_SIZE_25519*2];
	mpi_limb_t m[LIMB_SIZE_25519+1];
	mpi_limb_t cy;
	int msb;

	(void)ctx;
	if (w->nlimbs != wsize || u->nlimbs != wsize || v->nlimbs != wsize)
		log_bug("mulm_25519: different sizes\n");

	up = u->d;
	vp = v->d;
	wp = w->d;

	mpihelp_mul_n(n, up, vp, wsize);
	memcpy(wp, n, wsize * BYTES_PER_MPI_LIMB);
	wp[LIMB_SIZE_25519-1] &= ~((mpi_limb_t)1 << (255 % BITS_PER_MPI_LIMB));

	memcpy(m, n+LIMB_SIZE_25519-1, (wsize+1) * BYTES_PER_MPI_LIMB);
	mpihelp_rshift(m, m, LIMB_SIZE_25519+1, (255 % BITS_PER_MPI_LIMB));

	memcpy(n, m, wsize * BYTES_PER_MPI_LIMB);
	cy = mpihelp_lshift(m, m, LIMB_SIZE_25519, 4);
	m[LIMB_SIZE_25519] = cy;
	cy = mpihelp_add_n(m, m, n, wsize);
	m[LIMB_SIZE_25519] += cy;
	cy = mpihelp_add_n(m, m, n, wsize);
	m[LIMB_SIZE_25519] += cy;
	cy = mpihelp_add_n(m, m, n, wsize);
	m[LIMB_SIZE_25519] += cy;

	cy = mpihelp_add_n(wp, wp, m, wsize);
	m[LIMB_SIZE_25519] += cy;

	memset(m, 0, wsize * BYTES_PER_MPI_LIMB);
	msb = (wp[LIMB_SIZE_25519-1] >> (255 % BITS_PER_MPI_LIMB));
	m[0] = (m[LIMB_SIZE_25519] * 2 + msb) * 19;
	wp[LIMB_SIZE_25519-1] &= ~((mpi_limb_t)1 << (255 % BITS_PER_MPI_LIMB));
	mpihelp_add_n(wp, wp, m, wsize);

	m[0] = 0;
	cy = mpihelp_sub_n(wp, wp, ctx->p->d, wsize);
	mpih_set_cond(m, ctx->p->d, wsize, (cy != 0UL));
	mpihelp_add_n(wp, wp, m, wsize);
}

static void ec_mul2_25519(MPI w, MPI u, struct mpi_ec_ctx *ctx)
{
	ec_addm_25519(w, u, u, ctx);
}

static void ec_pow2_25519(MPI w, const MPI b, struct mpi_ec_ctx *ctx)
{
	ec_mulm_25519(w, b, b, ctx);
}

/* Routines for 2^448 - 2^224 - 1.  */

#define LIMB_SIZE_448 ((448+BITS_PER_MPI_LIMB-1)/BITS_PER_MPI_LIMB)
#define LIMB_SIZE_HALF_448 ((LIMB_SIZE_448+1)/2)

static void ec_addm_448(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx)
{
	mpi_ptr_t wp, up, vp;
	mpi_size_t wsize = LIMB_SIZE_448;
	mpi_limb_t n[LIMB_SIZE_448];
	mpi_limb_t cy;

	if (w->nlimbs != wsize || u->nlimbs != wsize || v->nlimbs != wsize)
		log_bug("addm_448: different sizes\n");

	memset(n, 0, sizeof(n));
	up = u->d;
	vp = v->d;
	wp = w->d;

	cy = mpihelp_add_n(wp, up, vp, wsize);
	mpih_set_cond(n, ctx->p->d, wsize, (cy != 0UL));
	mpihelp_sub_n(wp, wp, n, wsize);
}

static void ec_subm_448(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx)
{
	mpi_ptr_t wp, up, vp;
	mpi_size_t wsize = LIMB_SIZE_448;
	mpi_limb_t n[LIMB_SIZE_448];
	mpi_limb_t borrow;

	if (w->nlimbs != wsize || u->nlimbs != wsize || v->nlimbs != wsize)
		log_bug("subm_448: different sizes\n");

	memset(n, 0, sizeof(n));
	up = u->d;
	vp = v->d;
	wp = w->d;

	borrow = mpihelp_sub_n(wp, up, vp, wsize);
	mpih_set_cond(n, ctx->p->d, wsize, (borrow != 0UL));
	mpihelp_add_n(wp, wp, n, wsize);
}

static void ec_mulm_448(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx)
{
	mpi_ptr_t wp, up, vp;
	mpi_size_t wsize = LIMB_SIZE_448;
	mpi_limb_t n[LIMB_SIZE_448*2];
	mpi_limb_t a2[LIMB_SIZE_HALF_448];
	mpi_limb_t a3[LIMB_SIZE_HALF_448];
	mpi_limb_t b0[LIMB_SIZE_HALF_448];
	mpi_limb_t b1[LIMB_SIZE_HALF_448];
	mpi_limb_t cy;
	int i;
#if (LIMB_SIZE_HALF_448 > LIMB_SIZE_448/2)
	mpi_limb_t b1_rest, a3_rest;
#endif

	if (w->nlimbs != wsize || u->nlimbs != wsize || v->nlimbs != wsize)
		log_bug("mulm_448: different sizes\n");

	up = u->d;
	vp = v->d;
	wp = w->d;

	mpihelp_mul_n(n, up, vp, wsize);

	for (i = 0; i < (wsize + 1) / 2; i++) {
		b0[i] = n[i];
		b1[i] = n[i+wsize/2];
		a2[i] = n[i+wsize];
		a3[i] = n[i+wsize+wsize/2];
	}

#if (LIMB_SIZE_HALF_448 > LIMB_SIZE_448/2)
	b0[LIMB_SIZE_HALF_448-1] &= ((mpi_limb_t)1UL << 32)-1;
	a2[LIMB_SIZE_HALF_448-1] &= ((mpi_limb_t)1UL << 32)-1;

	b1_rest = 0;
	a3_rest = 0;

	for (i = (wsize + 1) / 2 - 1; i >= 0; i--) {
		mpi_limb_t b1v, a3v;
		b1v = b1[i];
		a3v = a3[i];
		b1[i] = (b1_rest << 32) | (b1v >> 32);
		a3[i] = (a3_rest << 32) | (a3v >> 32);
		b1_rest = b1v & (((mpi_limb_t)1UL << 32)-1);
		a3_rest = a3v & (((mpi_limb_t)1UL << 32)-1);
	}
#endif

	cy = mpihelp_add_n(b0, b0, a2, LIMB_SIZE_HALF_448);
	cy += mpihelp_add_n(b0, b0, a3, LIMB_SIZE_HALF_448);
	for (i = 0; i < (wsize + 1) / 2; i++)
		wp[i] = b0[i];
#if (LIMB_SIZE_HALF_448 > LIMB_SIZE_448/2)
	wp[LIMB_SIZE_HALF_448-1] &= (((mpi_limb_t)1UL << 32)-1);
#endif

#if (LIMB_SIZE_HALF_448 > LIMB_SIZE_448/2)
	cy = b0[LIMB_SIZE_HALF_448-1] >> 32;
#endif

	cy = mpihelp_add_1(b1, b1, LIMB_SIZE_HALF_448, cy);
	cy += mpihelp_add_n(b1, b1, a2, LIMB_SIZE_HALF_448);
	cy += mpihelp_add_n(b1, b1, a3, LIMB_SIZE_HALF_448);
	cy += mpihelp_add_n(b1, b1, a3, LIMB_SIZE_HALF_448);
#if (LIMB_SIZE_HALF_448 > LIMB_SIZE_448/2)
	b1_rest = 0;
	for (i = (wsize + 1) / 2 - 1; i >= 0; i--) {
		mpi_limb_t b1v = b1[i];
		b1[i] = (b1_rest << 32) | (b1v >> 32);
		b1_rest = b1v & (((mpi_limb_t)1UL << 32)-1);
	}
	wp[LIMB_SIZE_HALF_448-1] |= (b1_rest << 32);
#endif
	for (i = 0; i < wsize / 2; i++)
		wp[i+(wsize + 1) / 2] = b1[i];

#if (LIMB_SIZE_HALF_448 > LIMB_SIZE_448/2)
	cy = b1[LIMB_SIZE_HALF_448-1];
#endif

	memset(n, 0, wsize * BYTES_PER_MPI_LIMB);

#if (LIMB_SIZE_HALF_448 > LIMB_SIZE_448/2)
	n[LIMB_SIZE_HALF_448-1] = cy << 32;
#else
	n[LIMB_SIZE_HALF_448] = cy;
#endif
	n[0] = cy;
	mpihelp_add_n(wp, wp, n, wsize);

	memset(n, 0, wsize * BYTES_PER_MPI_LIMB);
	cy = mpihelp_sub_n(wp, wp, ctx->p->d, wsize);
	mpih_set_cond(n, ctx->p->d, wsize, (cy != 0UL));
	mpihelp_add_n(wp, wp, n, wsize);
}

static void ec_mul2_448(MPI w, MPI u, struct mpi_ec_ctx *ctx)
{
	ec_addm_448(w, u, u, ctx);
}

static void ec_pow2_448(MPI w, const MPI b, struct mpi_ec_ctx *ctx)
{
	ec_mulm_448(w, b, b, ctx);
}

struct field_table {
	const char *p;

	/* computation routines for the field.  */
	void (*addm)(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx);
	void (*subm)(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx);
	void (*mulm)(MPI w, MPI u, MPI v, struct mpi_ec_ctx *ctx);
	void (*mul2)(MPI w, MPI u, struct mpi_ec_ctx *ctx);
	void (*pow2)(MPI w, const MPI b, struct mpi_ec_ctx *ctx);
};

static const struct field_table field_table[] = {
	{
		"0x7FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFED",
		ec_addm_25519,
		ec_subm_25519,
		ec_mulm_25519,
		ec_mul2_25519,
		ec_pow2_25519
	},
	{
		"0xFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFE"
		"FFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFFF",
		ec_addm_448,
		ec_subm_448,
		ec_mulm_448,
		ec_mul2_448,
		ec_pow2_448
	},
	{ NULL, NULL, NULL, NULL, NULL, NULL },
};

/* Force recomputation of all helper variables.  */
static void mpi_ec_get_reset(struct mpi_ec_ctx *ec)
{
	ec->t.valid.a_is_pminus3 = 0;
	ec->t.valid.two_inv_p = 0;
}

/* Accessor for helper variable.  */
static int ec_get_a_is_pminus3(struct mpi_ec_ctx *ec)
{
	MPI tmp;

	if (!ec->t.valid.a_is_pminus3) {
		ec->t.valid.a_is_pminus3 = 1;
		tmp = mpi_alloc_like(ec->p);
		mpi_sub_ui(tmp, ec->p, 3);
		ec->t.a_is_pminus3 = !mpi_cmp(ec->a, tmp);
		mpi_free(tmp);
	}

	return ec->t.a_is_pminus3;
}

/* Accessor for helper variable.  */
static MPI ec_get_two_inv_p(struct mpi_ec_ctx *ec)
{
	if (!ec->t.valid.two_inv_p) {
		ec->t.valid.two_inv_p = 1;
		if (!ec->t.two_inv_p)
			ec->t.two_inv_p = mpi_alloc(0);
		ec_invm(ec->t.two_inv_p, mpi_const(MPI_C_TWO), ec);
	}
	return ec->t.two_inv_p;
}

static const char *const curve25519_bad_points[] = {
	"0x7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffed",
	"0x0000000000000000000000000000000000000000000000000000000000000000",
	"0x0000000000000000000000000000000000000000000000000000000000000001",
	"0x00b8495f16056286fdb1329ceb8d09da6ac49ff1fae35616aeb8413b7c7aebe0",
	"0x57119fd0dd4e22d8868e1c58c45c44045bef839c55b1d0b1248c50a3bc959c5f",
	"0x7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffec",
	"0x7fffffffffffffffffffffffffffffffffffffffffffffffffffffffffffffee",
	NULL
};

static const char *const curve448_bad_points[] = {
	"0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffe"
	"ffffffffffffffffffffffffffffffffffffffffffffffffffffffff",
	"0x00000000000000000000000000000000000000000000000000000000"
	"00000000000000000000000000000000000000000000000000000000",
	"0x00000000000000000000000000000000000000000000000000000000"
	"00000000000000000000000000000000000000000000000000000001",
	"0xfffffffffffffffffffffffffffffffffffffffffffffffffffffffe"
	"fffffffffffffffffffffffffffffffffffffffffffffffffffffffe",
	"0xffffffffffffffffffffffffffffffffffffffffffffffffffffffff"
	"00000000000000000000000000000000000000000000000000000000",
	NULL
};

static const char *const *bad_points_table[] = {
	curve25519_bad_points,
	curve448_bad_points,
};

static void mpi_ec_coefficient_normalize(MPI a, MPI p)
{
	if (a->sign) {
		mpi_resize(a, p->nlimbs);
		mpihelp_sub_n(a->d, p->d, a->d, p->nlimbs);
		a->nlimbs = p->nlimbs;
		a->sign = 0;
	}
}

/* This function initialized a context for elliptic curve based on the
 * field GF(p).  P is the prime specifying this field, A is the first
 * coefficient.  CTX is expected to be zeroized.
 */
void mpi_ec_init(struct mpi_ec_ctx *ctx, enum gcry_mpi_ec_models model,
			enum ecc_dialects dialect,
			int flags, MPI p, MPI a, MPI b)
{
	int i;
	static int use_barrett = -1 /* TODO: 1 or -1 */;

	mpi_ec_coefficient_normalize(a, p);
	mpi_ec_coefficient_normalize(b, p);

	/* Fixme: Do we want to check some constraints? e.g.  a < p  */

	ctx->model = model;
	ctx->dialect = dialect;
	ctx->flags = flags;
	if (dialect == ECC_DIALECT_ED25519)
		ctx->nbits = 256;
	else
		ctx->nbits = mpi_get_nbits(p);
	ctx->p = mpi_copy(p);
	ctx->a = mpi_copy(a);
	ctx->b = mpi_copy(b);

	ctx->t.p_barrett = use_barrett > 0 ? mpi_barrett_init(ctx->p, 0) : NULL;

	mpi_ec_get_reset(ctx);

	if (model == MPI_EC_MONTGOMERY) {
		for (i = 0; i < DIM(bad_points_table); i++) {
			MPI p_candidate = mpi_scanval(bad_points_table[i][0]);
			int match_p = !mpi_cmp(ctx->p, p_candidate);
			int j;

			mpi_free(p_candidate);
			if (!match_p)
				continue;

			for (j = 0; i < DIM(ctx->t.scratch) && bad_points_table[i][j]; j++)
				ctx->t.scratch[j] = mpi_scanval(bad_points_table[i][j]);
		}
	} else {
		/* Allocate scratch variables.  */
		for (i = 0; i < DIM(ctx->t.scratch); i++)
			ctx->t.scratch[i] = mpi_alloc_like(ctx->p);
	}

	ctx->addm = ec_addm;
	ctx->subm = ec_subm;
	ctx->mulm = ec_mulm;
	ctx->mul2 = ec_mul2;
	ctx->pow2 = ec_pow2;

	for (i = 0; field_table[i].p; i++) {
		MPI f_p;

		f_p = mpi_scanval(field_table[i].p);
		if (!f_p)
			break;

		if (!mpi_cmp(p, f_p)) {
			ctx->addm = field_table[i].addm;
			ctx->subm = field_table[i].subm;
			ctx->mulm = field_table[i].mulm;
			ctx->mul2 = field_table[i].mul2;
			ctx->pow2 = field_table[i].pow2;
			mpi_free(f_p);

			mpi_resize(ctx->a, ctx->p->nlimbs);
			ctx->a->nlimbs = ctx->p->nlimbs;

			mpi_resize(ctx->b, ctx->p->nlimbs);
			ctx->b->nlimbs = ctx->p->nlimbs;

			for (i = 0; i < DIM(ctx->t.scratch) && ctx->t.scratch[i]; i++)
				ctx->t.scratch[i]->nlimbs = ctx->p->nlimbs;

			break;
		}

		mpi_free(f_p);
	}
}
EXPORT_SYMBOL_GPL(mpi_ec_init);

void mpi_ec_deinit(struct mpi_ec_ctx *ctx)
{
	int i;

	mpi_barrett_free(ctx->t.p_barrett);

	/* Domain parameter.  */
	mpi_free(ctx->p);
	mpi_free(ctx->a);
	mpi_free(ctx->b);
	mpi_point_release(ctx->G);
	mpi_free(ctx->n);

	/* The key.  */
	mpi_point_release(ctx->Q);
	mpi_free(ctx->d);

	/* Private data of ec.c.  */
	mpi_free(ctx->t.two_inv_p);

	for (i = 0; i < DIM(ctx->t.scratch); i++)
		mpi_free(ctx->t.scratch[i]);
}
EXPORT_SYMBOL_GPL(mpi_ec_deinit);

/* Compute the affine coordinates from the projective coordinates in
 * POINT.  Set them into X and Y.  If one coordinate is not required,
 * X or Y may be passed as NULL.  CTX is the usual context. Returns: 0
 * on success or !0 if POINT is at infinity.
 */
int mpi_ec_get_affine(MPI x, MPI y, MPI_POINT point, struct mpi_ec_ctx *ctx)
{
	if (!mpi_cmp_ui(point->z, 0))
		return -1;

	switch (ctx->model) {
	case MPI_EC_WEIERSTRASS: /* Using Jacobian coordinates.  */
		{
			MPI z1, z2, z3;

			z1 = mpi_new(0);
			z2 = mpi_new(0);
			ec_invm(z1, point->z, ctx);  /* z1 = z^(-1) mod p  */
			ec_mulm(z2, z1, z1, ctx);    /* z2 = z^(-2) mod p  */

			if (x)
				ec_mulm(x, point->x, z2, ctx);

			if (y) {
				z3 = mpi_new(0);
				ec_mulm(z3, z2, z1, ctx);      /* z3 = z^(-3) mod p */
				ec_mulm(y, point->y, z3, ctx);
				mpi_free(z3);
			}

			mpi_free(z2);
			mpi_free(z1);
		}
		return 0;

	case MPI_EC_MONTGOMERY:
		{
			if (x)
				mpi_set(x, point->x);

			if (y) {
				log_fatal("%s: Getting Y-coordinate on %s is not supported\n",
						"mpi_ec_get_affine", "Montgomery");
				return -1;
			}
		}
		return 0;

	case MPI_EC_EDWARDS:
		{
			MPI z;

			z = mpi_new(0);
			ec_invm(z, point->z, ctx);

			mpi_resize(z, ctx->p->nlimbs);
			z->nlimbs = ctx->p->nlimbs;

			if (x) {
				mpi_resize(x, ctx->p->nlimbs);
				x->nlimbs = ctx->p->nlimbs;
				ctx->mulm(x, point->x, z, ctx);
			}
			if (y) {
				mpi_resize(y, ctx->p->nlimbs);
				y->nlimbs = ctx->p->nlimbs;
				ctx->mulm(y, point->y, z, ctx);
			}

			mpi_free(z);
		}
		return 0;

	default:
		return -1;
	}
}
EXPORT_SYMBOL_GPL(mpi_ec_get_affine);

/*  RESULT = 2 * POINT  (Weierstrass version). */
static void dup_point_weierstrass(MPI_POINT result,
		MPI_POINT point, struct mpi_ec_ctx *ctx)
{
#define x3 (result->x)
#define y3 (result->y)
#define z3 (result->z)
#define t1 (ctx->t.scratch[0])
#define t2 (ctx->t.scratch[1])
#define t3 (ctx->t.scratch[2])
#define l1 (ctx->t.scratch[3])
#define l2 (ctx->t.scratch[4])
#define l3 (ctx->t.scratch[5])

	if (!mpi_cmp_ui(point->y, 0) || !mpi_cmp_ui(point->z, 0)) {
		/* P_y == 0 || P_z == 0 => [1:1:0] */
		mpi_set_ui(x3, 1);
		mpi_set_ui(y3, 1);
		mpi_set_ui(z3, 0);
	} else {
		if (ec_get_a_is_pminus3(ctx)) {
			/* Use the faster case.  */
			/* L1 = 3(X - Z^2)(X + Z^2) */
			/*                          T1: used for Z^2. */
			/*                          T2: used for the right term. */
			ec_pow2(t1, point->z, ctx);
			ec_subm(l1, point->x, t1, ctx);
			ec_mulm(l1, l1, mpi_const(MPI_C_THREE), ctx);
			ec_addm(t2, point->x, t1, ctx);
			ec_mulm(l1, l1, t2, ctx);
		} else {
			/* Standard case. */
			/* L1 = 3X^2 + aZ^4 */
			/*                          T1: used for aZ^4. */
			ec_pow2(l1, point->x, ctx);
			ec_mulm(l1, l1, mpi_const(MPI_C_THREE), ctx);
			ec_powm(t1, point->z, mpi_const(MPI_C_FOUR), ctx);
			ec_mulm(t1, t1, ctx->a, ctx);
			ec_addm(l1, l1, t1, ctx);
		}
		/* Z3 = 2YZ */
		ec_mulm(z3, point->y, point->z, ctx);
		ec_mul2(z3, z3, ctx);

		/* L2 = 4XY^2 */
		/*                              T2: used for Y2; required later. */
		ec_pow2(t2, point->y, ctx);
		ec_mulm(l2, t2, point->x, ctx);
		ec_mulm(l2, l2, mpi_const(MPI_C_FOUR), ctx);

		/* X3 = L1^2 - 2L2 */
		/*                              T1: used for L2^2. */
		ec_pow2(x3, l1, ctx);
		ec_mul2(t1, l2, ctx);
		ec_subm(x3, x3, t1, ctx);

		/* L3 = 8Y^4 */
		/*                              T2: taken from above. */
		ec_pow2(t2, t2, ctx);
		ec_mulm(l3, t2, mpi_const(MPI_C_EIGHT), ctx);

		/* Y3 = L1(L2 - X3) - L3 */
		ec_subm(y3, l2, x3, ctx);
		ec_mulm(y3, y3, l1, ctx);
		ec_subm(y3, y3, l3, ctx);
	}

#undef x3
#undef y3
#undef z3
#undef t1
#undef t2
#undef t3
#undef l1
#undef l2
#undef l3
}

/*  RESULT = 2 * POINT  (Montgomery version). */
static void dup_point_montgomery(MPI_POINT result,
				MPI_POINT point, struct mpi_ec_ctx *ctx)
{
	(void)result;
	(void)point;
	(void)ctx;
	log_fatal("%s: %s not yet supported\n",
			"mpi_ec_dup_point", "Montgomery");
}

/*  RESULT = 2 * POINT  (Twisted Edwards version). */
static void dup_point_edwards(MPI_POINT result,
		MPI_POINT point, struct mpi_ec_ctx *ctx)
{
#define X1 (point->x)
#define Y1 (point->y)
#define Z1 (point->z)
#define X3 (result->x)
#define Y3 (result->y)
#define Z3 (result->z)
#define B (ctx->t.scratch[0])
#define C (ctx->t.scratch[1])
#define D (ctx->t.scratch[2])
#define E (ctx->t.scratch[3])
#define F (ctx->t.scratch[4])
#define H (ctx->t.scratch[5])
#define J (ctx->t.scratch[6])

	/* Compute: (X_3 : Y_3 : Z_3) = 2( X_1 : Y_1 : Z_1 ) */

	/* B = (X_1 + Y_1)^2  */
	ctx->addm(B, X1, Y1, ctx);
	ctx->pow2(B, B, ctx);

	/* C = X_1^2 */
	/* D = Y_1^2 */
	ctx->pow2(C, X1, ctx);
	ctx->pow2(D, Y1, ctx);

	/* E = aC */
	if (ctx->dialect == ECC_DIALECT_ED25519)
		ctx->subm(E, ctx->p, C, ctx);
	else
		ctx->mulm(E, ctx->a, C, ctx);

	/* F = E + D */
	ctx->addm(F, E, D, ctx);

	/* H = Z_1^2 */
	ctx->pow2(H, Z1, ctx);

	/* J = F - 2H */
	ctx->mul2(J, H, ctx);
	ctx->subm(J, F, J, ctx);

	/* X_3 = (B - C - D) · J */
	ctx->subm(X3, B, C, ctx);
	ctx->subm(X3, X3, D, ctx);
	ctx->mulm(X3, X3, J, ctx);

	/* Y_3 = F · (E - D) */
	ctx->subm(Y3, E, D, ctx);
	ctx->mulm(Y3, Y3, F, ctx);

	/* Z_3 = F · J */
	ctx->mulm(Z3, F, J, ctx);

#undef X1
#undef Y1
#undef Z1
#undef X3
#undef Y3
#undef Z3
#undef B
#undef C
#undef D
#undef E
#undef F
#undef H
#undef J
}

/*  RESULT = 2 * POINT  */
static void
mpi_ec_dup_point(MPI_POINT result, MPI_POINT point, struct mpi_ec_ctx *ctx)
{
	switch (ctx->model) {
	case MPI_EC_WEIERSTRASS:
		dup_point_weierstrass(result, point, ctx);
		break;
	case MPI_EC_MONTGOMERY:
		dup_point_montgomery(result, point, ctx);
		break;
	case MPI_EC_EDWARDS:
		dup_point_edwards(result, point, ctx);
		break;
	}
}

/* RESULT = P1 + P2  (Weierstrass version).*/
static void add_points_weierstrass(MPI_POINT result,
		MPI_POINT p1, MPI_POINT p2,
		struct mpi_ec_ctx *ctx)
{
#define x1 (p1->x)
#define y1 (p1->y)
#define z1 (p1->z)
#define x2 (p2->x)
#define y2 (p2->y)
#define z2 (p2->z)
#define x3 (result->x)
#define y3 (result->y)
#define z3 (result->z)
#define l1 (ctx->t.scratch[0])
#define l2 (ctx->t.scratch[1])
#define l3 (ctx->t.scratch[2])
#define l4 (ctx->t.scratch[3])
#define l5 (ctx->t.scratch[4])
#define l6 (ctx->t.scratch[5])
#define l7 (ctx->t.scratch[6])
#define l8 (ctx->t.scratch[7])
#define l9 (ctx->t.scratch[8])
#define t1 (ctx->t.scratch[9])
#define t2 (ctx->t.scratch[10])

	if ((!mpi_cmp(x1, x2)) && (!mpi_cmp(y1, y2)) && (!mpi_cmp(z1, z2))) {
		/* Same point; need to call the duplicate function.  */
		mpi_ec_dup_point(result, p1, ctx);
	} else if (!mpi_cmp_ui(z1, 0)) {
		/* P1 is at infinity.  */
		mpi_set(x3, p2->x);
		mpi_set(y3, p2->y);
		mpi_set(z3, p2->z);
	} else if (!mpi_cmp_ui(z2, 0)) {
		/* P2 is at infinity.  */
		mpi_set(x3, p1->x);
		mpi_set(y3, p1->y);
		mpi_set(z3, p1->z);
	} else {
		int z1_is_one = !mpi_cmp_ui(z1, 1);
		int z2_is_one = !mpi_cmp_ui(z2, 1);

		/* l1 = x1 z2^2  */
		/* l2 = x2 z1^2  */
		if (z2_is_one)
			mpi_set(l1, x1);
		else {
			ec_pow2(l1, z2, ctx);
			ec_mulm(l1, l1, x1, ctx);
		}
		if (z1_is_one)
			mpi_set(l2, x2);
		else {
			ec_pow2(l2, z1, ctx);
			ec_mulm(l2, l2, x2, ctx);
		}
		/* l3 = l1 - l2 */
		ec_subm(l3, l1, l2, ctx);
		/* l4 = y1 z2^3  */
		ec_powm(l4, z2, mpi_const(MPI_C_THREE), ctx);
		ec_mulm(l4, l4, y1, ctx);
		/* l5 = y2 z1^3  */
		ec_powm(l5, z1, mpi_const(MPI_C_THREE), ctx);
		ec_mulm(l5, l5, y2, ctx);
		/* l6 = l4 - l5  */
		ec_subm(l6, l4, l5, ctx);

		if (!mpi_cmp_ui(l3, 0)) {
			if (!mpi_cmp_ui(l6, 0)) {
				/* P1 and P2 are the same - use duplicate function. */
				mpi_ec_dup_point(result, p1, ctx);
			} else {
				/* P1 is the inverse of P2.  */
				mpi_set_ui(x3, 1);
				mpi_set_ui(y3, 1);
				mpi_set_ui(z3, 0);
			}
		} else {
			/* l7 = l1 + l2  */
			ec_addm(l7, l1, l2, ctx);
			/* l8 = l4 + l5  */
			ec_addm(l8, l4, l5, ctx);
			/* z3 = z1 z2 l3  */
			ec_mulm(z3, z1, z2, ctx);
			ec_mulm(z3, z3, l3, ctx);
			/* x3 = l6^2 - l7 l3^2  */
			ec_pow2(t1, l6, ctx);
			ec_pow2(t2, l3, ctx);
			ec_mulm(t2, t2, l7, ctx);
			ec_subm(x3, t1, t2, ctx);
			/* l9 = l7 l3^2 - 2 x3  */
			ec_mul2(t1, x3, ctx);
			ec_subm(l9, t2, t1, ctx);
			/* y3 = (l9 l6 - l8 l3^3)/2  */
			ec_mulm(l9, l9, l6, ctx);
			ec_powm(t1, l3, mpi_const(MPI_C_THREE), ctx); /* fixme: Use saved value*/
			ec_mulm(t1, t1, l8, ctx);
			ec_subm(y3, l9, t1, ctx);
			ec_mulm(y3, y3, ec_get_two_inv_p(ctx), ctx);
		}
	}

#undef x1
#undef y1
#undef z1
#undef x2
#undef y2
#undef z2
#undef x3
#undef y3
#undef z3
#undef l1
#undef l2
#undef l3
#undef l4
#undef l5
#undef l6
#undef l7
#undef l8
#undef l9
#undef t1
#undef t2
}

/* RESULT = P1 + P2  (Montgomery version).*/
static void add_points_montgomery(MPI_POINT result,
		MPI_POINT p1, MPI_POINT p2,
		struct mpi_ec_ctx *ctx)
{
	(void)result;
	(void)p1;
	(void)p2;
	(void)ctx;
	log_fatal("%s: %s not yet supported\n",
			"mpi_ec_add_points", "Montgomery");
}

/* RESULT = P1 + P2  (Twisted Edwards version).*/
static void add_points_edwards(MPI_POINT result,
		MPI_POINT p1, MPI_POINT p2,
		struct mpi_ec_ctx *ctx)
{
#define X1 (p1->x)
#define Y1 (p1->y)
#define Z1 (p1->z)
#define X2 (p2->x)
#define Y2 (p2->y)
#define Z2 (p2->z)
#define X3 (result->x)
#define Y3 (result->y)
#define Z3 (result->z)
#define A (ctx->t.scratch[0])
#define B (ctx->t.scratch[1])
#define C (ctx->t.scratch[2])
#define D (ctx->t.scratch[3])
#define E (ctx->t.scratch[4])
#define F (ctx->t.scratch[5])
#define G (ctx->t.scratch[6])
#define tmp (ctx->t.scratch[7])

	point_resize(result, ctx);

	/* Compute: (X_3 : Y_3 : Z_3) = (X_1 : Y_1 : Z_1) + (X_2 : Y_2 : Z_3) */

	/* A = Z1 · Z2 */
	ctx->mulm(A, Z1, Z2, ctx);

	/* B = A^2 */
	ctx->pow2(B, A, ctx);

	/* C = X1 · X2 */
	ctx->mulm(C, X1, X2, ctx);

	/* D = Y1 · Y2 */
	ctx->mulm(D, Y1, Y2, ctx);

	/* E = d · C · D */
	ctx->mulm(E, ctx->b, C, ctx);
	ctx->mulm(E, E, D, ctx);

	/* F = B - E */
	ctx->subm(F, B, E, ctx);

	/* G = B + E */
	ctx->addm(G, B, E, ctx);

	/* X_3 = A · F · ((X_1 + Y_1) · (X_2 + Y_2) - C - D) */
	ctx->addm(tmp, X1, Y1, ctx);
	ctx->addm(X3, X2, Y2, ctx);
	ctx->mulm(X3, X3, tmp, ctx);
	ctx->subm(X3, X3, C, ctx);
	ctx->subm(X3, X3, D, ctx);
	ctx->mulm(X3, X3, F, ctx);
	ctx->mulm(X3, X3, A, ctx);

	/* Y_3 = A · G · (D - aC) */
	if (ctx->dialect == ECC_DIALECT_ED25519) {
		ctx->addm(Y3, D, C, ctx);
	} else {
		ctx->mulm(Y3, ctx->a, C, ctx);
		ctx->subm(Y3, D, Y3, ctx);
	}
	ctx->mulm(Y3, Y3, G, ctx);
	ctx->mulm(Y3, Y3, A, ctx);

	/* Z_3 = F · G */
	ctx->mulm(Z3, F, G, ctx);


#undef X1
#undef Y1
#undef Z1
#undef X2
#undef Y2
#undef Z2
#undef X3
#undef Y3
#undef Z3
#undef A
#undef B
#undef C
#undef D
#undef E
#undef F
#undef G
#undef tmp
}

/* Compute a step of Montgomery Ladder (only use X and Z in the point).
 * Inputs:  P1, P2, and x-coordinate of DIF = P1 - P1.
 * Outputs: PRD = 2 * P1 and  SUM = P1 + P2.
 */
static void montgomery_ladder(MPI_POINT prd, MPI_POINT sum,
		MPI_POINT p1, MPI_POINT p2, MPI dif_x,
		struct mpi_ec_ctx *ctx)
{
	ctx->addm(sum->x, p2->x, p2->z, ctx);
	ctx->subm(p2->z, p2->x, p2->z, ctx);
	ctx->addm(prd->x, p1->x, p1->z, ctx);
	ctx->subm(p1->z, p1->x, p1->z, ctx);
	ctx->mulm(p2->x, p1->z, sum->x, ctx);
	ctx->mulm(p2->z, prd->x, p2->z, ctx);
	ctx->pow2(p1->x, prd->x, ctx);
	ctx->pow2(p1->z, p1->z, ctx);
	ctx->addm(sum->x, p2->x, p2->z, ctx);
	ctx->subm(p2->z, p2->x, p2->z, ctx);
	ctx->mulm(prd->x, p1->x, p1->z, ctx);
	ctx->subm(p1->z, p1->x, p1->z, ctx);
	ctx->pow2(sum->x, sum->x, ctx);
	ctx->pow2(sum->z, p2->z, ctx);
	ctx->mulm(prd->z, p1->z, ctx->a, ctx); /* CTX->A: (a-2)/4 */
	ctx->mulm(sum->z, sum->z, dif_x, ctx);
	ctx->addm(prd->z, p1->x, prd->z, ctx);
	ctx->mulm(prd->z, prd->z, p1->z, ctx);
}

/* RESULT = P1 + P2 */
void mpi_ec_add_points(MPI_POINT result,
		MPI_POINT p1, MPI_POINT p2,
		struct mpi_ec_ctx *ctx)
{
	switch (ctx->model) {
	case MPI_EC_WEIERSTRASS:
		add_points_weierstrass(result, p1, p2, ctx);
		break;
	case MPI_EC_MONTGOMERY:
		add_points_montgomery(result, p1, p2, ctx);
		break;
	case MPI_EC_EDWARDS:
		add_points_edwards(result, p1, p2, ctx);
		break;
	}
}
EXPORT_SYMBOL_GPL(mpi_ec_add_points);

/* Scalar point multiplication - the main function for ECC.  If takes
 * an integer SCALAR and a POINT as well as the usual context CTX.
 * RESULT will be set to the resulting point.
 */
void mpi_ec_mul_point(MPI_POINT result,
			MPI scalar, MPI_POINT point,
			struct mpi_ec_ctx *ctx)
{
	MPI x1, y1, z1, k, h, yy;
	unsigned int i, loops;
	struct gcry_mpi_point p1, p2, p1inv;

	if (ctx->model == MPI_EC_EDWARDS) {
		/* Simple left to right binary method.  Algorithm 3.27 from
		 * {author={Hankerson, Darrel and Menezes, Alfred J. and Vanstone, Scott},
		 *  title = {Guide to Elliptic Curve Cryptography},
		 *  year = {2003}, isbn = {038795273X},
		 *  url = {http://www.cacr.math.uwaterloo.ca/ecc/},
		 *  publisher = {Springer-Verlag New York, Inc.}}
		 */
		unsigned int nbits;
		int j;

		if (mpi_cmp(scalar, ctx->p) >= 0)
			nbits = mpi_get_nbits(scalar);
		else
			nbits = mpi_get_nbits(ctx->p);

		mpi_set_ui(result->x, 0);
		mpi_set_ui(result->y, 1);
		mpi_set_ui(result->z, 1);
		point_resize(point, ctx);

		point_resize(result, ctx);
		point_resize(point, ctx);

		for (j = nbits-1; j >= 0; j--) {
			mpi_ec_dup_point(result, result, ctx);
			if (mpi_test_bit(scalar, j))
				mpi_ec_add_points(result, result, point, ctx);
		}
		return;
	} else if (ctx->model == MPI_EC_MONTGOMERY) {
		unsigned int nbits;
		int j;
		struct gcry_mpi_point p1_, p2_;
		MPI_POINT q1, q2, prd, sum;
		unsigned long sw;
		mpi_size_t rsize;

		/* Compute scalar point multiplication with Montgomery Ladder.
		 * Note that we don't use Y-coordinate in the points at all.
		 * RESULT->Y will be filled by zero.
		 */

		nbits = mpi_get_nbits(scalar);
		point_init(&p1);
		point_init(&p2);
		point_init(&p1_);
		point_init(&p2_);
		mpi_set_ui(p1.x, 1);
		mpi_free(p2.x);
		p2.x = mpi_copy(point->x);
		mpi_set_ui(p2.z, 1);

		point_resize(&p1, ctx);
		point_resize(&p2, ctx);
		point_resize(&p1_, ctx);
		point_resize(&p2_, ctx);

		mpi_resize(point->x, ctx->p->nlimbs);
		point->x->nlimbs = ctx->p->nlimbs;

		q1 = &p1;
		q2 = &p2;
		prd = &p1_;
		sum = &p2_;

		for (j = nbits-1; j >= 0; j--) {
			MPI_POINT t;

			sw = mpi_test_bit(scalar, j);
			point_swap_cond(q1, q2, sw, ctx);
			montgomery_ladder(prd, sum, q1, q2, point->x, ctx);
			point_swap_cond(prd, sum, sw, ctx);
			t = q1;  q1 = prd;  prd = t;
			t = q2;  q2 = sum;  sum = t;
		}

		mpi_clear(result->y);
		sw = (nbits & 1);
		point_swap_cond(&p1, &p1_, sw, ctx);

		rsize = p1.z->nlimbs;
		MPN_NORMALIZE(p1.z->d, rsize);
		if (rsize == 0) {
			mpi_set_ui(result->x, 1);
			mpi_set_ui(result->z, 0);
		} else {
			z1 = mpi_new(0);
			ec_invm(z1, p1.z, ctx);
			ec_mulm(result->x, p1.x, z1, ctx);
			mpi_set_ui(result->z, 1);
			mpi_free(z1);
		}

		point_free(&p1);
		point_free(&p2);
		point_free(&p1_);
		point_free(&p2_);
		return;
	}

	x1 = mpi_alloc_like(ctx->p);
	y1 = mpi_alloc_like(ctx->p);
	h  = mpi_alloc_like(ctx->p);
	k  = mpi_copy(scalar);
	yy = mpi_copy(point->y);

	if (mpi_has_sign(k)) {
		k->sign = 0;
		ec_invm(yy, yy, ctx);
	}

	if (!mpi_cmp_ui(point->z, 1)) {
		mpi_set(x1, point->x);
		mpi_set(y1, yy);
	} else {
		MPI z2, z3;

		z2 = mpi_alloc_like(ctx->p);
		z3 = mpi_alloc_like(ctx->p);
		ec_mulm(z2, point->z, point->z, ctx);
		ec_mulm(z3, point->z, z2, ctx);
		ec_invm(z2, z2, ctx);
		ec_mulm(x1, point->x, z2, ctx);
		ec_invm(z3, z3, ctx);
		ec_mulm(y1, yy, z3, ctx);
		mpi_free(z2);
		mpi_free(z3);
	}
	z1 = mpi_copy(mpi_const(MPI_C_ONE));

	mpi_mul(h, k, mpi_const(MPI_C_THREE)); /* h = 3k */
	loops = mpi_get_nbits(h);
	if (loops < 2) {
		/* If SCALAR is zero, the above mpi_mul sets H to zero and thus
		 * LOOPs will be zero.  To avoid an underflow of I in the main
		 * loop we set LOOP to 2 and the result to (0,0,0).
		 */
		loops = 2;
		mpi_clear(result->x);
		mpi_clear(result->y);
		mpi_clear(result->z);
	} else {
		mpi_set(result->x, point->x);
		mpi_set(result->y, yy);
		mpi_set(result->z, point->z);
	}
	mpi_free(yy); yy = NULL;

	p1.x = x1; x1 = NULL;
	p1.y = y1; y1 = NULL;
	p1.z = z1; z1 = NULL;
	point_init(&p2);
	point_init(&p1inv);

	/* Invert point: y = p - y mod p  */
	point_set(&p1inv, &p1);
	ec_subm(p1inv.y, ctx->p, p1inv.y, ctx);

	for (i = loops-2; i > 0; i--) {
		mpi_ec_dup_point(result, result, ctx);
		if (mpi_test_bit(h, i) == 1 && mpi_test_bit(k, i) == 0) {
			point_set(&p2, result);
			mpi_ec_add_points(result, &p2, &p1, ctx);
		}
		if (mpi_test_bit(h, i) == 0 && mpi_test_bit(k, i) == 1) {
			point_set(&p2, result);
			mpi_ec_add_points(result, &p2, &p1inv, ctx);
		}
	}

	point_free(&p1);
	point_free(&p2);
	point_free(&p1inv);
	mpi_free(h);
	mpi_free(k);
}
EXPORT_SYMBOL_GPL(mpi_ec_mul_point);

/* Return true if POINT is on the curve described by CTX.  */
int mpi_ec_curve_point(MPI_POINT point, struct mpi_ec_ctx *ctx)
{
	int res = 0;
	MPI x, y, w;

	x = mpi_new(0);
	y = mpi_new(0);
	w = mpi_new(0);

	/* Check that the point is in range.  This needs to be done here and
	 * not after conversion to affine coordinates.
	 */
	if (mpi_cmpabs(point->x, ctx->p) >= 0)
		goto leave;
	if (mpi_cmpabs(point->y, ctx->p) >= 0)
		goto leave;
	if (mpi_cmpabs(point->z, ctx->p) >= 0)
		goto leave;

	switch (ctx->model) {
	case MPI_EC_WEIERSTRASS:
		{
			MPI xxx;

			if (mpi_ec_get_affine(x, y, point, ctx))
				goto leave;

			xxx = mpi_new(0);

			/* y^2 == x^3 + a·x + b */
			ec_pow2(y, y, ctx);

			ec_pow3(xxx, x, ctx);
			ec_mulm(w, ctx->a, x, ctx);
			ec_addm(w, w, ctx->b, ctx);
			ec_addm(w, w, xxx, ctx);

			if (!mpi_cmp(y, w))
				res = 1;

			mpi_free(xxx);
		}
		break;

	case MPI_EC_MONTGOMERY:
		{
#define xx y
			/* With Montgomery curve, only X-coordinate is valid. */
			if (mpi_ec_get_affine(x, NULL, point, ctx))
				goto leave;

			/* The equation is: b * y^2 == x^3 + a · x^2 + x */
			/* We check if right hand is quadratic residue or not by
			 * Euler's criterion.
			 */
			/* CTX->A has (a-2)/4 and CTX->B has b^-1 */
			ec_mulm(w, ctx->a, mpi_const(MPI_C_FOUR), ctx);
			ec_addm(w, w, mpi_const(MPI_C_TWO), ctx);
			ec_mulm(w, w, x, ctx);
			ec_pow2(xx, x, ctx);
			ec_addm(w, w, xx, ctx);
			ec_addm(w, w, mpi_const(MPI_C_ONE), ctx);
			ec_mulm(w, w, x, ctx);
			ec_mulm(w, w, ctx->b, ctx);
#undef xx
			/* Compute Euler's criterion: w^(p-1)/2 */
#define p_minus1 y
			ec_subm(p_minus1, ctx->p, mpi_const(MPI_C_ONE), ctx);
			mpi_rshift(p_minus1, p_minus1, 1);
			ec_powm(w, w, p_minus1, ctx);

			res = !mpi_cmp_ui(w, 1);
#undef p_minus1
		}
		break;

	case MPI_EC_EDWARDS:
		{
			if (mpi_ec_get_affine(x, y, point, ctx))
				goto leave;

			mpi_resize(w, ctx->p->nlimbs);
			w->nlimbs = ctx->p->nlimbs;

			/* a · x^2 + y^2 - 1 - b · x^2 · y^2 == 0 */
			ctx->pow2(x, x, ctx);
			ctx->pow2(y, y, ctx);
			if (ctx->dialect == ECC_DIALECT_ED25519)
				ctx->subm(w, ctx->p, x, ctx);
			else
				ctx->mulm(w, ctx->a, x, ctx);
			ctx->addm(w, w, y, ctx);
			ctx->mulm(x, x, y, ctx);
			ctx->mulm(x, x, ctx->b, ctx);
			ctx->subm(w, w, x, ctx);
			if (!mpi_cmp_ui(w, 1))
				res = 1;
		}
		break;
	}

leave:
	mpi_free(w);
	mpi_free(x);
	mpi_free(y);

	return res;
}
EXPORT_SYMBOL_GPL(mpi_ec_curve_point);
