add gen_mcl_fp_mont

dev
MITSUNARI Shigeo 9 years ago
parent 8e4ed1aa0b
commit 407e7636b0
  1. 45
      src/gen.cpp
  2. 15
      src/llvm_gen.hpp
  3. 34
      src/mul.txt

@ -25,6 +25,7 @@ struct Code : public mcl::Generator {
FunctionMap mcl_fp_mul_UnitPreM; FunctionMap mcl_fp_mul_UnitPreM;
FunctionMap mcl_fpDbl_mulPreM; FunctionMap mcl_fpDbl_mulPreM;
FunctionMap mcl_fpDbl_sqrPreM; FunctionMap mcl_fpDbl_sqrPreM;
FunctionMap mcl_fp_montM;
FunctionMap mcl_fp_montRedM; FunctionMap mcl_fp_montRedM;
Code() : unit(0), unit2(0), bit(0), N(0) { } Code() : unit(0), unit2(0), bit(0), N(0) { }
@ -593,6 +594,49 @@ struct Code : public mcl::Generator {
generic_fpDbl_mul(py, px, px); generic_fpDbl_mul(py, px, px);
endFunc(); endFunc();
} }
void gen_mcl_fp_mont()
{
const int bu = bit + unit;
const int bu2 = bit + unit * 2;
resetGlobalIdx();
Operand pz(IntPtr, bit);
Operand px(IntPtr, unit);
Operand py(IntPtr, unit);
Operand pp(IntPtr, unit);
Operand r(Int, unit);
std::string name = "mcl_fp_mont" + cybozu::itoa(bit);
mcl_fp_montM[bit] = Function(name, Void, pz, px, py, pp, r);
beginFunc(mcl_fp_montM[bit]);
Operand p = load(bitcast(pp, Operand(IntPtr, bit)));
Operand z, s, a;
for (uint32_t i = 0; i < N; i++) {
Operand y = load(getelementptr(py, makeImm(unit, i)));
Operand xy = call(mulPvM[bit], px, y);
Operand at;
if (i == 0) {
a = zext(xy, bu2);
at = trunc(xy, unit);
} else {
xy = zext(xy, bu2);
a = add(s, xy);
at = trunc(a, unit);
}
Operand q = mul(at, r);
Operand pq = call(mulPvM[bit], pp, q);
pq = zext(pq, bu2);
Operand t = add(a, pq);
s = lshr(t, unit);
}
s = trunc(s, bu);
p = zext(p, bu);
Operand vc = sub(s, p);
Operand c = trunc(lshr(vc, bit), 1);
z = select(c, s, vc);
z = trunc(z, bit);
store(z, pz);
ret(Void);
endFunc();
}
void gen_mcl_fp_montRed() void gen_mcl_fp_montRed()
{ {
const int bu = bit + unit; const int bu = bit + unit;
@ -651,6 +695,7 @@ struct Code : public mcl::Generator {
gen_mcl_fp_mul_UnitPre(); gen_mcl_fp_mul_UnitPre();
gen_mcl_fpDbl_mulPre(); gen_mcl_fpDbl_mulPre();
gen_mcl_fpDbl_sqrPre(); gen_mcl_fpDbl_sqrPre();
gen_mcl_fp_mont();
gen_mcl_fp_montRed(); gen_mcl_fp_montRed();
} }
void setBit(uint32_t bit) void setBit(uint32_t bit)

@ -149,6 +149,7 @@ struct Generator {
Eval call(const Function& f, const Operand& op1, const Operand& op2); Eval call(const Function& f, const Operand& op1, const Operand& op2);
Eval call(const Function& f, const Operand& op1, const Operand& op2, const Operand& op3); Eval call(const Function& f, const Operand& op1, const Operand& op2, const Operand& op3);
Eval call(const Function& f, const Operand& op1, const Operand& op2, const Operand& op3, const Operand& op4); Eval call(const Function& f, const Operand& op1, const Operand& op2, const Operand& op3, const Operand& op4);
Eval call(const Function& f, const Operand& op1, const Operand& op2, const Operand& op3, const Operand& op4, const Operand& op5);
Operand makeImm(uint32_t bit, int64_t imm); Operand makeImm(uint32_t bit, int64_t imm);
}; };
@ -290,6 +291,14 @@ struct Generator::Function {
opv.push_back(op3); opv.push_back(op3);
opv.push_back(op4); opv.push_back(op4);
} }
Function(const std::string& name, const Operand& ret, const Operand& op1, const Operand& op2, const Operand& op3, const Operand& op4, const Operand& op5)
: name(name), ret(ret), isPrivate(false) {
opv.push_back(op1);
opv.push_back(op2);
opv.push_back(op3);
opv.push_back(op4);
opv.push_back(op5);
}
void setPrivate() void setPrivate()
{ {
isPrivate = true; isPrivate = true;
@ -544,6 +553,12 @@ inline Generator::Eval Generator::call(const Generator::Function& f, const Gener
return impl::callSub(f, tbl, CYBOZU_NUM_OF_ARRAY(tbl)); return impl::callSub(f, tbl, CYBOZU_NUM_OF_ARRAY(tbl));
} }
inline Generator::Eval Generator::call(const Generator::Function& f, const Generator::Operand& op1, const Generator::Operand& op2, const Generator::Operand& op3, const Generator::Operand& op4, const Generator::Operand& opt5)
{
const Operand *tbl[] = { &op1, &op2, &op3, &op4, &opt5 };
return impl::callSub(f, tbl, CYBOZU_NUM_OF_ARRAY(tbl));
}
#define MCL_GEN_FUNCTION(name, ...) Function name(#name, __VA_ARGS__) #define MCL_GEN_FUNCTION(name, ...) Function name(#name, __VA_ARGS__)
} // mcl } // mcl

@ -2,37 +2,3 @@
@define bu = bit + unit @define bu = bit + unit
@define bu2 = bit + unit * 2 @define bu2 = bit + unit * 2
define void @mcl_fp_mont$(bit)(i$(bit)* %pz, i$(unit)* %px, i$(unit)* %py, i$(unit)* %pp, i$(unit) %r) {
%ppt = bitcast i$(unit)* %pp to i$(bit)*
%p = load i$(bit)* %ppt
@for i, 0, N
%py$(i) = getelementptr i$(unit)* %py, i$(unit) $(i)
%y$(i) = load i$(unit)* %py$(i)
%xy$(i) = call i$(bu) @mulPv$(bit)x$(unit)(i$(unit)* %px, i$(unit) %y$(i))
@if i == 0
%a0 = zext i$(bu) %xy0 to i$(bu2)
%at$(i) = trunc i$(bu) %xy$(i) to i$(unit)
@else
%xye$(i) = zext i$(bu) %xy$(i) to i$(bu2)
%a$(i) = add i$(bu2) %s$(i-1), %xye$(i)
%at$(i) = trunc i$(bu2) %a$(i) to i$(unit)
@endif
%q$(i) = mul i$(unit) %at$(i), %r
%pq$(i) = call i$(bu) @mulPv$(bit)x$(unit)(i$(unit)* %pp, i$(unit) %q$(i))
%pqe$(i) = zext i$(bu) %pq$(i) to i$(bu2)
%t$(i) = add i$(bu2) %a$(i), %pqe$(i)
%s$(i) = lshr i$(bu2) %t$(i), $(unit)
@endfor
%v = trunc i$(bu2) %s$(N-1) to i$(bu)
%pe = zext i$(bit) %p to i$(bu)
%vc = sub i$(bu) %v, %pe
%c = lshr i$(bu) %vc, $(bit)
%c1 = trunc i$(bu) %c to i1
%z = select i1 %c1, i$(bu) %v, i$(bu) %vc
%zt = trunc i$(bu) %z to i$(bit)
store i$(bit) %zt, i$(bit)* %pz
ret void
}

Loading…
Cancel
Save