montgomery_ladder (mpi_point_t prd, mpi_point_t sum,
                   mpi_point_t p1, mpi_point_t p2, gcry_mpi_t dif_x,
                   mpi_ec_t 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);
}
montgomery_ladder (mpi_point_t prd, mpi_point_t sum,
                   mpi_point_t p1, mpi_point_t p2, gcry_mpi_t dif_x,
                   mpi_ec_t 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->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);
}