在比特幣中飞苇,經(jīng)常出現(xiàn)三個詞:私鑰,公鑰和地址
蜗顽。他們是什么意思呢布卡?他們之間又有什么樣的關(guān)系呢?搞清楚他們之間的關(guān)系和區(qū)別雇盖,是了解比特幣的基礎(chǔ)忿等。
私鑰
先說說私鑰,一般我們看到的私鑰是下面這樣的一段字符串:
5KYZdUEo39z3FPrtuX2QbbwGnNP5zTd7yyr2SC1j299sBCnWjss
支持比特幣協(xié)議的應(yīng)用都可以正確把這段字符串轉(zhuǎn)換成比特幣的私鑰崔挖,再轉(zhuǎn)換出公鑰贸街,再得到一個地址,如果該地址上面有對應(yīng)的比特幣狸相,就可以使用這個私鑰花費上面的比特幣薛匪。
-
私鑰本質(zhì)上是隨機數(shù)
私鑰本質(zhì)上是一個隨機數(shù),由32個byte組成的數(shù)組脓鹃,1個byte等于8位二進制逸尖,一個二進制只有兩個值0或者1。所以私鑰的總數(shù)是將近2(8*32)=2256個,但是有一些私鑰并不能使用娇跟,他真實的大小是介于:
1 ~ 0xFFFF FFFF FFFF FFFF FFFF FFFF FFFF FFFE BAAE DCE6 AF48 A03B BFD2 5E8C D036 4141
之間的數(shù)岩齿。這個數(shù)量已經(jīng)超過了宇宙中原子的總數(shù),想要遍歷所有的私鑰苞俘,耗盡整個太陽的能量也是不可能的纯衍。
我們所說的比特幣私鑰的是密碼學(xué)上面安全的,并不是說不可能出現(xiàn)重復(fù)的私鑰苗胀,而是說不可能通過遍歷的方式找到某一個特定的私鑰,或者通過其它的方式找瓦堵,而不通過私鑰就能花費地址上面的比特幣,私鑰的安全性是由數(shù)學(xué)上保證的。
私鑰的總數(shù)量很大淌铐,但是私鑰的生成是依賴隨機數(shù)的澜术,真正的隨機是很難做到的,大部分私鑰的生成都是依賴于偽隨機算法(PRNG)
惋鸥。
偽隨機是用函數(shù)生成隨機數(shù)杂穷。它并不真正是隨機的。只是一個比較近似真隨機的隨機數(shù)卦绣。
私鑰生成的隨機性就很重要的耐量,密碼學(xué)上安全的隨機是指:
隨機是不可預(yù)測的,隨機的結(jié)果是不可遍歷的滤港,如果不是安全的隨機數(shù)生成器廊蜒,生成的私鑰就有可能被別人碰撞到。不依賴隨機生成的私鑰就會大大的降低其生成的概率空間溅漾。
公鑰和地址的生成都依賴私鑰山叮,所以我們只需要保存私鑰即可,有了私鑰就能生成公鑰和地址添履,就能夠花費對應(yīng)地址上面的比特幣屁倔。
- 私鑰到字符串
上面提高的私鑰字符串是按照一定的規(guī)律從32位byte數(shù)據(jù)格式化生成的,32個byte的數(shù)組是由256個0或者1組成的,如果顯示出來暮胧,不僅僅是識別率不高锐借,而且私鑰太長。
因此私鑰字符串就是對于原始的隨機數(shù)進行一定的轉(zhuǎn)換叔壤,轉(zhuǎn)換為識別率高的形式瞎饲,上面私鑰的是對32個byte數(shù)組就做了Base58
的轉(zhuǎn)換.
Base58是用于比特幣中使用的一種獨特的編碼方式,主要用于產(chǎn)生Bitcoin的錢包地址和私鑰炼绘。相比Base64嗅战,Base58不使用數(shù)字"0",字母大寫"O",字母大寫"I"驮捍,和字母小寫"l"疟呐,以及"+"和"/"符號。這樣做的主要原因是為了肉眼容易識別东且,在輸入的時候不容易打錯启具,
不過上面那段沒有規(guī)律的字符串輸入起來還是挺費勁的,當(dāng)然也可以把私鑰轉(zhuǎn)換其他形式珊泳,比如以單詞的形式(12或者24個單詞)鲁冯,腦錢包的形式,又或者自己記住的某一句話來生成私鑰,注意腦錢包生成的私鑰隨機的安全性并不高色查。
我們看到的私鑰除了以5開頭的以外薯演,還有以L
和K
開頭的私鑰,為什么會出現(xiàn)這樣的情況呢秧了?5跨扮,L,K
又帶代表什么呢验毡?這就要說到公鑰了衡创。
公鑰
比特幣的根基是橢圓曲線數(shù)字簽名算法
:
橢圓曲線數(shù)字簽名算法(ECDSA)是使用橢圓曲線密碼(ECC)對數(shù)字簽名算法(DSA)的模擬
橢圓曲線加密法(ECC)
是一種公私鑰加密技術(shù):
ECC以橢圓曲線理論為基礎(chǔ),利用橢圓曲線等式的性質(zhì)來產(chǎn)生密鑰晶通,而不是采用傳統(tǒng)的方法利用大質(zhì)數(shù)的積來產(chǎn)生璃氢,其特點是:密鑰長度小,安全性能高狮辽,整個數(shù)字簽名耗時小拔莱。
DSA(DigitalSignature Standard)數(shù)字簽名技術(shù):
在DSA數(shù)字簽名和認證中,發(fā)送者使用自己的私鑰對文件或消息進行簽名隘竭,接受者收到消息后使用發(fā)送者的公鑰來驗證簽名的真實性塘秦。
這里明確了私鑰
用來簽名
,而公鑰
用來驗證簽名
动看。
公鑰是由私鑰生成的尊剔,通過橢圓曲線(ECPoint)
生成,一個私鑰經(jīng)過橢圓曲線
變換之后能夠得到公鑰菱皆,公鑰是一個65個byte數(shù)組须误,一般我們會看到這樣的一個公鑰:
04a34b99f22c790c4e36b2b3c2c35a36db06226e41c692fc82b8b56ac1c540c5bd5b8dec5235a0fa8722476c7709c02559e3aa73aa03918ba2d492eea75abea235
顯示出的公鑰一般把byte數(shù)組是經(jīng)過hex(16進制)
的處理之后顯示,不經(jīng)過Base58的原因是: 公鑰是用來驗證私鑰的簽名仇轻,一般我們很少會看到公鑰京痢,使用私鑰簽名交易之后,會把自己的公鑰一起和交易發(fā)送出去篷店,這樣對于一個完整的交易開說祭椰,他就使用交易里包含的公鑰驗證私鑰的簽名是否正確臭家。
私鑰和公鑰是成對出現(xiàn)的,一個私鑰簽名的數(shù)據(jù)方淤,只有對應(yīng)的公鑰才能對其進行驗證钉赁,而地址也是從公鑰生成的,這樣就可以驗證花費的交易是不是屬于這個地址了携茂!
- 回答下上面的問題為什么會出現(xiàn)5開頭或者L,K開頭的私鑰你踩?
出現(xiàn)這種情況是因為公鑰的不同格式而產(chǎn)生了不同的私鑰格式,早期的比特幣開發(fā)者沒有使用壓縮的公鑰(橢圓曲線是對稱的讳苦,知道了一半的信息就可以推導(dǎo)出來另外一半的信息了)带膜,因此只需要保存一般的公鑰信息即可。壓縮的公鑰只有33個byte,而未壓縮的公鑰有65個byte鸳谜。
私鑰開頭的第一位的不同钱慢,是用來區(qū)分該私鑰使用的公鑰是否支持壓縮格式
壓縮的公鑰對比特幣的意義很大,比特幣是去中心化的p2p加密貨幣
卿堂,每個節(jié)點都會擁有完整的交易記錄,除了coinbase
(挖礦得到的比特幣)以外懒棉,每個交易都需要發(fā)送公鑰草描,支持壓縮格式的公鑰,每個交易的數(shù)據(jù)就可以減少32個字節(jié)策严,這對整個比特幣網(wǎng)絡(luò)是非常有意義的,整個比特幣網(wǎng)絡(luò)的數(shù)據(jù)在傳輸和保存中都可以提高不少效率穗慕。
而對私鑰進行Base58編碼的時候,老版本未壓縮公鑰的私鑰是33位byte數(shù)組妻导,第一位存放私鑰的Version信息
逛绵,當(dāng)前值為128,生成的Base58都是以5開頭倔韭。
老版本未壓縮私鑰=Base58(version+32位隨機數(shù))
支持壓縮公鑰的私鑰是34位术浪,同樣是第一位是version信息,它的值也是128寿酌,而多出來的一位是最后一個byte是用來存放是否壓縮信息的信息
胰苏,1就表示是支持壓縮格式的公鑰
。經(jīng)過Base58處理之后正好是L或者K開頭
新版本私鑰格式=Base58(version+32位隨機數(shù)+是否支持壓縮)
例子中的私鑰不僅僅包含了32個byte數(shù)組的信息醇疼,還是私鑰version的信息以及其公鑰是否壓縮的信息(通過位數(shù)和值來判斷)
公鑰是否壓縮除了對私鑰的顯示有影響以外硕并,還會對地址有影響。
地址
公鑰太長了秧荆,所以就有更短一些的地址的概念倔毙,另一方面沒有發(fā)送過交易的地址,并不想暴露自己的公鑰乙濒,而地址是通過摘要算法
生成的,不會暴露公鑰的真實內(nèi)容:
地址是由公鑰產(chǎn)生的,地址長度為25byte,經(jīng)過base58處理陕赃,地址未尾添加了4個字節(jié)的校驗位。
我們看到的地址一般都是Base58
編碼處理的,地址的生成比較復(fù)雜凯正,公鑰到地址生成的過程是毙玻,先對公鑰做一次SHA256
(哈希算法)。
sha-256-hash= SHA-256(public key)
再經(jīng)過了hash160
處理廊散, hash160:RIPEMD(PACE integrity Primitives Evaluation Message Digest)
是一種原始完整性校驗消息摘要桑滩,160標(biāo)準(zhǔn)對應(yīng)20字節(jié):
hash160=hash160(sha-256-hash)
對結(jié)果進行hash160處理可以得到一個20個byte的數(shù)組,在這個20位的byte數(shù)組前面再加上一個byte,這個byte就是地址的Version信息允睹,地址的Version當(dāng)前值為0运准,Version信息在比特幣的test網(wǎng)絡(luò)
上會使用不同的值,比特幣地址完成的表示就是:
address=Base58(version+hash160(SHA-256(public key))+checksum)
checksum是用來對于比特幣地址進行檢驗的,再得到的hash160中加入地址的version信息 缭受,再對該信息做兩次SHA-256
之后取前4位就是checksum:
checksum=get_front_four( SHA-256(SHA-256(version+hash160)))
其中hash160是這個過程中最重要的信息胁澳,從這個值就可以到地址的前21位(第一位是version)和后面的checksum, 進而可以生成Base58格式的地址。而從Base58格式的地址中也可以得到hash160米者,也就是說hash160格式可以和Base58格式的地址互換韭畸。
私鑰的不同對于地址有什么樣的影響呢?
前面已經(jīng)說了:
一個隨機數(shù)可以有一個壓縮的公鑰蔓搞,和一個未壓縮的公鑰
而每個公鑰都會生成一個地址胰丁,上面私鑰其實可以有兩個地址分別為:
1HZwkjkeaoZfTSaJxDw6aKkxp45agDiEzN(未壓縮公鑰)
1F3sAm6ZtwLAUnj7d38pGFxtP3RVEvtsbV (壓縮公鑰)
這兩個地址都是這一個隨機數(shù)生成的地址,每個地址上面的比特幣都可以用這個隨機數(shù)對應(yīng)的私鑰花費喂分。目前大多數(shù)的應(yīng)用默認都使用壓縮格式的私鑰锦庸。
- 總結(jié)
對于私鑰,公鑰和地址來說蒲祈,公鑰
作為私鑰到地址的中間橋梁甘萧,他在交易的驗證是最關(guān)鍵的:對于一個交易的驗證,公鑰的作用:
- 公鑰生成地址梆掸,驗證發(fā)送交易的地址是否和該公鑰生成的地址一致
- 公鑰驗證私鑰的簽名扬卷,用來驗證該交易是否使用了正確的私鑰簽名
- 私鑰生成公鑰是成對出現(xiàn),公鑰可以生成對應(yīng)的唯一地址酸钦,這樣就能確認了該地址發(fā)送的交易是否使用了對應(yīng)的私鑰