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

add valueArraySize input to v3 circuits #80

Merged
merged 12 commits into from
Feb 29, 2024
6 changes: 3 additions & 3 deletions circuits.go
Original file line number Diff line number Diff line change
Expand Up @@ -22,7 +22,7 @@ const (
// AtomicQueryMTPV2CircuitID is a type for credentialAtomicQueryMTPV2.circom
AtomicQueryMTPV2CircuitID CircuitID = "credentialAtomicQueryMTPV2"
// AtomicQueryV3CircuitID is a type for credentialAtomicQueryV3.circom
AtomicQueryV3CircuitID CircuitID = "credentialAtomicQueryV3-beta.0"
AtomicQueryV3CircuitID CircuitID = "credentialAtomicQueryV3-beta.1"
// AtomicQueryMTPV2OnChainCircuitID is a type for credentialAtomicQueryMTPV2OnChain.circom
AtomicQueryMTPV2OnChainCircuitID CircuitID = "credentialAtomicQueryMTPV2OnChain"
// AtomicQuerySigCircuitID is a type for credentialAttrQuerySig.circom
Expand All @@ -32,15 +32,15 @@ const (
// AtomicQuerySigV2OnChainCircuitID is a type for credentialAttrQuerySigV2OnChain.circom
AtomicQuerySigV2OnChainCircuitID CircuitID = "credentialAtomicQuerySigV2OnChain"
// AtomicQueryV3OnChainCircuitID is a type for credentialAtomicQueryV3OnChain.circom
AtomicQueryV3OnChainCircuitID CircuitID = "credentialAtomicQueryV3OnChain-beta.0"
AtomicQueryV3OnChainCircuitID CircuitID = "credentialAtomicQueryV3OnChain-beta.1"
// JsonLDAtomicQueryMTPCircuitID is a type for credentialJsonLDAtomicQueryMTP.circom
JsonLDAtomicQueryMTPCircuitID CircuitID = "credentialJsonLDAtomicQueryMTP"
// SybilMTPCircuitID is a type for sybilMTP.circom
SybilMTPCircuitID CircuitID = "sybilCredentialAtomicMTP"
// SybilSigCircuitID is a type for sybilSig.circom
SybilSigCircuitID CircuitID = "sybilCredentialAtomicSig"
// LinkedMultiQuery10CircuitID is a type for linkedMultiQuery10.circom
LinkedMultiQuery10CircuitID CircuitID = "linkedMultiQuery10-beta.0"
LinkedMultiQuery10CircuitID CircuitID = "linkedMultiQuery10-beta.1"
)

// ErrorCircuitIDNotFound returns if CircuitID is not registered
Expand Down
46 changes: 25 additions & 21 deletions credentialAtomicQueryV3.go
Original file line number Diff line number Diff line change
Expand Up @@ -84,18 +84,18 @@ type atomicQueryV3CircuitInputs struct {
IsRevocationChecked int `json:"isRevocationChecked"`
// Query
// JSON path
ClaimPathNotExists int `json:"claimPathNotExists"` // 0 for inclusion, 1 for non-inclusion
ClaimPathMtp []string `json:"claimPathMtp"`
ClaimPathMtpNoAux string `json:"claimPathMtpNoAux"` // 1 if aux node is empty, 0 if non-empty or for inclusion proofs
ClaimPathMtpAuxHi *merkletree.Hash `json:"claimPathMtpAuxHi"` // 0 for inclusion proof
ClaimPathMtpAuxHv *merkletree.Hash `json:"claimPathMtpAuxHv"` // 0 for inclusion proof
ClaimPathKey string `json:"claimPathKey"` // hash of path in merklized json-ld document
ClaimPathValue string `json:"claimPathValue"` // value in this path in merklized json-ld document

Operator int `json:"operator"`
SlotIndex int `json:"slotIndex"`
Timestamp int64 `json:"timestamp"`
Value []string `json:"value"`
ClaimPathMtp []string `json:"claimPathMtp"`
ClaimPathMtpNoAux string `json:"claimPathMtpNoAux"` // 1 if aux node is empty, 0 if non-empty or for inclusion proofs
ClaimPathMtpAuxHi *merkletree.Hash `json:"claimPathMtpAuxHi"` // 0 for inclusion proof
ClaimPathMtpAuxHv *merkletree.Hash `json:"claimPathMtpAuxHv"` // 0 for inclusion proof
ClaimPathKey string `json:"claimPathKey"` // hash of path in merklized json-ld document
ClaimPathValue string `json:"claimPathValue"` // value in this path in merklized json-ld document

Operator int `json:"operator"`
SlotIndex int `json:"slotIndex"`
Timestamp int64 `json:"timestamp"`
Value []string `json:"value"`
ActualValueArraySize int `json:"valueArraySize"`

IssuerClaimMtp []*merkletree.Hash `json:"issuerClaimMtp"`
IssuerClaimClaimsTreeRoot *merkletree.Hash `json:"issuerClaimClaimsTreeRoot"`
Expand Down Expand Up @@ -127,6 +127,10 @@ func (a AtomicQueryV3Inputs) Validate() error {
return errors.New(ErrorEmptyQueryValue)
}

if err := a.Query.ValidateValueArraySize(a.GetValueArrSize()); err != nil {
return err
}

switch a.ProofType {
case BJJSignatureProofType:
if a.Claim.SignatureProof == nil {
Expand Down Expand Up @@ -265,7 +269,6 @@ func (a AtomicQueryV3Inputs) InputsMarshal() ([]byte, error) {
s.IssuerClaimNonRevMtpAuxHv = nodeAuxNonRev.value
s.IssuerClaimNonRevMtpNoAux = nodeAuxNonRev.noAux

s.ClaimPathNotExists = existenceToInt(valueProof.MTP.Existence)
nodAuxJSONLD := GetNodeAuxValue(valueProof.MTP)
s.ClaimPathMtpNoAux = nodAuxJSONLD.noAux
s.ClaimPathMtpAuxHi = nodAuxJSONLD.key
Expand All @@ -278,6 +281,7 @@ func (a AtomicQueryV3Inputs) InputsMarshal() ([]byte, error) {
return nil, err
}
s.Value = bigIntArrayToStringArray(values)
s.ActualValueArraySize = len(a.Query.Values)

s.LinkNonce = "0"
if a.LinkNonce != nil {
Expand Down Expand Up @@ -337,14 +341,14 @@ type AtomicQueryV3PubSignals struct {
Timestamp int64 `json:"timestamp"`
Merklized int `json:"merklized"`
ClaimPathKey *big.Int `json:"claimPathKey"`
ClaimPathNotExists int `json:"claimPathNotExists"` // 0 for inclusion, 1 for non-inclusion
IsRevocationChecked int `json:"isRevocationChecked"` // 0 revocation not check, // 1 for check revocation
ProofType int `json:"proofType"`
LinkID *big.Int `json:"linkID"`
Nullifier *big.Int `json:"nullifier"`
OperatorOutput *big.Int `json:"operatorOutput"`
VerifierID *core.ID `json:"verifierID"`
NullifierSessionID *big.Int `json:"nullifierSessionID"`
ActualValueArraySize int `json:"valueArraySize"`
}

// PubSignalsUnmarshal unmarshal credentialAtomicQueryV3.circom public signals
Expand All @@ -363,11 +367,11 @@ func (ao *AtomicQueryV3PubSignals) PubSignalsUnmarshal(data []byte) error {
// issuerClaimNonRevState
// timestamp
// claimSchema
// claimPathNotExists
// claimPathKey
// slotIndex
// operator
// value
// valueArraySize
// verifierID
// nullifierSessionID

Expand Down Expand Up @@ -469,12 +473,6 @@ func (ao *AtomicQueryV3PubSignals) PubSignalsUnmarshal(data []byte) error {
ao.ClaimSchema = core.NewSchemaHashFromInt(schemaInt)
fieldIdx++

// - ClaimPathNotExists
if ao.ClaimPathNotExists, err = strconv.Atoi(sVals[fieldIdx]); err != nil {
return err
}
fieldIdx++

// - ClaimPathKey
if ao.ClaimPathKey, ok = big.NewInt(0).SetString(sVals[fieldIdx], 10); !ok {
return fmt.Errorf("invalid claimPathKey: %s", sVals[fieldIdx])
Expand Down Expand Up @@ -504,6 +502,12 @@ func (ao *AtomicQueryV3PubSignals) PubSignalsUnmarshal(data []byte) error {
fieldIdx++
}

// - valueArraySize
if ao.ActualValueArraySize, err = strconv.Atoi(sVals[fieldIdx]); err != nil {
return err
}
fieldIdx++

// - VerifierID
if sVals[fieldIdx] != "0" {
if ao.VerifierID, err = idFromIntStr(sVals[fieldIdx]); err != nil {
Expand Down
82 changes: 26 additions & 56 deletions credentialAtomicQueryV3OnChain.go
Original file line number Diff line number Diff line change
Expand Up @@ -49,7 +49,7 @@ type AtomicQueryV3OnChainInputs struct {

NullifierSessionID *big.Int

AuthEnabled int
IsBJJAuthEnabled int
}

// atomicQueryV3OnChainCircuitInputs type represents credentialAtomicQueryV3OnChain.circom private inputs required by prover
Expand Down Expand Up @@ -90,18 +90,18 @@ type atomicQueryV3OnChainCircuitInputs struct {
IsRevocationChecked int `json:"isRevocationChecked"`
// Query
// JSON path
ClaimPathNotExists int `json:"claimPathNotExists"` // 0 for inclusion, 1 for non-inclusion
ClaimPathMtp []string `json:"claimPathMtp"`
ClaimPathMtpNoAux string `json:"claimPathMtpNoAux"` // 1 if aux node is empty, 0 if non-empty or for inclusion proofs
ClaimPathMtpAuxHi *merkletree.Hash `json:"claimPathMtpAuxHi"` // 0 for inclusion proof
ClaimPathMtpAuxHv *merkletree.Hash `json:"claimPathMtpAuxHv"` // 0 for inclusion proof
ClaimPathKey string `json:"claimPathKey"` // hash of path in merklized json-ld document
ClaimPathValue string `json:"claimPathValue"` // value in this path in merklized json-ld document

Operator int `json:"operator"`
SlotIndex int `json:"slotIndex"`
Timestamp int64 `json:"timestamp"`
Value []string `json:"value"`
ClaimPathMtp []string `json:"claimPathMtp"`
ClaimPathMtpNoAux string `json:"claimPathMtpNoAux"` // 1 if aux node is empty, 0 if non-empty or for inclusion proofs
ClaimPathMtpAuxHi *merkletree.Hash `json:"claimPathMtpAuxHi"` // 0 for inclusion proof
ClaimPathMtpAuxHv *merkletree.Hash `json:"claimPathMtpAuxHv"` // 0 for inclusion proof
ClaimPathKey string `json:"claimPathKey"` // hash of path in merklized json-ld document
ClaimPathValue string `json:"claimPathValue"` // value in this path in merklized json-ld document

Operator int `json:"operator"`
SlotIndex int `json:"slotIndex"`
Timestamp int64 `json:"timestamp"`
Value []string `json:"value"`
ValueArraySize int `json:"valueArraySize"`

IssuerClaimMtp []*merkletree.Hash `json:"issuerClaimMtp"`
IssuerClaimClaimsTreeRoot *merkletree.Hash `json:"issuerClaimClaimsTreeRoot"`
Expand Down Expand Up @@ -146,7 +146,7 @@ type atomicQueryV3OnChainCircuitInputs struct {

NullifierSessionID string `json:"nullifierSessionID"`

AuthEnabled string `json:"authEnabled"`
IsBJJAuthEnabled string `json:"isBJJAuthEnabled"`
}

func (a AtomicQueryV3OnChainInputs) Validate() error {
Expand All @@ -163,11 +163,15 @@ func (a AtomicQueryV3OnChainInputs) Validate() error {
return errors.New(ErrorEmptyQueryValue)
}

if err := a.Query.ValidateValueArraySize(a.GetValueArrSize()); err != nil {
return err
}

if a.Challenge == nil {
return errors.New(ErrorEmptyChallenge)
}

if a.AuthEnabled == 1 {
if a.IsBJJAuthEnabled == 1 {
if a.AuthClaimIncMtp == nil {
return errors.New(ErrorEmptyAuthClaimProof)
}
Expand Down Expand Up @@ -272,7 +276,7 @@ func (a AtomicQueryV3OnChainInputs) InputsMarshal() ([]byte, error) {

s.Challenge = a.Challenge.String()

if a.AuthEnabled == 1 {
if a.IsBJJAuthEnabled == 1 {
s.AuthClaim = a.AuthClaim

s.ClaimsTreeRoot = a.TreeState.ClaimsRoot
Expand Down Expand Up @@ -358,7 +362,6 @@ func (a AtomicQueryV3OnChainInputs) InputsMarshal() ([]byte, error) {
s.IssuerClaimNonRevMtpAuxHv = nodeAuxNonRev.value
s.IssuerClaimNonRevMtpNoAux = nodeAuxNonRev.noAux

s.ClaimPathNotExists = existenceToInt(valueProof.MTP.Existence)
nodAuxJSONLD := GetNodeAuxValue(valueProof.MTP)
s.ClaimPathMtpNoAux = nodAuxJSONLD.noAux
s.ClaimPathMtpAuxHi = nodAuxJSONLD.key
Expand All @@ -371,6 +374,7 @@ func (a AtomicQueryV3OnChainInputs) InputsMarshal() ([]byte, error) {
return nil, err
}
s.Value = bigIntArrayToStringArray(values)
s.ValueArraySize = len(a.Query.Values)

s.LinkNonce = "0"
if a.LinkNonce != nil {
Expand All @@ -387,7 +391,7 @@ func (a AtomicQueryV3OnChainInputs) InputsMarshal() ([]byte, error) {
s.NullifierSessionID = a.NullifierSessionID.String()
}

s.AuthEnabled = strconv.Itoa(a.AuthEnabled)
s.IsBJJAuthEnabled = strconv.Itoa(a.IsBJJAuthEnabled)

return json.Marshal(s)
}
Expand Down Expand Up @@ -454,24 +458,19 @@ type AtomicQueryV3OnChainPubSignals struct {
IssuerState *merkletree.Hash `json:"issuerState"`
IssuerClaimNonRevState *merkletree.Hash `json:"issuerClaimNonRevState"`
Timestamp int64 `json:"timestamp"`
Merklized int `json:"merklized"`
IsRevocationChecked int `json:"isRevocationChecked"` // 0 revocation not check, // 1 for check revocation
QueryHash *big.Int `json:"circuitQueryHash"`
Challenge *big.Int `json:"challenge"`
GlobalRoot *merkletree.Hash `json:"gistRoot"`
ProofType int `json:"proofType"`
LinkID *big.Int `json:"linkID"`
Nullifier *big.Int `json:"nullifier"`
OperatorOutput *big.Int `json:"operatorOutput"`
VerifierID *core.ID `json:"verifierID"`
NullifierSessionID *big.Int `json:"nullifierSessionID"`
AuthEnabled int `json:"authEnabled"`
IsBJJAuthEnabled int `json:"isBJJAuthEnabled"`
}

// PubSignalsUnmarshal unmarshal credentialAtomicQueryV3OnChain.circom public signals
func (ao *AtomicQueryV3OnChainPubSignals) PubSignalsUnmarshal(data []byte) error {
// expected order:
// merklized
// userID
// circuitQueryHash
// issuerState
Expand All @@ -483,12 +482,9 @@ func (ao *AtomicQueryV3OnChainPubSignals) PubSignalsUnmarshal(data []byte) error
// challenge
// gistRoot
// issuerID
// isRevocationChecked
// issuerClaimNonRevState
// timestamp
// verifierID
// nullifierSessionID
// authEnabled
// isBJJAuthEnabled

var sVals []string
err := json.Unmarshal(data, &sVals)
Expand All @@ -498,12 +494,6 @@ func (ao *AtomicQueryV3OnChainPubSignals) PubSignalsUnmarshal(data []byte) error

fieldIdx := 0

// -- merklized
if ao.Merklized, err = strconv.Atoi(sVals[fieldIdx]); err != nil {
return err
}
fieldIdx++

// - userID
if ao.UserID, err = idFromIntStr(sVals[fieldIdx]); err != nil {
return err
Expand Down Expand Up @@ -571,12 +561,6 @@ func (ao *AtomicQueryV3OnChainPubSignals) PubSignalsUnmarshal(data []byte) error
}
fieldIdx++

// - isRevocationChecked
if ao.IsRevocationChecked, err = strconv.Atoi(sVals[fieldIdx]); err != nil {
return err
}
fieldIdx++

// - issuerClaimNonRevState
if ao.IssuerClaimNonRevState, err = merkletree.NewHashFromString(sVals[fieldIdx]); err != nil {
return err
Expand All @@ -590,22 +574,8 @@ func (ao *AtomicQueryV3OnChainPubSignals) PubSignalsUnmarshal(data []byte) error
}
fieldIdx++

// - VerifierID
if sVals[fieldIdx] != "0" {
if ao.VerifierID, err = idFromIntStr(sVals[fieldIdx]); err != nil {
return err
}
}
fieldIdx++

// - NullifierSessionID
if ao.NullifierSessionID, ok = big.NewInt(0).SetString(sVals[fieldIdx], 10); !ok {
return fmt.Errorf("invalid verifier session ID: %s", sVals[fieldIdx])
}
fieldIdx++

// - AuthEnabled
if ao.AuthEnabled, err = strconv.Atoi(sVals[fieldIdx]); err != nil {
// - IsBJJAuthEnabled
if ao.IsBJJAuthEnabled, err = strconv.Atoi(sVals[fieldIdx]); err != nil {
return err
}

Expand Down
Loading
Loading