int BN_GF2m_mod_solve_quad_arr(BIGNUM *r, const BIGNUM *a_, const unsigned int p[], BN_CTX *ctx)
	{
	int ret = 0, count = 0;
	unsigned int j;
	BIGNUM *a, *z, *rho, *w, *w2, *tmp;
	if (!p[0])
		return BN_zero(r);
	BN_CTX_start(ctx);
	a = BN_CTX_get(ctx);
	z = BN_CTX_get(ctx);
	w = BN_CTX_get(ctx);
	if (w == NULL) goto err;
	if (!BN_GF2m_mod_arr(a, a_, p)) goto err;
	if (BN_is_zero(a))
		{
		ret = BN_zero(r);
		goto err;
		}
	if (p[0] & 0x1)
		{
		if (!BN_copy(z, a)) goto err;
		for (j = 1; j <= (p[0] - 1) / 2; j++)
			{
			if (!BN_GF2m_mod_sqr_arr(z, z, p, ctx)) goto err;
			if (!BN_GF2m_mod_sqr_arr(z, z, p, ctx)) goto err;
			if (!BN_GF2m_add(z, z, a)) goto err;
			}
		}
	else
		{
		rho = BN_CTX_get(ctx);
		w2 = BN_CTX_get(ctx);
		tmp = BN_CTX_get(ctx);
		if (tmp == NULL) goto err;
		do
			{
			if (!BN_rand(rho, p[0], 0, 0)) goto err;
			if (!BN_GF2m_mod_arr(rho, rho, p)) goto err;
			if (!BN_zero(z)) goto err;
			if (!BN_copy(w, rho)) goto err;
			for (j = 1; j <= p[0] - 1; j++)
				{
				if (!BN_GF2m_mod_sqr_arr(z, z, p, ctx)) goto err;
				if (!BN_GF2m_mod_sqr_arr(w2, w, p, ctx)) goto err;
				if (!BN_GF2m_mod_mul_arr(tmp, w2, a, p, ctx)) goto err;
				if (!BN_GF2m_add(z, z, tmp)) goto err;
				if (!BN_GF2m_add(w, w2, rho)) goto err;
				}
			count++;
			} while (BN_is_zero(w) && (count < MAX_ITERATIONS));
		if (BN_is_zero(w))
			{
			BNerr(BN_F_BN_GF2M_MOD_SOLVE_QUAD_ARR,BN_R_TOO_MANY_ITERATIONS);
			goto err;
			}
		}
	if (!BN_GF2m_mod_sqr_arr(w, z, p, ctx)) goto err;
	if (!BN_GF2m_add(w, z, w)) goto err;
	if (BN_GF2m_cmp(w, a)) goto err;
	if (!BN_copy(r, z)) goto err;
	bn_check_top(r);
	ret = 1;
  err:
	BN_CTX_end(ctx);
	return ret;
	}
['int BN_GF2m_mod_solve_quad_arr(BIGNUM *r, const BIGNUM *a_, const unsigned int p[], BN_CTX *ctx)\n\t{\n\tint ret = 0, count = 0;\n\tunsigned int j;\n\tBIGNUM *a, *z, *rho, *w, *w2, *tmp;\n\tif (!p[0])\n\t\treturn BN_zero(r);\n\tBN_CTX_start(ctx);\n\ta = BN_CTX_get(ctx);\n\tz = BN_CTX_get(ctx);\n\tw = BN_CTX_get(ctx);\n\tif (w == NULL) goto err;\n\tif (!BN_GF2m_mod_arr(a, a_, p)) goto err;\n\tif (BN_is_zero(a))\n\t\t{\n\t\tret = BN_zero(r);\n\t\tgoto err;\n\t\t}\n\tif (p[0] & 0x1)\n\t\t{\n\t\tif (!BN_copy(z, a)) goto err;\n\t\tfor (j = 1; j <= (p[0] - 1) / 2; j++)\n\t\t\t{\n\t\t\tif (!BN_GF2m_mod_sqr_arr(z, z, p, ctx)) goto err;\n\t\t\tif (!BN_GF2m_mod_sqr_arr(z, z, p, ctx)) goto err;\n\t\t\tif (!BN_GF2m_add(z, z, a)) goto err;\n\t\t\t}\n\t\t}\n\telse\n\t\t{\n\t\trho = BN_CTX_get(ctx);\n\t\tw2 = BN_CTX_get(ctx);\n\t\ttmp = BN_CTX_get(ctx);\n\t\tif (tmp == NULL) goto err;\n\t\tdo\n\t\t\t{\n\t\t\tif (!BN_rand(rho, p[0], 0, 0)) goto err;\n\t\t\tif (!BN_GF2m_mod_arr(rho, rho, p)) goto err;\n\t\t\tif (!BN_zero(z)) goto err;\n\t\t\tif (!BN_copy(w, rho)) goto err;\n\t\t\tfor (j = 1; j <= p[0] - 1; j++)\n\t\t\t\t{\n\t\t\t\tif (!BN_GF2m_mod_sqr_arr(z, z, p, ctx)) goto err;\n\t\t\t\tif (!BN_GF2m_mod_sqr_arr(w2, w, p, ctx)) goto err;\n\t\t\t\tif (!BN_GF2m_mod_mul_arr(tmp, w2, a, p, ctx)) goto err;\n\t\t\t\tif (!BN_GF2m_add(z, z, tmp)) goto err;\n\t\t\t\tif (!BN_GF2m_add(w, w2, rho)) goto err;\n\t\t\t\t}\n\t\t\tcount++;\n\t\t\t} while (BN_is_zero(w) && (count < MAX_ITERATIONS));\n\t\tif (BN_is_zero(w))\n\t\t\t{\n\t\t\tBNerr(BN_F_BN_GF2M_MOD_SOLVE_QUAD_ARR,BN_R_TOO_MANY_ITERATIONS);\n\t\t\tgoto err;\n\t\t\t}\n\t\t}\n\tif (!BN_GF2m_mod_sqr_arr(w, z, p, ctx)) goto err;\n\tif (!BN_GF2m_add(w, z, w)) goto err;\n\tif (BN_GF2m_cmp(w, a)) goto err;\n\tif (!BN_copy(r, z)) goto err;\n\tbn_check_top(r);\n\tret = 1;\n  err:\n\tBN_CTX_end(ctx);\n\treturn ret;\n\t}']