diff --git a/ot/simplestOT/simplestOT_test.go b/ot/simot/simot_test.go similarity index 58% rename from ot/simplestOT/simplestOT_test.go rename to ot/simot/simot_test.go index 8868f8f8f..32e4aa550 100644 --- a/ot/simplestOT/simplestOT_test.go +++ b/ot/simot/simot_test.go @@ -1,4 +1,8 @@ -package simplestOT +// Reference: https://eprint.iacr.org/2015/267.pdf (1 out of 2 OT case) +// Sender has 2 messages m0, m1 +// Receiver receives mc based on the choice bit c + +package simot import ( "bytes" @@ -8,15 +12,43 @@ import ( "github.com/cloudflare/circl/group" ) -const TestBaseOTCount = 100 +const testSimOTCount = 100 + +func simOT(myGroup group.Group, sender *SenderSimOT, receiver *ReceiverSimOT, m0, m1 []byte, choice, index int) error { + // Initialization + A := sender.InitSender(myGroup, m0, m1, index) + + // Round 1 + // Sender sends A to receiver + B := receiver.Round1Receiver(myGroup, choice, index, A) + + // Round 2 + // Receiver sends B to sender + e0, e1 := sender.Round2Sender(B) + + // Round 3 + // Sender sends e0 e1 to receiver + errDec := receiver.Round3Receiver(e0, e1, receiver.c) + if errDec != nil { + return errDec + } + + return nil +} -func testNegativeBaseOT(t *testing.T, myGroup group.Group, choice int) { +func testNegativeSimOT(t *testing.T, myGroup group.Group, choice int) { var sender SenderSimOT var receiver ReceiverSimOT m0 := make([]byte, myGroup.Params().ScalarLength) m1 := make([]byte, myGroup.Params().ScalarLength) - rand.Read(m0) - rand.Read(m1) + _, errRand := rand.Read(m0) + if errRand != nil { + panic(errRand) + } + _, errRand = rand.Read(m1) + if errRand != nil { + panic(errRand) + } // Initialization A := sender.InitSender(myGroup, m0, m1, 0) @@ -32,7 +64,7 @@ func testNegativeBaseOT(t *testing.T, myGroup group.Group, choice int) { // The receiver will not learn anything about m_{1-c} errDec := receiver.Round3Receiver(e0, e1, 1-choice) if errDec == nil { - t.Error("BaseOT decryption failed", errDec) + t.Error("SimOT decryption failed", errDec) } if choice == 0 { @@ -54,23 +86,29 @@ func testNegativeBaseOT(t *testing.T, myGroup group.Group, choice int) { t.Error("Receiver decryption should fail") } } - } // Input: myGroup, the group we operate in -func testBaseOT(t *testing.T, myGroup group.Group, choice int) { +func testSimOT(t *testing.T, myGroup group.Group, choice int) { var sender SenderSimOT var receiver ReceiverSimOT m0 := make([]byte, myGroup.Params().ScalarLength) m1 := make([]byte, myGroup.Params().ScalarLength) - rand.Read(m0) - rand.Read(m1) - err := BaseOT(myGroup, &sender, &receiver, m0, m1, choice, 0) - if err != nil { - t.Error("BaseOT failed", err) + _, errRand := rand.Read(m0) + if errRand != nil { + panic(errRand) + } + _, errRand = rand.Read(m1) + if errRand != nil { + panic(errRand) + } + + errDec := simOT(myGroup, &sender, &receiver, m0, m1, choice, 0) + if errDec != nil { + t.Error("AES GCM Decryption failed") } - //Confirm + if choice == 0 { equal0 := bytes.Compare(sender.m0, receiver.mc) if equal0 != 0 { @@ -84,29 +122,41 @@ func testBaseOT(t *testing.T, myGroup group.Group, choice int) { } } -func benchmarBaseOT(b *testing.B, myGroup group.Group) { +func benchmarSimOT(b *testing.B, myGroup group.Group) { var sender SenderSimOT var receiver ReceiverSimOT m0 := make([]byte, myGroup.Params().ScalarLength) m1 := make([]byte, myGroup.Params().ScalarLength) - rand.Read(m0) - rand.Read(m1) + _, errRand := rand.Read(m0) + if errRand != nil { + panic(errRand) + } + _, errRand = rand.Read(m1) + if errRand != nil { + panic(errRand) + } for iter := 0; iter < b.N; iter++ { - err := BaseOT(myGroup, &sender, &receiver, m0, m1, iter%2, 0) - if err != nil { - b.Error("BaseOT failed") + errDec := simOT(myGroup, &sender, &receiver, m0, m1, iter%2, 0) + if errDec != nil { + b.Error("AES GCM Decryption failed") } } } -func benchmarkBaseOTRound(b *testing.B, myGroup group.Group) { +func benchmarkSimOTRound(b *testing.B, myGroup group.Group) { var sender SenderSimOT var receiver ReceiverSimOT m0 := make([]byte, myGroup.Params().ScalarLength) m1 := make([]byte, myGroup.Params().ScalarLength) - rand.Read(m0) - rand.Read(m1) + _, errRand := rand.Read(m0) + if errRand != nil { + panic(errRand) + } + _, errRand = rand.Read(m1) + if errRand != nil { + panic(errRand) + } b.Run("Sender-Initialization", func(b *testing.B) { for i := 0; i < b.N; i++ { @@ -127,7 +177,6 @@ func benchmarkBaseOTRound(b *testing.B, myGroup group.Group) { b.Run("Sender-Round2", func(b *testing.B) { for i := 0; i < b.N; i++ { sender.Round2Sender(B) - } }) @@ -152,34 +201,31 @@ func benchmarkBaseOTRound(b *testing.B, myGroup group.Group) { if equal0 != 0 { b.Error("Receiver decryption failed") } - } -func TestBaseOT(t *testing.T) { - - t.Run("BaseOT", func(t *testing.T) { - for i := 0; i < TestBaseOTCount; i++ { +func TestSimOT(t *testing.T) { + t.Run("SimOT", func(t *testing.T) { + for i := 0; i < testSimOTCount; i++ { currGroup := group.P256 choice := i % 2 - testBaseOT(t, currGroup, choice) + testSimOT(t, currGroup, choice) } }) - t.Run("BaseOTNegative", func(t *testing.T) { - for i := 0; i < TestBaseOTCount; i++ { + t.Run("SimOTNegative", func(t *testing.T) { + for i := 0; i < testSimOTCount; i++ { currGroup := group.P256 choice := i % 2 - testNegativeBaseOT(t, currGroup, choice) + testNegativeSimOT(t, currGroup, choice) } }) - } -func BenchmarkBaseOT(b *testing.B) { +func BenchmarkSimOT(b *testing.B) { currGroup := group.P256 - benchmarBaseOT(b, currGroup) + benchmarSimOT(b, currGroup) } -func BenchmarkBaseOTRound(b *testing.B) { +func BenchmarkSimOTRound(b *testing.B) { currGroup := group.P256 - benchmarkBaseOTRound(b, currGroup) + benchmarkSimOTRound(b, currGroup) } diff --git a/ot/simplestOT/simplestOTLocal.go b/ot/simot/simotlocal.go similarity index 98% rename from ot/simplestOT/simplestOTLocal.go rename to ot/simot/simotlocal.go index a977e7fc7..fabd3de56 100644 --- a/ot/simplestOT/simplestOTLocal.go +++ b/ot/simot/simotlocal.go @@ -1,4 +1,4 @@ -package simplestOT +package simot import ( "crypto/aes" @@ -66,7 +66,7 @@ func aesDecGCM(key, ciphertext []byte) ([]byte, error) { // Input: myGroup, the group we operate in // Input: m0, m1 the 2 message of the sender -// Input: index, the index of this BaseOT +// Input: index, the index of this SimOT // Output: A = [a]G, a the sender randomness func (sender *SenderSimOT) InitSender(myGroup group.Group, m0, m1 []byte, index int) group.Element { sender.a = myGroup.RandomNonZeroScalar(rand.Reader) @@ -87,7 +87,7 @@ func (sender *SenderSimOT) InitSender(myGroup group.Group, m0, m1 []byte, index // Input: myGroup, the group we operate in // Input: choice, the receiver choice bit -// Input: index, the index of this BaseOT +// Input: index, the index of this SimOT // Input: A, from sender // Output: B = [b]G if c == 0, B = A+[b]G if c == 1 (Implementation in constant time). b, the receiver randomness func (receiver *ReceiverSimOT) Round1Receiver(myGroup group.Group, choice int, index int, A group.Element) group.Element { diff --git a/ot/simplestOT/simplestOTParty.go b/ot/simot/simotparty.go similarity index 98% rename from ot/simplestOT/simplestOTParty.go rename to ot/simot/simotparty.go index f41f6aac7..d4f677130 100644 --- a/ot/simplestOT/simplestOTParty.go +++ b/ot/simot/simotparty.go @@ -1,4 +1,4 @@ -package simplestOT +package simot import "github.com/cloudflare/circl/group" diff --git a/ot/simplestOT/simplestOT.go b/ot/simplestOT/simplestOT.go deleted file mode 100644 index 778f893b9..000000000 --- a/ot/simplestOT/simplestOT.go +++ /dev/null @@ -1,36 +0,0 @@ -// Reference: https://eprint.iacr.org/2015/267.pdf (1 out of 2 OT case) -// Sender has 2 messages m0, m1 -// Receiver receives mc based on the choice bit c - -package simplestOT - -import ( - "github.com/cloudflare/circl/group" -) - -// Input: myGroup, the group we operate in -// Input: m0, m1 the 2 message of the sender -// Input: choice, the bit c of the receiver -// Input: index, the index of this BaseOT -func BaseOT(myGroup group.Group, sender *SenderSimOT, receiver *ReceiverSimOT, m0, m1 []byte, choice, index int) error { - - // Initialization - A := sender.InitSender(myGroup, m0, m1, index) - - // Round 1 - // Sender sends A to receiver - B := receiver.Round1Receiver(myGroup, choice, index, A) - - // Round 2 - // Receiver sends B to sender - e0, e1 := sender.Round2Sender(B) - - // Round 3 - // Sender sends e0 e1 to receiver - errDec := receiver.Round3Receiver(e0, e1, receiver.c) - if errDec != nil { - return errDec - } - - return nil -} diff --git a/tss/ecdsa/ot/Fmul/FmulLocal.go b/tss/ecdsa/dkls/fmul/fmulLocal.go similarity index 80% rename from tss/ecdsa/ot/Fmul/FmulLocal.go rename to tss/ecdsa/dkls/fmul/fmulLocal.go index 59cbddf24..0ad7d13ae 100644 --- a/tss/ecdsa/ot/Fmul/FmulLocal.go +++ b/tss/ecdsa/dkls/fmul/fmulLocal.go @@ -1,4 +1,4 @@ -package Fmul +package fmul import ( "crypto/rand" @@ -6,23 +6,31 @@ import ( "sync" "github.com/cloudflare/circl/group" - "github.com/cloudflare/circl/ot/simplestOT" + "github.com/cloudflare/circl/ot/simot" "golang.org/x/sync/errgroup" ) +// Input: myGroup, the group we operate in +// Input: securityParameter +// Output: The number of SimOT needed +func DecideNumOT(myGroup group.Group, sp int) int { + numSimOT := int(myGroup.Params().ScalarLength*8) + sp + return numSimOT +} + // ---- Sender Initialization ---- // Input: myGroup, the group we operate in // Input: a, the sender private input -// Input: n, the total number of BaseOT -// Output: Array of A=[ai]G for n BaseOT +// Input: n, the total number of SimOT +// Output: Array of A=[ai]G for n SimOT func (sender *SenderFmul) SenderInit(myGroup group.Group, a group.Scalar, n int) []group.Element { sender.myGroup = myGroup sender.a = a.Copy() sender.deltas = make([]group.Scalar, n) sender.m0s = make([][]byte, n) sender.m1s = make([][]byte, n) - sender.baseOTsenders = make([]simplestOT.SenderSimOT, n) + sender.simOTsenders = make([]simot.SenderSimOT, n) var fmulWait sync.WaitGroup fmulWait.Add(n) @@ -48,10 +56,10 @@ func (sender *SenderFmul) SenderInit(myGroup group.Group, a group.Scalar, n int) } sender.m1s[index] = m1iByte - // n Base OT Sender Initialization - var BaseOTSender simplestOT.SenderSimOT - BaseOTSender.InitSender(myGroup, sender.m0s[index], sender.m1s[index], index) - sender.baseOTsenders[index] = BaseOTSender + // n Sim OT Sender Initialization + var simOTSender simot.SenderSimOT + simOTSender.InitSender(myGroup, sender.m0s[index], sender.m1s[index], index) + sender.simOTsenders[index] = simOTSender }(i) } fmulWait.Wait() @@ -61,20 +69,19 @@ func (sender *SenderFmul) SenderInit(myGroup group.Group, a group.Scalar, n int) As := make([]group.Element, n) for i := 0; i < n; i++ { - As[i] = sender.baseOTsenders[i].A.Copy() + As[i] = sender.simOTsenders[i].A.Copy() } return As - } // ---- Round1: Sender sends As to receiver ---- -// Receiver randomly generates n choice bits, either 0 or 1 for BaseOT, either -1(Scalar) or 1(Scalar) for Fmul +// Receiver randomly generates n choice bits, either 0 or 1 for SimOT, either -1(Scalar) or 1(Scalar) for Fmul // Matching 0 or 1 to -1(Scalar) or 1(Scalar) in constant time // Input: myGroup, the group we operate in // Input: As, the n [ai]G received from sender // Input: b, the receiver private input -// Input: n, the total number of BaseOT +// Input: n, the total number of SimOT // Output: Array of B = [b]G if c == 0, B = A+[b]G if c == 1 func (receiver *ReceiverFmul) ReceiverRound1(myGroup group.Group, As []group.Element, b group.Scalar, n int) []group.Element { receiver.myGroup = myGroup @@ -88,7 +95,7 @@ func (receiver *ReceiverFmul) ReceiverRound1(myGroup group.Group, As []group.Ele Scalar1.SetUint64(1) Scalar1.Neg(Scalar1) - receiver.baseOTreceivers = make([]simplestOT.ReceiverSimOT, n) + receiver.simOTreceivers = make([]simot.ReceiverSimOT, n) var fmulWait sync.WaitGroup fmulWait.Add(n) @@ -106,7 +113,7 @@ func (receiver *ReceiverFmul) ReceiverRound1(myGroup group.Group, As []group.Ele receiver.tsScalar[index] = Scalar1.Copy() receiver.tsScalar[index].Sub(receiver.tsScalar[index], currScalar) receiver.zs[index] = myGroup.NewScalar() - receiver.baseOTreceivers[index].Round1Receiver(myGroup, receiver.ts[index], index, As[index]) + receiver.simOTreceivers[index].Round1Receiver(myGroup, receiver.ts[index], index, As[index]) }(i) } fmulWait.Wait() @@ -116,7 +123,7 @@ func (receiver *ReceiverFmul) ReceiverRound1(myGroup group.Group, As []group.Ele Bs := make([]group.Element, n) for i := 0; i < n; i++ { - Bs[i] = receiver.baseOTreceivers[i].B.Copy() + Bs[i] = receiver.simOTreceivers[i].B.Copy() } return Bs } @@ -124,7 +131,7 @@ func (receiver *ReceiverFmul) ReceiverRound1(myGroup group.Group, As []group.Ele // ---- Round 2: Receiver sends Bs = [bi]G or Ai+[bi]G to sender ---- // Input: Bs, the n [bi]G or Ai+[bi]G received from receiver -// Input: n, the total number of BaseOT +// Input: n, the total number of SimOT // Output: Array of m0s encryptions and m1s encryptions func (sender *SenderFmul) SenderRound2(Bs []group.Element, n int) ([][]byte, [][]byte) { var fmulWait sync.WaitGroup @@ -132,7 +139,7 @@ func (sender *SenderFmul) SenderRound2(Bs []group.Element, n int) ([][]byte, [][ for i := 0; i < n; i++ { go func(index int) { defer fmulWait.Done() - sender.baseOTsenders[index].Round2Sender(Bs[index]) + sender.simOTsenders[index].Round2Sender(Bs[index]) }(i) } fmulWait.Wait() @@ -140,7 +147,7 @@ func (sender *SenderFmul) SenderRound2(Bs []group.Element, n int) ([][]byte, [][ e0s := make([][]byte, n) e1s := make([][]byte, n) for i := 0; i < n; i++ { - e0s[i], e1s[i] = sender.baseOTsenders[i].Returne0e1() + e0s[i], e1s[i] = sender.simOTsenders[i].Returne0e1() } return e0s, e1s @@ -149,7 +156,7 @@ func (sender *SenderFmul) SenderRound2(Bs []group.Element, n int) ([][]byte, [][ // ---- Round 3: Sender sends e0s, e1s to receiver ---- // Input: e0s, e1s, the encryptions of m0s and m1s -// Input: n, the total number of BaseOT +// Input: n, the total number of SimOT // Ouptut: Blinding sigma and Array of v func (receiver *ReceiverFmul) ReceiverRound3(e0s, e1s [][]byte, n int) (group.Scalar, []group.Scalar, error) { var errGroup errgroup.Group @@ -158,11 +165,11 @@ func (receiver *ReceiverFmul) ReceiverRound3(e0s, e1s [][]byte, n int) (group.Sc for i := 0; i < n; i++ { func(index int) { errGroup.Go(func() error { - errDec := receiver.baseOTreceivers[index].Round3Receiver(e0s[index], e1s[index], receiver.ts[index]) + errDec := receiver.simOTreceivers[index].Round3Receiver(e0s[index], e1s[index], receiver.ts[index]) if errDec != nil { return errDec } - mc := receiver.baseOTreceivers[index].Returnmc() + mc := receiver.simOTreceivers[index].Returnmc() errByte := receiver.zs[index].UnmarshalBinary(mc) if errByte != nil { panic(errByte) @@ -212,7 +219,7 @@ func (receiver *ReceiverFmul) ReceiverRound3(e0s, e1s [][]byte, n int) (group.Sc // Input: vs, from receiver // Input: sigma, blinding from receiver -// Input: n, the total number of BaseOT +// Input: n, the total number of SimOT func (sender *SenderFmul) SenderRound4(vs []group.Scalar, sigma group.Scalar, n int) { sender.s1.SetUint64(0) diff --git a/tss/ecdsa/dkls/fmul/fmulParty.go b/tss/ecdsa/dkls/fmul/fmulParty.go new file mode 100644 index 000000000..44f312e5f --- /dev/null +++ b/tss/ecdsa/dkls/fmul/fmulParty.go @@ -0,0 +1,28 @@ +package fmul + +import ( + "github.com/cloudflare/circl/group" + "github.com/cloudflare/circl/ot/simot" +) + +type SenderFmul struct { + a group.Scalar // The input of the sender + deltas []group.Scalar // The n random of the sender + m0s [][]byte // The n m0 messages of the sender + m1s [][]byte // The n m1 messages of the sender + simOTsenders []simot.SenderSimOT // The n senders for n simOT + s1 group.Scalar // The final additive share + myGroup group.Group // The elliptic curve we operate in +} + +type ReceiverFmul struct { + b group.Scalar // The input of the receiver + ts []int // The n choice bits of the receiver, either 0 or 1 + tsScalar []group.Scalar // The scalar version of n choice bits, either -1 or 1 + zs []group.Scalar // The n OT transferred messages from the sender + vs []group.Scalar // The n random of the receiver such that v*t = b + sigma group.Scalar // The blinding scalar + simOTreceivers []simot.ReceiverSimOT // The n receivers for n simOT + s2 group.Scalar // The final additive share + myGroup group.Group // The elliptic curve we operate in +} diff --git a/tss/ecdsa/ot/Fmul/Fmul_test.go b/tss/ecdsa/dkls/fmul/fmul_test.go similarity index 74% rename from tss/ecdsa/ot/Fmul/Fmul_test.go rename to tss/ecdsa/dkls/fmul/fmul_test.go index 44df8313d..ca8ebefd6 100644 --- a/tss/ecdsa/ot/Fmul/Fmul_test.go +++ b/tss/ecdsa/dkls/fmul/fmul_test.go @@ -1,4 +1,9 @@ -package Fmul +// Reference: https://eprint.iacr.org/2021/1373.pdf +// Sender and receiver has private input a and b +// Sender and receiver get s1 and s2 such that a*b = s1+s2 from Fmul +// This scheme based on pure OT but not OT extension + +package fmul import ( "crypto/rand" @@ -8,7 +13,36 @@ import ( "github.com/cloudflare/circl/group" ) -const TestFmulCount = 50 +const testFmulCount = 50 + +// Input: aInput, bInput, the private input from both sender and receiver +// Input: myGroup, the group we operate in +// Input: n, the total number of SimOT +func fmul(sender *SenderFmul, receiver *ReceiverFmul, aInput, bInput group.Scalar, myGroup group.Group, n int) error { + // Sender Initialization + As := sender.SenderInit(myGroup, aInput, n) + + // ---- Round1: Sender sends As to receiver ---- + + Bs := receiver.ReceiverRound1(myGroup, As, bInput, n) + + // ---- Round 2: Receiver sends Bs = [bi]G or Ai+[bi]G to sender ---- + + e0s, e1s := sender.SenderRound2(Bs, n) + + // ---- Round 3: Sender sends e0s, e1s to receiver ---- + + sigma, vs, errDec := receiver.ReceiverRound3(e0s, e1s, n) + if errDec != nil { + return errDec + } + + // ---- Round 4: receiver sends sigma as well as vs to sender ---- + + sender.SenderRound4(vs, sigma, n) + + return nil +} func testFmul(t *testing.T, myGroup group.Group) { n := DecideNumOT(myGroup, 128) @@ -17,7 +51,7 @@ func testFmul(t *testing.T, myGroup group.Group) { aSender := myGroup.RandomNonZeroScalar(rand.Reader) bReceiver := myGroup.RandomNonZeroScalar(rand.Reader) - err := Fmul(&sender, &receiver, aSender, bReceiver, myGroup, n) + err := fmul(&sender, &receiver, aSender, bReceiver, myGroup, n) if err != nil { t.Error("Fmul decryption fail", err) } @@ -31,7 +65,6 @@ func testFmul(t *testing.T, myGroup group.Group) { if add.IsEqual(mul) == false { t.Error("Fmul reconstruction failed") } - } // Note the receiver has no space to cheat in the protocol. @@ -63,9 +96,7 @@ func testFmulNegative(t *testing.T, myGroup group.Group) { } randomIndex := int(nBig.Int64()) savee0 := make([]byte, len(e0s[randomIndex])) - for i := 0; i < int(len(e0s[randomIndex])); i++ { - savee0[i] = e0s[randomIndex][i] - } + copy(savee0, e0s[randomIndex]) e0s[randomIndex] = e1s[randomIndex] e1s[randomIndex] = savee0 @@ -75,7 +106,6 @@ func testFmulNegative(t *testing.T, myGroup group.Group) { if err == nil { t.Error("Fmul decryption should fail", err) } - } func benchmarFmul(b *testing.B, myGroup group.Group) { @@ -86,7 +116,7 @@ func benchmarFmul(b *testing.B, myGroup group.Group) { aSender := myGroup.RandomNonZeroScalar(rand.Reader) bReceiver := myGroup.RandomNonZeroScalar(rand.Reader) - err := Fmul(&sender, &receiver, aSender, bReceiver, myGroup, n) + err := fmul(&sender, &receiver, aSender, bReceiver, myGroup, n) if err != nil { b.Error("Fmul reconstruction failed") } @@ -156,24 +186,21 @@ func benchmarFmulRound(b *testing.B, myGroup group.Group) { if add.IsEqual(mul) == false { b.Error("Fmul reconstruction failed") } - } func TestFmul(t *testing.T) { - - t.Run("Fmul", func(t *testing.T) { - for i := 0; i < TestFmulCount; i++ { + t.Run("fmul", func(t *testing.T) { + for i := 0; i < testFmulCount; i++ { currGroup := group.P256 testFmul(t, currGroup) } }) - t.Run("FmulNegative", func(t *testing.T) { - for i := 0; i < TestFmulCount; i++ { + t.Run("fmulNegative", func(t *testing.T) { + for i := 0; i < testFmulCount; i++ { currGroup := group.P256 testFmulNegative(t, currGroup) } }) - } func BenchmarkFmul(b *testing.B) { diff --git a/tss/ecdsa/ot/Fmul/Fmul.go b/tss/ecdsa/ot/Fmul/Fmul.go deleted file mode 100644 index 265d3caa8..000000000 --- a/tss/ecdsa/ot/Fmul/Fmul.go +++ /dev/null @@ -1,47 +0,0 @@ -// Reference: https://eprint.iacr.org/2021/1373.pdf -// Sender and receiver has private input a and b -// Sender and receiver get s1 and s2 such that a*b = s1+s2 from Fmul -// This scheme based on pure OT but not OT extension - -package Fmul - -import ( - "github.com/cloudflare/circl/group" -) - -// Input: myGroup, the group we operate in -// Input: securityParameter -// Output: The number of BaseOT needed -func DecideNumOT(myGroup group.Group, sp int) int { - numBaseOT := int(myGroup.Params().ScalarLength*8) + sp - return numBaseOT -} - -// Input: aInput, bInput, the private input from both sender and receiver -// Input: myGroup, the group we operate in -// Input: n, the total number of BaseOT -func Fmul(sender *SenderFmul, receiver *ReceiverFmul, aInput, bInput group.Scalar, myGroup group.Group, n int) error { - // Sender Initialization - As := sender.SenderInit(myGroup, aInput, n) - - // ---- Round1: Sender sends As to receiver ---- - - Bs := receiver.ReceiverRound1(myGroup, As, bInput, n) - - // ---- Round 2: Receiver sends Bs = [bi]G or Ai+[bi]G to sender ---- - - e0s, e1s := sender.SenderRound2(Bs, n) - - // ---- Round 3: Sender sends e0s, e1s to receiver ---- - - sigma, vs, errDec := receiver.ReceiverRound3(e0s, e1s, n) - if errDec != nil { - return errDec - } - - // ---- Round 4: receiver sends sigma as well as vs to sender ---- - - sender.SenderRound4(vs, sigma, n) - - return nil -} diff --git a/tss/ecdsa/ot/Fmul/FmulParty.go b/tss/ecdsa/ot/Fmul/FmulParty.go deleted file mode 100644 index 4a09d38f9..000000000 --- a/tss/ecdsa/ot/Fmul/FmulParty.go +++ /dev/null @@ -1,28 +0,0 @@ -package Fmul - -import ( - "github.com/cloudflare/circl/group" - "github.com/cloudflare/circl/ot/simplestOT" -) - -type SenderFmul struct { - a group.Scalar // The input of the sender - deltas []group.Scalar // The n random of the sender - m0s [][]byte // The n m0 messages of the sender - m1s [][]byte // The n m1 messages of the sender - baseOTsenders []simplestOT.SenderSimOT // The n senders for n baseOT - s1 group.Scalar // The final additive share - myGroup group.Group // The elliptic curve we operate in -} - -type ReceiverFmul struct { - b group.Scalar // The input of the receiver - ts []int // The n choice bits of the receiver, either 0 or 1 - tsScalar []group.Scalar // The scalar version of n choice bits, either -1 or 1 - zs []group.Scalar // The n OT transfered messages from the sender - vs []group.Scalar // The n random of the receiver such that v*t = b - sigma group.Scalar // The blinding scalar - baseOTreceivers []simplestOT.ReceiverSimOT // The n receivers for n baseOT - s2 group.Scalar // The final additive share - myGroup group.Group // The elliptic curve we operate in -} diff --git a/zk/dl/zkRDL.go b/zk/dl/dl.go similarity index 84% rename from zk/dl/zkRDL.go rename to zk/dl/dl.go index 1b4e32f96..98ac03d9a 100644 --- a/zk/dl/zkRDL.go +++ b/zk/dl/dl.go @@ -1,9 +1,9 @@ // Reference: https://datatracker.ietf.org/doc/html/rfc8235#page-6 // Prove the knowledge of [k] given [k]G, G and the curve where the points reside -package zkRDL +package dl import ( - "crypto/rand" + "io" "github.com/cloudflare/circl/group" ) @@ -12,9 +12,8 @@ import ( // Input: R = [kA]DB // Input: proverLabel, verifierLabel labels of prover and verifier // Ouptput: (V,r), the prove such that we know kA without revealing kA -func ProveGen(myGroup group.Group, DB, R group.Element, kA group.Scalar, proverLabel, verifierLabel []byte) (group.Element, group.Scalar) { - - v := myGroup.RandomNonZeroScalar(rand.Reader) +func ProveGen(myGroup group.Group, DB, R group.Element, kA group.Scalar, proverLabel, verifierLabel, dst []byte, rnd io.Reader) (group.Element, group.Scalar) { + v := myGroup.RandomNonZeroScalar(rnd) V := myGroup.NewElement() V.Mul(DB, v) @@ -38,8 +37,7 @@ func ProveGen(myGroup group.Group, DB, R group.Element, kA group.Scalar, proverL hashByte = append(hashByte, proverLabel...) hashByte = append(hashByte, verifierLabel...) - dst := "zeroknowledge" - c := myGroup.HashToScalar(hashByte, []byte(dst)) + c := myGroup.HashToScalar(hashByte, dst) kAc := myGroup.NewScalar() kAc.Mul(c, kA) @@ -54,7 +52,7 @@ func ProveGen(myGroup group.Group, DB, R group.Element, kA group.Scalar, proverL // Input: (V,r), the prove such that the prover knows kA // Input: proverLabel, verifierLabel labels of prover and verifier // Output: V ?= [r]D_B +[c]R -func Verify(myGroup group.Group, DB, R group.Element, V group.Element, r group.Scalar, proverLabel, verifierLabel []byte) bool { +func Verify(myGroup group.Group, DB, R group.Element, V group.Element, r group.Scalar, proverLabel, verifierLabel, dst []byte) bool { // Hash the transcript (D_B | V | R | proverLabel | verifierLabel) to get the random coin DBByte, errByte := DB.MarshalBinary() if errByte != nil { @@ -74,8 +72,7 @@ func Verify(myGroup group.Group, DB, R group.Element, V group.Element, r group.S hashByte = append(hashByte, proverLabel...) hashByte = append(hashByte, verifierLabel...) - dst := "zeroknowledge" - c := myGroup.HashToScalar(hashByte, []byte(dst)) + c := myGroup.HashToScalar(hashByte, dst) rDB := myGroup.NewElement() rDB.Mul(DB, r) diff --git a/zk/dl/zkRDL_test.go b/zk/dl/dl_test.go similarity index 57% rename from zk/dl/zkRDL_test.go rename to zk/dl/dl_test.go index 4716981d7..aaf306e43 100644 --- a/zk/dl/zkRDL_test.go +++ b/zk/dl/dl_test.go @@ -1,4 +1,4 @@ -package zkRDL +package dl import ( "crypto/rand" @@ -7,53 +7,53 @@ import ( "github.com/cloudflare/circl/group" ) -const TestzkRDLCount = 10 +const testzkDLCount = 10 -func testzkRDL(t *testing.T, myGroup group.Group) { +func testzkDL(t *testing.T, myGroup group.Group) { kA := myGroup.RandomNonZeroScalar(rand.Reader) DB := myGroup.RandomElement(rand.Reader) R := myGroup.NewElement() R.Mul(DB, kA) - V, r := ProveGen(myGroup, DB, R, kA, []byte("Prover"), []byte("Verifier")) + dst := "zeroknowledge" + rnd := rand.Reader + V, r := ProveGen(myGroup, DB, R, kA, []byte("Prover"), []byte("Verifier"), []byte(dst), rnd) - verify := Verify(myGroup, DB, R, V, r, []byte("Prover"), []byte("Verifier")) + verify := Verify(myGroup, DB, R, V, r, []byte("Prover"), []byte("Verifier"), []byte(dst)) if verify == false { t.Error("zkRDL verification failed") } - } -func testzkRDLNegative(t *testing.T, myGroup group.Group) { +func testzkDLNegative(t *testing.T, myGroup group.Group) { kA := myGroup.RandomNonZeroScalar(rand.Reader) DB := myGroup.RandomElement(rand.Reader) R := myGroup.RandomElement(rand.Reader) - V, r := ProveGen(myGroup, DB, R, kA, []byte("Prover"), []byte("Verifier")) + dst := "zeroknowledge" + rnd := rand.Reader + V, r := ProveGen(myGroup, DB, R, kA, []byte("Prover"), []byte("Verifier"), []byte(dst), rnd) - verify := Verify(myGroup, DB, R, V, r, []byte("Prover"), []byte("Verifier")) + verify := Verify(myGroup, DB, R, V, r, []byte("Prover"), []byte("Verifier"), []byte(dst)) if verify == true { t.Error("zkRDL verification should fail") } - } -func TestZKRDL(t *testing.T) { - - t.Run("zkRDL", func(t *testing.T) { - for i := 0; i < TestzkRDLCount; i++ { +func TestZKDL(t *testing.T) { + t.Run("zkDL", func(t *testing.T) { + for i := 0; i < testzkDLCount; i++ { currGroup := group.P256 - testzkRDL(t, currGroup) + testzkDL(t, currGroup) } }) - t.Run("zkRDLNegative", func(t *testing.T) { - for i := 0; i < TestzkRDLCount; i++ { + t.Run("zkDLNegative", func(t *testing.T) { + for i := 0; i < testzkDLCount; i++ { currGroup := group.P256 - testzkRDLNegative(t, currGroup) + testzkDLNegative(t, currGroup) } }) - }