123456789101112131415161718192021222324252627282930313233343536373839404142434445464748495051525354555657585960616263646566676869707172737475767778798081828384858687888990919293949596979899100101102103104105106107108109110111112113114115116117118119120121122123124125126127128129130131132133134135136137138139140141142143144145146147148149150151152153154155156157158159160161162163164165166167168169170171172173174175176177178179180181182183184185186187188189(*****************************************************************************)(* *)(* MIT License *)(* Copyright (c) 2022 Nomadic Labs <contact@nomadic-labs.com> *)(* *)(* Permission is hereby granted, free of charge, to any person obtaining a *)(* copy of this software and associated documentation files (the "Software"),*)(* to deal in the Software without restriction, including without limitation *)(* the rights to use, copy, modify, merge, publish, distribute, sublicense, *)(* and/or sell copies of the Software, and to permit persons to whom the *)(* Software is furnished to do so, subject to the following conditions: *)(* *)(* The above copyright notice and this permission notice shall be included *)(* in all copies or substantial portions of the Software. *)(* *)(* THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR*)(* IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, *)(* FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL *)(* THE AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER*)(* LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING *)(* FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER *)(* DEALINGS IN THE SOFTWARE. *)(* *)(*****************************************************************************)moduleFr=Bls12_381.FrmoduleStubs=structtypefr=Fr.ttypefr_arrayexternalallocate_fr_array:int->fr_array="caml_polynomial_allocate_fr_array_stubs"(** [allocate_fr_array n] allocates an OCaml custom block to hold a C array
containing [n] zeros of blst_fr
- requires: [n > 0]
- ensures: [size res = n] and [res] is initialized with zeros of blst_fr *)externalerase_fr_array:fr_array->int->unit="caml_polynomial_erase_fr_array_stubs"(** [erase_fr_array p n] writes [n] zeros of blst_fr in a given array [p]
- requires: [n <= size p]
- ensures: a prefix of size [n] of an array [p] is filled with zeros *)externalof_fr_array:frarray->fr_array->int->unit="caml_polynomial_of_fr_array_stubs"[@@noalloc](** [of_fr_array res p n] converts a given C array [p] of at least size [n] to
an OCaml array [res] of size [n]
- requires: [n <= size p]
- ensures: [size res = n] and [res] is a prefix of [p] *)externalget:fr->fr_array->int->unit="caml_polynomial_get_stubs"[@@noalloc](** [get res p i] writes [i]-th element of a given array [p] in [res]
- requires: [0 <= i < size p]
- ensures: [res = p[i]] *)externalcopy:fr_array->fr_array->int->int->unit="caml_polynomial_copy_stubs"[@@noalloc](** [copy a b offset len] starting from position [offset] copies [len]
elements from array [b] to array [a]
requires:
- [a] and [b] be disjoint
- [len <= size a]
- [offset + len <= size b]
ensures: [a[i] = b[offset + i]] for [i = 0..(len - 1)] *)externalof_dense:fr_array->frarray->int->unit="caml_polynomial_of_dense_stubs"[@@noalloc](** [of_dense res p n] converts an OCaml array [p] of size [n] to a C array [res] of
size [n]
requires:
- [size res = n]
- [size p = n] *)externaleq:fr_array->fr_array->int->int->bool="caml_polynomial_eq_stubs"[@@noalloc](** [eq a b size_a size_b] checks whether a polynomial [a] is equal to a polynomial [b]
requires:
- [size a = size_a]
- [size b = size_b] *)externalis_zero:fr_array->int->bool="caml_polynomial_is_zero_stubs"[@@noalloc](** [is_zero p n] checks whether a prefix of size [n] of an array [p] is filled
with zeros of blst_fr
- requires: [size p >= n] *)endmoduleCarray:sigtypescalar=Bls12_381.Fr.ttypet=Stubs.fr_array*intvalencoding:tData_encoding.tvalallocate:int->Stubs.fr_array(** [allocate len] creates a C array of size [len] intialized with zeros of blst_fr *)valerase:t->unit(** [erase c] overwrites a C array [c] with zeros of blst_fr *)vallength:t->int(** [length c] returns the length of a C array [c] *)valget:t->int->scalar(** [get c i] returns the [i]-th element of a C array [c] *)valcopy:?offset:int->?len:int->t->t(** [copy c] copies [len] elements from a C array [c] starting from position [offset] *)valto_string:t->string(** [to_string c] returns the string representation of a C array [c] *)valto_array:t->scalararray(** [to_array c] converts a C array [c] to an OCaml array *)valof_array:scalararray->t(** [of_array c] converts an OCaml array [c] to a C array *)valequal:t->t->bool(** [equal a b] checks whether a C array [a] is equal to a C array [b]
Note: [equal] is defined as polynomial equality, i.e., [a] and [b] can have
different sizes and padded with zeros of blst_fr *)end=structtypescalar=Bls12_381.Fr.t(* Invariant: size of a P is always > 0 *)typet=Stubs.fr_array*intleterase(p,n)=Stubs.erase_fr_arraypnletlength(_,n)=nletget(p,n)i=ifi<0||i>=nthenraise@@Invalid_argument"get: index out of bounds";letres=Fr.(copyzero)inStubs.getrespi;resletallocaten=ifn<1thenraise@@Invalid_argument"allocate: should be greater than 1"elseStubs.allocate_fr_arraynletto_array(p,n)=letd=Array.initn(fun_->Fr.(copyzero))inStubs.of_fr_arraydpn;dletof_arraycoeff=letn=Array.lengthcoeffinletres=allocateninStubs.of_denserescoeffn;(res,n)letencoding:tData_encoding.t=letopenData_encodinginletfr_encoding=convFr.to_bytesFr.of_bytes_exn(Fixed.bytesFr.size_in_bytes)inconvto_arrayof_array(arrayfr_encoding)letto_stringp=String.concat" ; "(List.mapFr.to_string(Array.to_list@@to_arrayp))letcopy?(offset=0)?len(coefficients,n)=letlen=Option.value~default:nleninassert(offset+len<=n);letres=allocateleninStubs.copyrescoefficientsoffsetlen;(res,len)letequal(poly_1,size_1)(poly_2,size_2)=Stubs.eqpoly_1poly_2size_1size_2endincludeCarray