Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

Missing docs for c++ interface? #72

Closed
earonesty opened this issue Feb 26, 2020 · 14 comments
Closed

Missing docs for c++ interface? #72

earonesty opened this issue Feb 26, 2020 · 14 comments

Comments

@earonesty
Copy link
Contributor

earonesty commented Feb 26, 2020

There are only docs for the C interface. Is that what I should use in a C++ project?

How can I get the bit size for Fr? Is this the right way to create an Fr?

mcl::FpT<mcl::ZnTag, 256> Fr;

Which of these should I use for initializing:

This (seems ok):

Ec P;
mcl::initCurve<Ec, Fr>(MCL_BN381_1, &P);

Or (seems unsafe, cannot use more than 1 curve in an application)

initPairing(mcl::BLS12_381);
G1 P;

How do i get the order and bit-size of Fr/Fp for G1, and G2?

Can I switch between curves in one app? Or is this a big performance hit.

How do i get a 'generator' for G1, and G2? mapToG1(g1, 1) seems ok.

I got everything to work with BLS12_381 (I still thing I am doing some things wrong, lookoing at the getOp().mp instead of higher level stuff to get curve order... but when I use BN254, I get "bad size of register"

@earonesty earonesty changed the title docs for c++ interface Missing docs for c++ interface? Feb 26, 2020
@herumi
Copy link
Owner

herumi commented Feb 27, 2020

Is that what I should use in a C++ project?

I'm sorry for the inadequate documents. I have little time to write it, but I'll do little by little.

Can I switch between curves in one app? Or is this a big performance hit.

What curve parameters do you want to use? Could you tell me what you want?
(use pairing, or only elliptic curve?)

The current version does not support multi parameters.
At first, I had developed the features, but I gave up it because a class dependency was very complicated.

How can I get the bit size for Fr?

The direct function is not provided. Call mcl::gmp::getBitSize() after converting to mpz_class.

The generator of G1/G2 is not unique, so the api is not provided.
mapToG1(P, 1) or hashAndMapToG1(P, "abc", 3).
cf. sample/pairing.cpp

#include <mcl/bls12_381.hpp>

using namespace mcl::bn;

int main()
{
    initPairing(mcl::BLS12_381);
    Fr x;
    x.setStr("12345678abcdefadef", 16);
    printf("x=%s bitSize=%zd\n", x.getStr(16).c_str(), mcl::gmp::getBitSize(x.getMpz()));
    x.setByCSPRNG();
    printf("x=%s bitSize=%zd\n", x.getStr(16).c_str(), mcl::gmp::getBitSize(x.getMpz()));


}

@earonesty
Copy link
Contributor Author

earonesty commented Feb 27, 2020

Thank you so much! We are attempting to use this lib (it is faster than most others) for a searchable threshold encryption system.

  • For your reference, we do ~500 pairing/sec/core for the 381-bit curve. (Intel(R) Xeon(R) CPU E5-2690 0 @ 2.90GHz).

  • I want to provide mcl::BLS12_381, and mcl::BN254 support for pairing (4 times faster, but with weaker guaratees).

  • Currently I use the bitcoin library for secp256k1 support (we use this for some other operations), but probably I would switch to mcl just to have one less library to worry about.

  • It seems I will have to be very careful and "lock and switch", and call initPairing each time I switch between modes with mcl, especially if there are multiple threads using different pairing curves that could be dangerous with mcl.

  • I use mapTo(..1) for an arbitrary generator on G1/G2. I got everything to work for BLS12_381 (all tests pass on linux). But we still get "bad size of register" when init using BN254 for any operations.... even if we turn off all 381 support.

  • Our application uses bitcoin-style serialization for curve parameters (big endian with leading byte sign). Is this the same as "eth serialization"?

  • We disable GMP and use VINT on windows build. But this means we need to big-endian serialize with VINT. Still working on that.

@earonesty
Copy link
Contributor Author

earonesty commented Feb 27, 2020

Things I learned:

  • I figured out to define MCL_VINT_FIXED_BUFFER to compile without GMP.

  • isMSBserialize will always be false unless you change the bitSize of BaseFp? I cannot see how to get it to print out sign of curve points for serialize.

  • Common generator is getG1basePoint for G1, but not G2.

  • ETH mode is === big endian mode. Still can't get it to output 0x02 and 0x03 for the first byte though.

@herumi
Copy link
Owner

herumi commented Feb 28, 2020

there are multiple threads using different pairing curves that could be dangerous with mcl.

I tried to make a very dirty hack of bn.hpp.
I copied bn.hpp to bn2.hpp and renamed the namespace bn to bn2 and comment out according to mapto_wb19.hpp. multi-branch
The sample is multi.cpp.

Fr, G1, et al. are plain object data, then you can use them in a union if you call the correct method of each content.

union Fr {
    bn::Fr x;
    bn2::Fr x;
};

@herumi
Copy link
Owner

herumi commented Feb 28, 2020

But we still get "bad size of register" when init using BN254 for any operations.... even if we turn off all 381 support.

I've seen the error. make bin/bn_test.exe && bin/bn_test.exe runs well?
Could you tell me your OS/CPU/compiler and compile option?

And could you build the wrong binary with debug mode (-Og -g3) and

gdb <the binary>
catch throw
run
bt

Then I can know the position of the exception.

@herumi
Copy link
Owner

herumi commented Feb 28, 2020

Common generator is getG1basePoint for G1, but not G2.

Sorry, the getG1basePoint is NOT for pairing curves.
https://github.com/herumi/mcl/blob/master/include/mcl/bn.h#L544-L549

If you need the ETH base point for BLS12_381, then see Set String. For BN254, please select any generator that you want.

@herumi
Copy link
Owner

herumi commented Feb 28, 2020

ETH mode is === big endian mode. Still can't get it to output 0x02 and 0x03 for the first byte though.

Please see Serialization format of mcl. mcl does not support output 0x02 and 0x03. mcl supports only the compression serialization of ETH.

@earonesty
Copy link
Contributor Author

earonesty commented Feb 28, 2020

yes, bn_test.exe works well, i only have problems when including CMakeLists as a subproject.

make:

g++ -g3 -Wall -Wextra -Wformat=2 -Wcast-qual -Wcast-align -Wwrite-strings -Wfloat-equal -Wpointer-arith -m64 -I include -I test -fomit-frame-pointer -DNDEBUG -Ofast -DMCL_DONT_USE_OPENSSL -fPIC -DMCL_USE_LLVM=1 -c src/fp.cpp -o obj/fp.o -MMD -MP -MF obj/fp.d

vs cmake:

g++ -DMCL_USE_LLVM=1 -I/home/erik/kata/cpp/mcl/include -DMCL_USE_VINT -DMCL_VINT_FIXED_BUFFER -std=c++11 -Wall -Wextra -Wformat=2 -Wcast-qual -Wcast-align -Wwrite-strings -Wfloat-equal -Wpointer-arith -O3 -DNDEBUG -march=native -DMCL_USE_VINT -DMCL_VINT_FIXED_BUFFER -DMCL_DONT_USE_OPENSSL -O3 -DNDEBUG -fPIC -std=gnu++1z -o CMakeFiles/mcl_st.dir/src/fp.cpp.o -c /home/erik/kata/cpp/mcl/src/fp.cpp

maybe it's the O3 vs Ofast? or the -m64 ... not sure. i am trying to make them the same, switched from clang to g++ to be sure. this fails at the very beginning mcl::bn::initPairing(mcl::BN254) during Xbyak::RegExp::RegExp.

The same error occurs with BLS12_381. Haven't figured it out yet.

@herumi
Copy link
Owner

herumi commented Feb 29, 2020

I want to know the following information:

  • OS
  • CPU
  • compiler
  • the line of src/fp_generator.hpp where Xbyak::RegExp throws the exception

Does the following command run well? It runs well on Ubuntu 18.04.4 + Core i7-7700 + gcc 7.4(and clang 8.0.1)

cd mcl
g++ -I ./include -std=c++11 -Wall -Wextra -Wformat=2 -Wcast-qual -Wcast-align -Wwrite-strings -Wfloat-equal -Wpointer-arith -O3 -DNDEBUG -march=native -DMCL_USE_VINT -DMCL_VINT_FIXED_BUFFER -DMCL_DONT_USE_OPENSSL -O3 -DNDEBUG -fPIC -std=gnu++1z src/fp.cpp sample/pairing.cpp && ./a.out

@earonesty
Copy link
Contributor Author

earonesty commented Mar 2, 2020

OS: ubuntu
cpu: (Intel(R) Xeon(R) CPU E5-2690 0 @ 2.90GHz)
compiler: g++ (Ubuntu 7.4.0-1ubuntu1~18.04.1) 7.4.0

I found the problem! The issue was that I was calling initPairing during static initialization. This worked for BN381_1 but it did not work for BLS12_381.

Important when using mcl/c++: be sure to call initPairing from "main", or your regular entry point... not in static initialization.

I think everything works now...we are doing a searchable encryption system using pairings where you can search and never decrypt.

@earonesty
Copy link
Contributor Author

earonesty commented Mar 2, 2020

Windows 64-bit compile I get "divUnit for uint64_t is not supported".
I modified the CMakeLists: if (WIN32) set(CMAKE_CXX_FLAGS "${CMAKE_CXX_FLAGS} -DMCL_VINT_64BIT_PORTABLE")

@earonesty
Copy link
Contributor Author

earonesty commented Mar 2, 2020

I will write a up small help file explaing how to use in C++ (vs api.md which is for c).

Added a pull req to make the windows runtime lib choice optional in the CMakeFile (when using mcl as a cmake component, this was helpful)

@herumi
Copy link
Owner

herumi commented Mar 4, 2020

Windows 64-bit compile I get "divUnit for uint64_t is not supported".

I fixed it and use _udiv128 if possible at a53b6b7

@earonesty
Copy link
Contributor Author

the _udiv128 commit works well on 64-bit windows, i removed the portable flag, no longer needed

@herumi herumi closed this as completed Nov 30, 2021
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
None yet
Projects
None yet
Development

No branches or pull requests

2 participants