Zero knowledge proof मून मैथ
Zero knowledge proofs यह प्रदर्शित करते हैं कि आपने कंप्यूटेशन (computation) के इनपुट्स को उजागर किए बिना किसी कंप्यूटेशन को सही ढंग से निष्पादित (execute) किया है। एक zero knowledge प्रोग्रामिंग भाषा उस कंप्यूटेशन को दर्शाने का एक सुविधाजनक तरीका है।
Zero knowledge proofs के लिए एक सामान्य, लेकिन भ्रामक उदाहरण (analogy) यह है कि “मैं अपना ID कार्ड दिखाए बिना यह साबित कर सकता हूं कि मैं 21 वर्ष से अधिक का हूं।” इस तरह से तैयार किए जाने पर, आप zero knowledge proof नहीं बना सकते।
Zero knowledge proofs ज्ञान (knowledge) साबित नहीं करते हैं। वे कंप्यूटेशन के इनपुट्स को उजागर किए बिना एक सार्वजनिक एल्गोरिथम के सार्वजनिक आउटपुट (public output of a public algorithm) के लिए सही कंप्यूटेशन (correct computation) साबित करते हैं।
इसलिए zero knowledge ID कार्ड उस तरह से काम नहीं करते हैं। आइए एक वास्तविक उदाहरण लें। एक ज्ञात संख्या, मान लीजिए 1,093,073 को लेना और एक proof बनाना संभव है कि आपने उन दो नंबरों को (इस मामले में 1103, 991) उजागर किए बिना इसे प्राप्त करने के लिए दो नंबरों को गुणा किया था।
इसके zero knowledge proof में तीन घटक (components) होंगे:
- दो संख्याएँ (जिन्हें हम fields कहते हैं), इस मामले में, एन्क्रिप्टेड वर्ज़न 1103 और 991
- एक लंबी बाइट स्ट्रिंग (proof)
- गुणन (multiplication) एल्गोरिथम का एक प्रोग्रामेटिक विवरण
इनपुट्स को “एन्क्रिप्टेड” कहना थोड़ा भ्रामक है क्योंकि उन्हें डिक्रिप्ट करने का कोई प्राकृतिक तरीका नहीं है, लेकिन इस बारे में सोचने का यह एक उचित तरीका है। आप इनपुट्स के साथ गणितीय रूप से समझदार चीजें कर सकते हैं, लेकिन आप यह निर्धारित नहीं कर सकते कि उनके मूल मूल्य (original values) क्या थे)।
आप zero knowledge proofs को डिजिटल सिग्नेचर के अत्यधिक सामान्यीकृत (generalized) संस्करण के रूप में सोच सकते हैं।
डिजिटल सिग्नेचर के साथ, आप प्राइवेट की (private key) को साझा किए बिना प्राइवेट की के ज्ञान को साबित कर रहे होते हैं। आप पहले एक संदेश और एक पब्लिक की (public key) उपलब्ध कराकर इस ज्ञान को साबित करते हैं। फिर आप एक सिग्नेचर दिखाते हैं जो संदेश और पब्लिक की के अनुरूप (consistent) हो।
Zero knowledge proofs के लिए यह उदाहरण कुछ इस तरह काम करता है:
(पब्लिक आउटपुट, एन्क्रिप्टेड इनपुट, zero knowledge proof) —> डिजिटल सिग्नेचर
(एल्गोरिथम) —> पब्लिक की।
आप एक proof (बाइट स्ट्रिंग) तैयार करते हैं जो आउटपुट और एल्गोरिथम के अनुरूप होता है। वेरिफ़ायर वास्तव में कंप्यूटेशन को निष्पादित नहीं कर सकता है, लेकिन वे यह सत्यापित (verify) कर सकते हैं कि:
- एल्गोरिथम
- आउटपुट
- एन्क्रिप्टेड इनपुट्स, और
- proof स्ट्रिंग
ये सभी एक-दूसरे के अनुरूप हैं।
डिजिटल सिग्नेचर में, पब्लिक एड्रेस पहले से ज्ञात होता है। Zero knowledge एप्लिकेशन्स में, जो एल्गोरिथम आप निष्पादित कर रहे हैं वह पहले से ज्ञात होता है। आप जिस संदेश पर हस्ताक्षर कर रहे हैं उसके आधार पर डिजिटल सिग्नेचर बदल जाते हैं। इसी तरह, zero knowledge proofs में, आपकी proof स्ट्रिंग उन इनपुट्स और आउटपुट्स के साथ बदल जाएगी जिन्हें आप साबित कर रहे हैं।
सामान्य रूप में, एक zero knowledge कंप्यूटेशन इस तरह दिखता है:
prove(inputs, algorithm_description) -> (encrypted_inputs, proof, public_output)
verify(encrypted_inputs, proof, algorithm_description) == public_output
एक अधिक दिलचस्प उदाहरण zcash जैसी क्रिप्टोकरेंसी में पैसे का लेन-देन है। पैसे को स्थानांतरित करने वाला प्रत्येक ट्रांज़ैक्शन एक स्टेट ट्रांज़िशन (state transition) है, जो अपने आप में एक कंप्यूटेशन है। पब्लिक आउटपुट कुल सप्लाई है (जो मॉड्यूलो माइनर रिवार्ड्स को छोड़कर नहीं बदलती है)। एन्क्रिप्टेड इनपुट एड्रेस के बीच का बैलेंस ट्रांसफर है।
चूँकि zero knowledge proofs केवल कंप्यूटेशन्स हैं, वे बहुत स्वाभाविक रूप से प्रोग्रामिंग भाषाओं के साथ वर्णित किए जाने के अनुकूल हैं। पहले बताए गए गुणन एल्गोरिथम का प्रोग्रामेटिक विवरण याद है? उसे आसानी से एक पारंपरिक प्रोग्रामिंग भाषा में दर्शाया जा सकता है जो इसे पर्दे के पीछे “मून मैथ (moon math)” में कंपाइल करेगा।
बिना किसी और देरी के, यहाँ zero knowledge प्रोग्रामिंग भाषाओं की सूची दी गई है।
Circom, iden3 द्वारा निर्मित
यदि आप इलेक्ट्रिकल इंजीनियरिंग बैकग्राउंड से हैं, तो खुश हो जाइए। Zero knowledge में कंप्यूटेशन को दर्शाने का मुख्य तरीका बुलियन सर्किट (boolean circuits) है। बुलियन सर्किट वास्तव में विशाल गणितीय समीकरण होते हैं, इसलिए वे आसानी से उन मून मैथ समीकरणों में बदल जाते हैं जो पर्दे के पीछे होते हैं।
आप सोच रहे होंगे कि यदि zero knowledge को सर्किट के साथ दर्शाया जाता है, तो हैश एल्गोरिथम या फॉर लूप (for loop) जैसी चीज़ को कैसे निष्पादित किया जा सकता है? इसके लिए कई चरणों की आवश्यकता होती है, जबकि एक सर्किट चीज़ों को एक बार में कंप्यूट करता है।
यह प्रत्येक चरण को एक अलग सर्किट के रूप में मानकर और प्रत्येक चरण के लिए proofs की एक सूची रखकर पूरा किया जाता है। यह हमारे लिए सौभाग्य की बात है, क्योंकि अधिकांश कंप्यूटेशन्स को सर्किट के संदर्भ में वर्णित करना बहुत चुनौतीपूर्ण है।
शुक्र है, हमें खुद ALU (arithmetic logic units) को लागू करने के बजाय, Circom इसके ऊपर एब्स्ट्रैक्शन (abstraction) की एक लेयर प्रदान करता है। यहाँ दो संख्याओं को एक साथ जोड़ने का कोड दिया गया है:
pragma circom 2.0.0;
template Add(){
//Declaration of signals
signal input in1;
signal input in2;
signal output out;
out <== in1 + in2;
}
component main {public [in1,in2]} = Add();
ये टेम्पलेट्स आपको बिल्डिंग ब्लॉक्स को एक साथ असेंबल करके बहुत अधिक जटिल संचालन (operations) करने की अनुमति देते हैं, जैसे कि बाइट स्ट्रिंग्स को एक साथ जोड़ना (concatenate), एलिप्टिक कर्व अर्थमेटिक (elliptic curve arithmetic), या हैश फ़ंक्शन्स।
Zokrates
यदि दो संख्याओं को एक साथ जोड़ने के लिए छह पंक्तियों का कोड आपको पसंद नहीं आता है, तो शुक्र है कि इसके लिए हायर लेवल एब्स्ट्रैक्शन्स मौजूद हैं। यहाँ बताया गया है कि Zokrates इसे कैसे करता है:
def main(field x, field y) -> field {
field z = x + y;
return z;
}
Zero knowledge प्रोग्रामिंग भाषाएँ संख्याओं को fields के रूप में क्यों संदर्भित करती हैं? Zero knowledge proofs में गणित हमेशा एक बड़ी अभाज्य संख्या (prime number) के मॉड्यूलो पर किया जाता है (जैसा कि अधिकांश क्रिप्टोग्राफ़िक एल्गोरिथम में होता है)। यहाँ “field” शब्द “finite field” का संक्षिप्त रूप है क्योंकि संख्या के संभावित मानों की संख्या सीमित (finite) है। विशेष रूप से, यह उस अभाज्य संख्या का आकार है जिस पर आप मॉड्यूलो अर्थमेटिक कर रहे हैं।
जाहिर है, उन संख्याओं को उजागर किए बिना यह साबित करना कि आप दो संख्याओं का योग जानते हैं, बहुत दिलचस्प नहीं है। शुरुआत के उदाहरण का उपयोग करते हुए यहाँ एक बेहतर एप्लिकेशन (application) दिया गया है।
Zokrates में Zero knowledge ID कार्ड

zero knowledge proof id कार्ड एल्गोरिथम
कुछ संशोधनों के साथ, हम अपने zero knowledge ID कार्ड को काम करने लायक बना सकते हैं।
शुरुआत करने के लिए, किसी अथॉरिटी द्वारा यह सत्यापित किए बिना उम्र का प्रदर्शन करना संभव नहीं है कि आपका जन्म किसी निश्चित तिथि पर हुआ था। लेकिन यहाँ एक तरीका है जिससे आप किसी तथ्य के ज्ञान को कंप्यूटेशन के proof में बदल सकते हैं।
सरकार आपका जन्मदिन, आपकी नागरिकता ID संख्या (citizen id) और एक रैंडम सॉल्ट (random salt) लेती है। वे इन स्ट्रिंग्स को एक साथ जोड़ते हैं, उन्हें हैश करते हैं, और हैश डाइजेस्ट पर डिजिटल रूप से हस्ताक्षर करते हैं। जब आप किसी संस्थान में कुछ ऑर्डर करने जाते हैं जिसके लिए यह साबित करने की आवश्यकता होती है कि आप 21 वर्ष से अधिक के हैं, तो आप अपना एन्क्रिप्टेड जन्मदिन, अपनी एन्क्रिप्टेड नागरिकता ID, अपना एन्क्रिप्टेड रैंडम सॉल्ट, सरकार द्वारा हस्ताक्षरित हैश और बाइट स्ट्रिंग proof प्रदान करेंगे।
लक्ष्य यह साबित करना है कि आप हस्ताक्षरित हैश उत्पन्न करने के लिए एल्गोरिथम को सही ढंग से निष्पादित कर सकते हैं।
आम तौर पर, आप एन्क्रिप्टेड मानों को एक साथ जोड़कर हस्ताक्षरित हैश प्राप्त नहीं कर सकते हैं, लेकिन यहीं पर zero knowledge प्रोग्रामिंग काम आती है। आप वास्तव में एन्क्रिप्टेड इनपुट्स को हैश नहीं कर रहे हैं, आप यह साबित कर रहे हैं कि आपने इनपुट्स को उजागर किए बिना कंप्यूटेशन को सही ढंग से किया है।
Zokrates में, यह आश्चर्यजनक रूप से एर्गोनोमिक (ergonomic) दिखता है:
import "hashes/sha256/512bitPacked" as sha256packed;
def main(private field birthday,
private field citizenId,
private field salt,
public requiredBirthday,
public field hashFirst128bits,
public field hashSecond128bits) {
field[2] hash = sha256packed([birthday, citizenId, salt]);
assert(hash[0] == hashFirst128bits);
assert(hash[1] == hashSecond128bits);
assert(birthday < requiredBirthday);
return;
}
// the signature for the hash would be validated in a traditional way
यह इतना डरावना नहीं लगता, है ना!? हम यह सुनिश्चित कर रहे हैं कि गुप्त मान (secret values) अपेक्षित हैश के समान हों और यह सुनिश्चित कर रहे हैं कि जन्मदिन के अनुरूप इनपुट थ्रेशोल्ड (threshold) को पार करता हो।
एक बात जो तुरंत ध्यान खींचती है: यदि जन्मदिन एन्क्रिप्टेड है तो यह पंक्ति
assert(birthday < requiredBirthday)
कैसे निष्पादित (execute) की जा सकती है?
कोड को गणित में कंपाइल किया जाता है जहाँ यह वास्तव में सार्थक होता है — इसे उस तरह से “निष्पादित (executed)” नहीं किया जाता है जैसा हम सामान्य रूप से सोचते हैं। इसी तरह, हैश सर्किट वास्तव में इनपुट्स को हैश नहीं कर रहा है। यह केवल यह सत्यापित कर रहा है कि एन्क्रिप्टेड इनपुट्स अंतर्निहित (underlying) सर्किट और साथ वाले proof के फ़ंक्शन के रूप में सार्वजनिक हैश आउटपुट के अनुरूप हैं।
Zokrates का मूल व्हाइटपेपर, IEEE 2018 में प्रकाशित (http://www.ise.tu-berlin.de/fileadmin/fg308/publications/2018/2018_eberhardt_ZoKrates.pdf)
Leo
Aleo blockchain एक प्राइवेसी (privacy) केंद्रित स्मार्ट कॉन्ट्रैक्ट चेन है, जिसमें Leo इसकी प्राथमिक प्रोग्रामिंग भाषा है। आप उनके online playground में देख सकते हैं कि यह भाषा कैसी है।
यह लिखते समय, केवल टेस्टनेट (testnet) लॉन्च किया गया है।
यहाँ दो संख्याओं को एक साथ जोड़ने वाली भाषा का उदाहरण है।
program helloworld.aleo {
transition main(public a: u32, b: u32) -> u32 {
let c: u32 = a + b;
return c;
}
}
Leo व्हाइटपेपर / अकादमिक पेपर: https://eprint.iacr.org/2021/651.pdf
Layer Two एप्लिकेशन्स
यद्यपि zero knowledge proofs प्राइवेसी के लिए प्रसिद्ध हैं, फिर भी ब्लॉकचेन स्केलेबिलिटी (scalability) के लिए इनका एक शक्तिशाली उपयोग (use case) है। याद रखें, वेरिफ़ायर वास्तव में एन्क्रिप्टेड इनपुट्स को एक साथ हैश या जोड़ नहीं सकता है और समझदार परिणाम प्राप्त नहीं कर सकता है। वे केवल यह मान्य (validate) करते हैं कि इनपुट, आउटपुट, सर्किट और proofs सुसंगत (consistent) हैं।
दिलचस्प बात यह है कि निरंतरता (consistency) साबित करना वास्तविक कंप्यूटेशन को निष्पादित करने की तुलना में कम्प्यूटेशनल रूप से आसान है। इसका मतलब यह है कि ट्रांज़ैक्शन को असेंबल करने वाले ब्लॉक प्रोड्यूसर (block producer) पर कम्प्यूटेशनल बोझ काफी होता है क्योंकि उन्हें कंप्यूटेशन करना होता है और proofs तैयार करने होते हैं, लेकिन प्रस्तावित ब्लॉक को मान्य करने वाले अन्य वैलिडेटर्स (validators) को बहुत कम काम करना पड़ता है क्योंकि उन्हें केवल proof को मान्य करना होता है, जो एसिम्प्टोटिकली (asymptotically) आसान है।
सर्वसम्मति (Consensus) तब नहीं होती जब ब्लॉक का उत्पादन होता है, यह तब होती है जब नेटवर्क के दो तिहाई से अधिक लोग सहमत होते हैं कि ब्लॉक वैध है। उन्हें जितना अधिक भारी कंप्यूटेशन करना होगा, सर्वसम्मति में उतना ही अधिक समय लगेगा, और इससे थ्रूपुट (throughput) की बाधाएं उत्पन्न होती हैं।
क्योंकि यह यूज़ केस तेज़ वेरिफ़िकेशन के लिए ऑप्टिमाइज़ करता है, आपको यह नहीं मान लेना चाहिए कि ऑपरेशन्स डिफ़ॉल्ट रूप से प्राइवेट होते हैं। निम्नलिखित भाषाओं के इम्प्लीमेंटेशन्स (implementations) जरूरी नहीं कि प्राइवेसी बनाए रखने के लिए ऑप्टिमाइज़ करें जब तक कि वे स्पष्ट रूप से ऐसा न कहें।
Aztec द्वारा Noir
Noir Aztec के लिए भाषा है, जो Ethereum के लिए एक प्राइवेसी केंद्रित L2 है। इसका सिंटैक्स (syntax) काफी हद तक Rust से प्रेरित है; यहाँ तक कि इसके बिल्ड टूल (build tool) को “nargo” कहा जाता है, जो स्पष्ट रूप से Rust के cargo से प्रेरित है।
यहाँ Noir द्वारा दो संख्याओं को एक साथ जोड़ने का उदाहरण है:
fn foo(x : Field, y : Field) -> Field {
x + y
}
Rust में, और Noir में, जिन स्टेटमेंट्स में सेमीकोलन (semicolon) नहीं होता है, उन्हें फ़ंक्शन रिटर्न के रूप में माना जाता है, अगर आप सोच रहे थे कि रिटर्न स्टेटमेंट कहाँ गायब हो गया।
Starkware द्वारा Cairo
Starknet एक और L2 है।
यह नाम CPU Algebraic Intermediate Representation का मिश्रित रूप (portmanteau) है। इंटरमीडिएट रिप्रेजेंटेशन भाषाओं का उद्देश्य केवल “असेंबली से थोड़ा ऊपर (barely above the assembly)” होना है, लेकिन zero knowledge proofs में, “असेंबली” zero knowledge साबित करने वाले बीजगणित (algebra) के सूत्र होते हैं।
C, या C++ डेवलपर्स (या असेंबली के साथ सहज महसूस करने वाले Solidity डेवलपर्स) इस भाषा के साथ काफी सहज महसूस करेंगे क्योंकि यह काफी लो-लेवल (low level) की है। यहाँ Cairo का playground दिया गया है।
परंपरा को बनाए रखते हुए, Cairo संख्याओं को “fields” के रूप में संदर्भित करता है लेकिन उन्हें “field elements” कहता है और सिंटैक्स में यह संक्षिप्त होकर “felt” (field + element) बन जाता है।
यहाँ Cairo द्वारा दो संख्याओं को जोड़ने का उदाहरण है:
%builtins output
// Import the serialize_word() function.
from starkware.cairo.common.serialize import serialize_word
func main{output_ptr: felt*}() {
tempvar x = 12;
tempvar y = 14;
tempvar z = x + y;
serialize_word(z);
return ();
}
Cairo व्हाइटपेपर: https://eprint.iacr.org/2021/1063.pdf
Solidity
आपने यहाँ इसे देखने की उम्मीद नहीं की थी, है ना?!
आपने Polygon और Matter Labs द्वारा बनाए जा रहे “zk evms” के बारे में काफी चर्चा सुनी होगी। चर्चा यह है कि आप वैनिला (vanilla) solidity को नियमित EVM बाइटकोड (bytecode) में कंपाइल कर सकते हैं और एक zero knowledge proof भी तैयार कर सकते हैं कि आपने बाइटकोड को सही ढंग से निष्पादित किया है। इसके लिए निश्चित रूप से एक विशेष वर्चुअल मशीन (virtual machine) की आवश्यकता होती है, जिसे कंपनियाँ अक्सर “zk evm” के किसी प्रकार के रूप में ब्रांड करती हैं।
आप EVM की स्टेट को दो एरे (arrays): स्टैक और मेमोरी द्वारा दर्शाए गए के रूप में सोच सकते हैं। प्रत्येक ऑपरेशन स्टैक और/या मेमोरी को बदलता है। प्रत्येक चरण इस बात का proof है कि जिस तरह से आपने स्टेट को बदला है वह आपके द्वारा अभी निष्पादित किए गए ऑपकोड (opcode) और पिछली स्टेट के अनुरूप है।
इस इनोवेशन के कारण Solidity के लंबे समय तक प्रासंगिक बने रहने की संभावना है, इसलिए हमारे Solidity bootcamp! को देखें। यह हमारे zero knowledge bootcamp के लिए एक शर्त (prerequisite) है।
मुझे किसका उपयोग करना चाहिए, और आगे के संसाधन (resources)
यदि आप Aleo, Starknet, या Aztec पर विकास (develop) करने की योजना बना रहे हैं, तो आपको उनकी संबंधित भाषाओं का उपयोग करना होगा। लेकिन अगर आप Ethereum पर एक प्राइवेसी केंद्रित स्मार्ट कॉन्ट्रैक्ट विकसित करने का प्रयास कर रहे हैं, तो आपको या तो Circom या Zokrates का उपयोग करना होगा। वर्तमान में Noir के पास solidity में कंपाइल करने के लिए भी सीमित समर्थन उपलब्ध है।
यद्यपि Circom की तुलना में अधिक आसान (friendlier) भाषा का सीधे उपयोग करना आकर्षक लग सकता है, लेकिन यह समझना आवश्यक है कि सर्किट प्रोग्रामिंग कैसे कार्य करती है। आखिरकार, यहाँ की भाषाएँ अंततः इसके समान ही किसी चीज़ में कंपाइल होती हैं। आप इस सूची में Circom के बाद वाली भाषाओं में अजीब बाधाओं को देखेंगे जिनका तब तक कोई मतलब नहीं होगा जब तक आपको यह अंदाजा न हो कि पर्दे के पीछे क्या हो रहा है। उदाहरण के लिए, Zokrates में “if” स्टेटमेंट्स की सभी ब्रांच निष्पादित (execute) होती हैं, और Cairo में मेमोरी को ओवरराइट (overwrite) नहीं किया जा सकता है।
Zero knowledge proofs के पीछे के गणित का कोई आसान परिचय जैसी कोई चीज़ नहीं है, लेकिन this paper किसी ऐसे व्यक्ति को समझ में आना चाहिए जिसने प्रीकैलकुलस (precalculus) या कोई बेसिक क्रिप्टोग्राफ़ी कोर्स किया हो।
Zero Knowledge Puzzles की प्रैक्टिस करें
यदि आप Circom का एक आसान परिचय चाहते हैं, तो उनके दस्तावेज़ पढ़ें और हमारे ओपन सोर्स Zero Knowledge Puzzles को हल करने का प्रयास करें।
मूल रूप से 22 दिसंबर, 2022 को प्रकाशित