func NewEquivalenceProof(
	zkpcp ZKPCurveParams, Base1, Result1, Base2, Result2 ECPoint, x *big.Int) (*EquivalenceProof, error) {
	modValue := new(big.Int).Mod(x, zkpcp.C.Params().N)
	check1 := zkpcp.Mult(Base1, modValue)
	if !check1.Equal(Result1) {
		return nil, &errorProof{"EquivalenceProve", "Base1 and Result1 are not related by x"}
	}
	check2 := zkpcp.Mult(Base2, modValue)
	if !check2.Equal(Result2) {
		return nil, &errorProof{"EquivalenceProve", "Base2 and Result2 are not related by x"}
	}
	u, err := rand.Int(rand.Reader, zkpcp.C.Params().N)  
	if err != nil {
		return nil, err
	}
	uBase1 := zkpcp.Mult(Base1, u)
	uBase2 := zkpcp.Mult(Base2, u)
	Challenge := GenerateChallenge(zkpcp, Base1.Bytes(), Result1.Bytes(),
		Base2.Bytes(), Result2.Bytes(),
		uBase1.Bytes(), uBase2.Bytes())
	HiddenValue := new(big.Int).Add(u, new(big.Int).Mul(Challenge, modValue))
	HiddenValue = HiddenValue.Mod(HiddenValue, zkpcp.C.Params().N)
	return &EquivalenceProof{
		uBase1,  
		uBase2,  
		Challenge,
		HiddenValue}, nil
}
NewEquivalenceProof generates an equivalence proof that Result1 is the scalar multiple of base Base1,
and Result2 is the scalar multiple of base Base2 and that both results are using the same x as discrete log.
package zksigma
import (
	"bytes"
	"crypto/rand"
	"fmt"
	"math/big"
)
type EquivalenceProof struct {
	UG          ECPoint   
	UH          ECPoint   
	Challenge   *big.Int  
	HiddenValue *big.Int  
}