Miniscript:讓比特幣程式設計更便捷高效的“神器”

買賣虛擬貨幣
比特幣為世界帶來了首個智慧合約開發語言——Script,其能夠讓不同的加密貨幣在不同的程式設計環境下被使用。然而這一概念在極具顛覆性的同時,使用起來卻有一定難度,特別是在較為複雜的花費環境下。無論是編寫較為複雜的智慧合約,還是驗證合約是否正確執行其職能,都很容易出現人為錯誤,在關係到資產安全的情況下,對於指令碼程式執行條件正確性的驗證變得尤為重要.在過去的一年中,區塊鏈工程師Andrew Poelstra, Pieter Wuille(比特幣核心開發人員、同時也是隔離見證機制SegWit建立者)和Sanket Kanjalkar開始著手改進這一點。透過將Script語言拆分簡化,保留其最基本的要素和功能,最佳化出了新的程式語言——Miniscript——減少了原程式語言的複雜性,讓所有進行比特幣程式設計的人們獲得更安全、便捷的體驗。

從理論上來講Miniscript相比Script有了更多的明確的使用條件和限制,但實際上人們可以用它完成任何Script所能做的事情。Blockstream研發主管以及Miniscript聯合設計者Andrew Poelstra表示。

SCRIPT

我們首先來簡單瞭解一下Script語言。

每一筆比特幣交易都包含兩個主要部分:輸入和輸出,二者都有自己的程式碼,輸入“解鎖”了代幣,而輸出將代幣再次“鎖住”,並規定了下一次被解鎖再次進行交易輸入的條件,在這些條件中通常包括一個有效的加密簽名,更多的可能條件例如:該比特幣必須經過一定的時間後,或必須含有特殊的密碼才能被使用或花費。

交易中的這段程式碼就是用Script建立的,Script是專門為比特幣設計的程式語言。其靈感來自於Forth,一種20世紀60年代發明的程式語言,最初設計用來操作射電望遠鏡。不過,Script在經過調整之後更加契合比特幣。

例如,Script中沒有使“迴圈”的操作碼:該語言不支援無限次執行相同的計算。因為在比特幣中,沒有必要無限次地執行相同的計算,因為比特幣的節點們實際上並不透過計算進行交易——而是驗證交易。關於為什麼會出現這種情況,Blockstream工程師羅素·奧康納在三年前就釋出了文章:對比特幣和以太坊的指令碼語言和理念進行比較,其中進行了較為詳細的解釋。

同時Script並沒有被“類化”,這意味著計算的結果可以以不同的方式被註釋和使用,舉個很簡單的例子,一個有效簽名的結果可能是“true”,而“true”可以被註釋轉化等於數字“1”進而用於數學程式中,true=1,而true+true則可以被看成1+1=2,意味著如果交易最少需要兩個有效簽名進行驗證,則其滿足了這個條件。

這其實為我們引入了Script語言中最重要的一個屬性——“難以推理” 這基本意味著Script的計算結果能夠以多種方式被註釋轉化,即使一個簽名是無效的,在Script中其仍可以出於某些原因將其編寫為有效。

在Bitcoin Script中的確有一些運算碼在執行時鬧出荒唐事,例如,將一個簽名解釋為真/假值,在此之後將該布林值轉化為數字(例如1/0)後編入堆疊索引中,再根據這一數值將堆疊重新排列,然而在實際執行過程中其具體規則是非常荒唐可笑的,Poelstra解釋道。

這樣一來在透過Script處理一些問題時會很棘手,尤其是在花費代幣的要求變得更加複雜時,一筆交易的發起者的程式碼中可能會無意中包含了允許代幣在其他條件下被使用的資訊,反過來也就是說,交易的收款方有可能因為沒有注意到這樣的“漏洞”而被發現這樣資訊的攻擊者攻擊受到損失。

總結來說,當前Bitcoin Script的最大問題是在對較為複雜的程式進行驗證時比較困難。

問題的具體舉例

關於以上的問題如何限制了Script的實用性,下面我們舉一個具體一些的例子。

Blockstream Green Wallet錢包有一個標準的“共同簽名”設定,錢包使用者掌控 2 個金鑰中的一個,Blockstream掌控另一個,這樣一來錢包中的數字資產能夠透過兩種方式被使用。使用者想要使用資產:使用者簽署了該筆交易並請求Blockstream一併簽署,通常Blockstream都會透過執行(經過郵箱或簡訊驗證碼二次確認後);但可能發生的一種情況是:Blockstream這一端出現了問題——如公司跑路或者丟失了金鑰,或出於其他原因無法簽署。在這樣的情況下,使用者需要使用一個備用方案來完成這筆交易:如在鎖定時間過後,使用者可以在預定時間過後完成該筆交易。

這樣的解決方案似乎可行,但仍會受到限制,比如使用者將無法再使用任何其他比特幣的潛在智慧合約,或在其終端增加更多靈活可擴充套件的設定。

現在Green有一個適用於所有客戶的預備指令碼,基本上就是一個簡單的多重簽名,但是我們並不真正在乎指令碼講了什麼,我們在乎的是,在規定時間內,交易代幣是否有可能在不需要我們簽名的情況下被交易?如果使用者提出一些與常人不同的要求,但只要原則上這些要求是我們關心和在乎的,我們就應該滿足和支援。

舉個例子,一些使用者以防有什麼意外發生,希望讓他的另一半或家人在一年後能夠繼承使用這筆資產;或以使用者是一家公司為例,其希望建立一個使用機制,例如需要三分之二或更多的董事會成員許可權才能共同使用資產。

當然從技術上來講,在比特幣指令碼語言中以上的情況都是可以被實現的,但這將需要使用者設計一個自定義程式,而Blockstream(資產託管方)也需要確保參與其中。

這樣就太複雜了,“如果使用者任意提供給我們一個指令碼語言,我們幾乎無法確定其是否滿足了我們所關心在乎的那個執行條件,因為所有指令碼行為的組合非常複雜,舉個例子,假如使用者提供的一個指令碼程式看上去需要一個簽名進行認證,但我們還需要考慮,如果使用者提供了一個non-signiture會發生什麼情況?其是否會觸發其他條件使資產能夠被呼叫?等等。”Poelstra解釋道。

Miniscript

在過去的一年中,Poelstra、Blockstream 核心技術工程師Pieter Wuille和Sanket Kanjalkar設計了Miniscript,Miniscript官方並不屬於Blockstream的產品。

簡而言之,Miniscript是一個“刪減版”的Script:從Script工具包Script toolkit中整合選擇了更加易用和易於被驗證的工具,而除去極少數基本無人使用的工具外,幾乎所有Script能幹的事Miniscript也能幹。本質上來講,一行Miniscript的程式碼仍可以看作等於一行有效地Script程式碼,只不過Miniscript透過防止程式碼出現意料之外結果而儘可能的減少Bug的出現。

就拿我們上面提到過的問題來說,使用者可以利用Miniscript更加容易地設計出一個便於Blockstream驗證其是否滿足執行條件的設定,詳細來講,Blockstream能夠更加清晰地明白使用者資產的被使用條件,如,要麼簽名透過,要麼時間到了,不管使用者在其自定義程式端還夾雜了任何其他附加條件,如額外的時間要求、多重簽名等,說白了,使用了Miniscript,在Blockstream端來看可以免去那些花裡胡哨的,可能影響驗證條件或偷換概念的東西,更乾淨利落。

Miniscript語言非常直接且可預測,其程式總能導向一個決策樹,將程式很清楚的呈現出來,就像影象編碼,易於推理。

就在上週,Pieter Wuille在Medium發文再次介紹了Miniscript(Miniscript: 改進後的比特幣指令碼語言),他拿一段在比特幣指令碼語言中的程式碼為例:<A> OP_CHECKSIG OP_IFDUP OP_NOTIF OP_DUP OP_HASh260 <hash260(B)> OP_EQUALVERIFY OP_CHECKSIGVERIFY <144> OP_CSV OP_ENDIF

其中,A和B為公鑰,在Miniscript中這段語言可以被精簡為:or_d(c:pk(A),and_v(vc:pk_h(B),older(144)))

這段程式碼很清楚明瞭地表現了代幣的解鎖條件:A簽名透過;或者經過 144 個區塊後B簽名透過。而很大一部分的Script可以以這樣的方式編寫。

策略語言和投入使用

儘管Miniscript也還在繼續開發中,但其早期版本已經發布並可以投入使用了。

甚至為了讓編寫Miniscript變得更加簡單,Wuille還設計了一種“策略語言”,策略語言更像是使用者編寫自己熟悉的語言,其最終可以被編譯至Miniscript格式,進而可以被用於Script,併入比特幣交易輸出中。

這種策略語言的最大好處就是,它會在根據指令碼編寫的不同情況下,儘可能地自動地轉換至最合適、高效的Miniscript格式。

在Script裡你可以有非常多的編寫方式表達‘或(or)’;有非常多的編寫方式表達‘和(and)’,但當然其中總有一些表達方法是更高效的,而策略語言中‘或(or)’、‘和and’和其他條件的表達方式是固定的,Pieter Wuille還設計編寫了一個超極簡單明瞭的編譯器(compiler),讓策略語言能夠以最優的方式轉化至Miniscript格式。

根據其線上編譯器,剛剛我們舉例編碼在策略語言中可以再次被轉化為:or(admin@chaindaily(A),admin@chaindaily(pk(B),older(144)))

這樣的寫法意思是:左邊的 “或(or)”被採用的概率是99%(A簽名透過);右邊情況“和(and)”(經過144個區塊後B簽名透過)發生概率為1%。

值得注意的是,以上並不僅僅是一個理論概念,雖然當前的Miniscript和編譯器都不是最終版本,但Blockstream內部已經正在將其使用於Liquid官方側鏈軟體的分支開發中了,其中一個功能被稱為Dynamic Federations,其允許現有的Liquid成員對新加入的成員進行管理,或對現有在聯盟控制下的比特幣使用許可權的指令碼進行更新。Miniscript為構建和更新此類相關的Script提供了更高效快速的工具,經過現有的Miniscript編譯器轉化後,原有的已經經過人工精簡和最佳化過的Liquid Script指令碼被再次精簡了 22 個位元組,相比原有的指令碼約節省了 5% 的工作量。更重要的是,其允許成員對新提出的指令碼更改的主體部分(成員金鑰、代幣緊急被呼叫的條件正確性以及聯盟新成員對原聯盟控制資產的使用條件等)進行自動化驗證,減少了成員間相互協調、對指令碼進行復雜的人工安全審計的必要。

目前Miniscript的策略語言編譯器可以支援C++和Rust語言的轉化,為了讓這項技術更易於使用,Pieter表示未來他們還需將它與其他常用軟體整合整合,透過實現對相位整形二進位制傳輸(雙二進位制,PSBT)和Miniscript的相容(更新器updater和終結器finalizer等),許多PSBT簽名使用者(包括硬體錢包)即使沒有顯式支援的情況下,也可被用於複雜的指令碼中;此外,由於許多策略語言的指令碼轉換結果還沒有被考慮到,編譯器也將會被進一步最佳化改進。

免責聲明:

  1. 本文版權歸原作者所有,僅代表作者本人觀點,不代表鏈報觀點或立場。
  2. 如發現文章、圖片等侵權行爲,侵權責任將由作者本人承擔。
  3. 鏈報僅提供相關項目信息,不構成任何投資建議

推荐阅读

;