Skip to content

Commit 3d4d31c

Browse files
committed
update readme
1 parent 85dab89 commit 3d4d31c

File tree

1 file changed

+64
-10
lines changed
  • xrpl4j-core/src/main/java/org/xrpl/xrpl4j/crypto/mpt

1 file changed

+64
-10
lines changed

xrpl4j-core/src/main/java/org/xrpl/xrpl4j/crypto/mpt/README.md

Lines changed: 64 additions & 10 deletions
Original file line numberDiff line numberDiff line change
@@ -186,15 +186,40 @@ ElGamalPedersenLinkProof balanceLinkageProof = linkProofGen.generateProof(
186186
);
187187
```
188188

189-
**Step 7: Combine proofs**
189+
**Step 7: Generate Bulletproof Range Proof**
190+
191+
The bulletproof proves that both the send amount and remaining balance are non-negative (in range [0, 2^64)).
192+
193+
```java
194+
// Compute remaining balance: senderCurrentBalance - sendAmount
195+
UnsignedLong remainingBalance = UnsignedLong.valueOf(
196+
senderCurrentBalance.longValue() - sendAmount.longValue()
197+
);
198+
199+
// Compute blinding factor for remaining balance: rho_rem = rho_balance - rho_amount
200+
byte[] negAmountBlinding = Secp256k1Operations.scalarNegate(amountBlindingFactorForSend.toBytes());
201+
byte[] rhoRemBytes = Secp256k1Operations.scalarAdd(balanceBlindingFactorForSend.toBytes(), negAmountBlinding);
202+
BlindingFactor rhoRem = BlindingFactor.fromBytes(rhoRemBytes);
203+
204+
// Generate aggregated bulletproof for {amount, remainingBalance}
205+
BulletproofRangeProofGenerator bulletproofGen = new JavaBulletproofRangeProofGenerator();
206+
BulletproofRangeProof bulletproof = bulletproofGen.generateProof(
207+
Arrays.asList(sendAmount, remainingBalance), // List of values
208+
Arrays.asList(amountBlindingFactorForSend, rhoRem), // List of blinding factors
209+
sendContext
210+
);
211+
```
212+
213+
**Step 8: Combine all proofs**
190214

191215
```java
192-
String fullZkProofHex = ZKProofUtils.combineSendProofsHex(
193-
samePlaintextProof, amountLinkageProof, balanceLinkageProof
216+
// SamePlaintextMultiProof (359) + Amount Linkage (195) + Balance Linkage (195) + Bulletproof (754) = 1503 bytes
217+
String fullZkProofHex = ZKProofUtils.combineSendProofsWithBulletproofHex(
218+
samePlaintextProof, amountLinkageProof, balanceLinkageProof, bulletproof
194219
);
195220

196-
String amountCommitmentHex = amountCommitment.toReversedHex64();
197-
String balanceCommitmentHex = balanceCommitment.toReversedHex64();
221+
String amountCommitmentHex = amountCommitment.hexValue();
222+
String balanceCommitmentHex = balanceCommitment.hexValue();
198223
```
199224

200225
---
@@ -253,9 +278,36 @@ ElGamalPedersenLinkProof balanceLinkageProof = linkProofGen.generateProof(
253278
convertBackBalanceBlindingFactor,
254279
context
255280
);
281+
```
256282

257-
String zkProofHex = balanceLinkageProof.hexValue();
258-
String balanceCommitmentHex = balanceCommitment.toReversedHex64();
283+
**Step 5: Generate Bulletproof Range Proof**
284+
285+
The bulletproof proves the remaining balance after conversion is non-negative.
286+
287+
```java
288+
// Compute remaining balance: currentBalance - convertBackAmount
289+
UnsignedLong remainingBalance = UnsignedLong.valueOf(
290+
currentBalance.longValue() - convertBackAmount.longValue()
291+
);
292+
293+
// Generate bulletproof for remaining balance (single value)
294+
BulletproofRangeProofGenerator bulletproofGen = new JavaBulletproofRangeProofGenerator();
295+
BulletproofRangeProof bulletproof = bulletproofGen.generateProof(
296+
Collections.singletonList(remainingBalance),
297+
Collections.singletonList(convertBackBalanceBlindingFactor), // Same blinding factor as balance commitment
298+
context
299+
);
300+
```
301+
302+
**Step 6: Combine proofs**
303+
304+
```java
305+
// Pedersen linkage proof (195 bytes) + Bulletproof (688 bytes) = 883 bytes total
306+
String zkProofHex = ZKProofUtils.combineConvertBackProofsHex(
307+
balanceLinkageProof, bulletproof
308+
);
309+
310+
String balanceCommitmentHex = balanceCommitment.hexValue();
259311
```
260312

261313
---
@@ -288,17 +340,16 @@ ConfidentialMPTClawbackContext context = ConfidentialMPTClawbackContext.generate
288340
```java
289341
JavaEqualityPlaintextProofGenerator equalityProofGen = new JavaEqualityPlaintextProofGenerator();
290342

343+
// The nonce is generated internally by the proof generator
291344
BlindingFactor issuerPrivateKeyAsBlindingFactor = BlindingFactor.fromBytes(
292345
issuerElGamalKeyPair.privateKey().naturalBytes().toByteArray()
293346
);
294-
BlindingFactor clawbackNonce = BlindingFactor.generate();
295347

296348
EqualityPlaintextProof clawbackProof = equalityProofGen.generateProof(
297349
issuerBalanceCiphertext, // ElGamalCiphertext - from MPToken.issuerEncryptedBalance
298350
issuerElGamalKeyPair.publicKey(), // ElGamalPublicKey
299351
clawbackAmount, // UnsignedLong
300352
issuerPrivateKeyAsBlindingFactor, // BlindingFactor - issuer's PRIVATE KEY
301-
clawbackNonce, // BlindingFactor
302353
context // ConfidentialMPTClawbackContext
303354
);
304355

@@ -315,7 +366,10 @@ JavaElGamalBalanceDecryptor decryptor = new JavaElGamalBalanceDecryptor();
315366
ElGamalCiphertext ciphertext = ElGamalCiphertext.fromBytes(
316367
BaseEncoding.base16().decode(encryptedHex)
317368
);
318-
long decryptedAmount = decryptor.decrypt(ciphertext, privateKey);
369+
370+
// Decrypt with search range [minAmount, maxAmount]
371+
// The decryptor uses baby-step giant-step algorithm to find the plaintext
372+
long decryptedAmount = decryptor.decrypt(ciphertext, privateKey, 0, 1_000_000);
319373
```
320374

321375
---

0 commit comments

Comments
 (0)