The MIRACL of IBE Signatures

As I look back over the year, I think my main “finds” have been the Go language and the MIRACL pairing library. Using these things, I have…

Photo by Helloquence on Unsplash

The MIRACL of IBE Signatures

As I look back over the year, I think my main “finds” have been the Go programming language and the MIRACL pairing library. Using these things, I have been able to bring alive abstract concepts and prove them. So, let’s take an example of illustrating the power of Go and MIRACL using a signing process in IBE (Identity Based Encryption).

With IBE rather than using a public key for Bob, we use something about Bob ID to create the public key. Bob then has a secret that he can use to generate the private key associated with this public key. In this article, we will use something simple, such as Bob’s email address. In this way, anyone who knows Bob’s ID will be able to encrypt something for him, but only he will be able to decrypt it. But what happens when Bob wants to sign for a message with IBE? Well, we will investigate in this article.

Signatures with IBE

First we have two curves (G1 and G2) and initially, we define a large prime number (q). Bob first selects a point on the G2 curve (P). First, a trust server selects a point on the G2 curve (P), and generates Bob secret key using a random number (s):

sk=s

Next the trust server creates Bob public key with:

Ppub=sP

This will be a point on the G2 curve.

Bob next takes the message (msg) and creates a hash of it:

h=H(msg)

And takes his ID and also hashes it:

ID=H(BobID)

He then creates this as a point on the G1 curve:

QID=Hp(ID)

This then creates with digital identity (DID) using his private key (s):

DID=sQID

And he then creates a random value for the message with r. Now he creates two elements for the signature:

U=rQID

V=(r+h)DID

The signature is then:

σ=(U,V)

To verify the signature, Alice performs the pairing of:

e(P,V)=e(Ppub,U+hQID)

This works because of the magic of crypto pairing:

Coding

The outline coding using the library from the MIRACL library is [code]:

package main
import (
	"fmt"
"github.com/miracl/core/go/core"
"github.com/miracl/core/go/core/BN254"
"math/rand"
"time"
"os"
)
func FP12toByte(F *BN254.FP12) []byte {
	const MFS int = int(BN254.MODBYTES)
var t [12 * MFS]byte
	F.ToBytes(t[:])
return(t[:])
}
func randval() *core.RAND {
    s1 := rand.NewSource(time.Now().UnixNano())
r1 := rand.New(s1)
    rng := core.NewRAND()
var raw [100]byte
for i := 0; i < 100; i++ {
raw[i] = byte(r1.Intn(255))
}
rng.Seed(100, raw[:])
return rng
}
func main() {
BobID:="athome"
msg:="Hello"
	argCount := len(os.Args[1:])
        if (argCount>0) {BobID= (os.Args[1])}
if (argCount>1) {msg= os.Args[2]}
    	q := BN254.NewBIGints(BN254.CURVE_Order)
	s:=BN254.Randomnum(q,randval())
r:=BN254.Randomnum(q,randval())

	sh:=core.NewHASH256()
for i:=0;i < len(msg);i++ {
sh.Process(msg[i])
}
	h:=BN254.FromBytes(sh.Hash())
	sh=core.NewHASH256()
for i:=0;i < len(BobID);i++ {
sh.Process(BobID[i])
}
	ID:=BN254.FromBytes(sh.Hash())
 
P := BN254.ECP2_generator()
	Ppub:=BN254.G2mul(P,s) 
	QID := BN254.ECP_hashit(ID)
	DID:=BN254.G1mul(QID,s)
	U := BN254.G1mul(QID,r)

	e := BN254.Modadd(r,h,q)
	V := BN254.G1mul(DID,e)
	hQID := BN254.G1mul(QID,h)
U.Add(hQID)
	LHS:=BN254.Ate(P,V);  LHS=BN254.Fexp(LHS)
	RHS:=BN254.Ate(Ppub,U); RHS=BN254.Fexp(RHS)


        fmt.Printf("\nMessage: %s\nBob's ID: %s\n\n",msg,BobID)
fmt.Printf("\nSecret: %s\nRandom: %s\n",s.ToString(),r.ToString())
fmt.Printf("\nDID: %s\nQID: %s\n",DID.ToString(),QID.ToString())
fmt.Printf("\nU: %s\nV: %s\n",U.ToString(),V.ToString())
fmt.Printf("\n\nPair - first 20 bytes:\t0x%x\n",FP12toByte(RHS)[:20])
if LHS.Equals(RHS) { fmt.Printf("\nSignatures match\n")}

}

A sample run is [here]:

Message: testing
Bob's ID: bob@home

Secret: 1d2524b1d305e68deb2e7bcbb8b5b9911a1aba30959efd4dec935dcb2d2d5b51
Random: 054a1d09881052799a0adcd78499dcadb67ce73f5668801d7a525d244bb30690
DID: (1c8b34a326122882ab0e854d9417860cb1df8a8ca77523a18e81d218f88beace,0a6382478dfedf44c58c219798536c8907e3be2ffdd8e17386c1c26a25128cf1)
QID: (24fe782588f174682f5eea7c6f9656dfa7a138814694a5594d38ea50aec70ed4,10da986194a99f6ed947e0831257ae2d52e957d2b5f7bf9205573a44d2062e68)
U: (0a6b76117cf991ac29f8ee3a7afa91e6ee6fa13766a1d699bf82b3ca125890b7,007da4bacf31f78a573a722193a26af9a98a42c86ebd177a9e7eaf94aa4ec4be)
V: (119b8b285f5b4d4c06377df70ba9117d957c6ad6dda4078df9aa0a711388110f,1484fc86afceedb2186ea8f6b66ba9b88186513b63dc48b87f1405419be3f5e5)

Pair - first 20 bytes:	0x2184d39a95ec0e07587bed1ae4a85c317a7b1cbc
Signatures match

Conclusions

Our current digital world is flawed, and little can really be trusted. We need to increasingly move into a world with proper digital signatures. With Go and MIRACL, things come alive!