自high筆記——基於非密碼學方法容錯的分佈式計算的完備理論

SMC(secure multiparty computation)多方安全計算致力於在結合多方資源進行計算下最大化的保護各方的隱私信息,隨着現今大數據時代的到來,SMC在數據安全領域有着越來越重要的地位。

大神Shamir提出的祕密共享(secret sharing)旨在將隱私數據拆分爲不同的份額分配給不同的人,每一個拿到份額的一方可以利用其計算,但無法通過自己的那一份得到完整的信息。這就好比小明畫了一幅畫,他把這幅畫做成拼圖給他的朋友每人一塊,任意一塊都不足夠他的朋友猜出畫上的內容,而只有多人將拼圖拼起來才能知道小明畫在紙上的信息。

SMC有許多實現的協議和方法,secret sharing擁有很好同態性質並且計算時間控制在多項式級,容易做成算法電路,因此許多協議都是基於secret sharing。

Completeness Theorems for Non-Cryptographic Fault-Tolerant Distributed Computation發表於1988年,是基於secret sharing的一個比較經典的protocol,後來有許多協議都對這個protocol提出了一些改進,因此對這個protocol的學習可以加深對於secret sharing的理解。

下面是作者作爲一個小白對這篇論文的理解和整理,淺顯且會出現理解的偏差,希望僅作討論使用。

原文:http://citeseerx.ist.psu.edu/viewdoc/downloaddoi=10.1.1.116.2968&rep=rep1&type=pdf
How to Share a Secret: https://cs.jhu.edu/~sdoshi/crypto/papers/shamirturing.pdf


首先提及兩種性質,t-private和t-resilient,分別對應gossip和byzantine agreement的問題。一套分佈式系統如果可以抵禦最多t個人的共謀(collusion)而不泄漏隱私,那麼這個分佈式系統具有t-private的特點;而如果這套系統可以在出現t個byzantine agreement問題中的叛賊將軍的情況下仍然計算出正確的結果,那麼稱這套系統具有t-resilient的性質。

總的來說,這篇文章說了兩個事:

  1. t<n2t< \frac{n}{2}時,對於所有計算都存在t-private的協議
  2. t<n3t< \frac{n}{3}時,對於所有計算都存在t-resilient的協議

由於題目中提到了完備性,所以文章中也分別對t大於等於n2n3\frac{n}{2}、\frac{n}{3}的情況進行了討論。

論文首先討論了分佈式系統的兩大實現原理,一個是基於密碼學原理,也就是創造一個單向函數(one-way function),利用這個函數進行信息交換,另一個基於非密碼學原理,也就是信息論,這類方法規避了密碼學對算力的假設,也即敵人有無限算力的情況下也無法威脅系統的隱私及安全,這種方法對隱私具有更高的定義,這篇文章敘述的協議就是基於第二種方法的。

整個協議基於Shamir大神提出的secret sharing,可以做到t-out-of-n,也就是t個人可以對某個信息進行操作,這樣規避了一些節點出現掉線甚至不忠誠的問題。協議的實現要基於一下假設:

  1. 協議實質上是n個完全同步的處理器中的程序
  2. 兩兩相互安全的信道
  3. 在一輪的信息交換中,每個處理器可以給其他的players各發送一條信息,閱讀所有收到的信息,並且進行無數次的運算
  4. 無限的算力。這裏要說明一下,因爲這個方法不基於處理器的計算能力,並且協議中不存在大量耗費時間的計算,所以在協議中對算力進行假設是沒有意義的。

協議分爲三個階段,分別是輸入階段(input stage)、計算階段(compute stage)和結果階段(final stage)。在輸入階段,每個數據的owner要對自己的數據進行一定的處理,不僅要保證自己的數據具有t-private的特性,還要具有t-resilient的特性,與此同時,還要讓數據的接收方在無法獲取實際數據的情況下信任它的數據;在計算階段,由於使用的多項式具有一定的同態性,每個節點在驗證信任他獲取的share是真實有效的後,對其進行計算和處理,使數據的使用者除了結果以外得不到任何信息;而在結果階段,希望得到數據運算結果的節點先根據數據的特點對數據進行驗證和糾錯,然後再根據得到的數據進行插值計算。

在輸入階段,數據的擁有者爲了保證系統的t-private的特性,隨機生成aiEa_i\in E, 得到f(x)=a0+a1x+a2x2+...+atxtf(x)=a_0+a_1x+a_2x^2+...+a_tx^t, 然後發送si=f(wi)s_i=f(w^i), i=1,2,…,n給每一個節點。根據線性代數的知識可以得到,只有t+1個人進行了共謀(collusion)才能迫使祕密泄漏,這就保證了t-private的特性。這裏E就是整個系統的域,E儘量要取大一些,能夠提高系統的安全,雖然會引入更大的計算量,但至少|E|要大於n。這裏的w滿足wn mod E=1w^n\ mod\ E=1,並且當j̸=nj\not=nwj mod E̸=1w^j\ mod\ E \not= 1。每個節點都有特定的i,相當於每個節點的identifier,這個i是互相知道的,爲什麼要用wiw^i呢,我們假設在final stage中某節點收到了序列(s0,s1,s2,...,sn1)(s_0,s_1,s_2,...,s_{n-1}),利用編碼理論的方法可以列出f(x)^=s0+s1x+...+sn1xn1\hat{f(x)}=s_0+s_1x+...+s_{n-1}x^{n-1},編碼時,當x=wiw^i,則根據傅立葉逆變換可以得到ai=1nf^(w1)a_i=\frac{1}{n}\hat{f}(w^{-1}),利用這一性質可以證明s序列是由g(x)=i=t+1n1(xwi)g(x)=\prod_{i=t+1}^{n-1}(x-w^{-i})生成的Generalized Reed-Muller Code,然後根據BCH碼的生成方法就能對s序列進行t個糾錯(12deg g(x)\frac{1}{2}deg\ g(x)),從而保證了t-resilient的特性。在數據owner分享他祕密的同時,其實並不是發給每個節點一對值,而是發送一個多項式fi(x)f_i(x),這個多項式的常數項爲對應的si,接收者通過計算fi(0)f_i(0)來獲取他的share,與此同時,owner還會配套發送多項式gi(x)g_i(x),利用這個函數,接收者們通過合作的方式來決定這個數據是否可接受,這個過程就是我們所說的零知識證明。

細節一: BCH碼
t-private的實現推薦去看Shamir的How to Share a Secret, 下面我來通過介紹BCH碼的方式介紹一下t-resilient的實現。我的理解較淺顯,如果想了解深入BCH碼,建議去看Peterson和Weldon的Error-Correcting Codes
BCH碼是在編碼理論中屬於循環線性碼的一種,名字來自於其發明者名字的首字母,它擁有對多個錯誤進行糾錯的能力,BCH碼與其他線性碼不同的地方在於他可以根據碼的糾錯能力來生成碼。
BCH碼的編碼涉及域論,假設GF(pm)GF(p^m)GF(p)GF(p)的擴域,GF(pm)GF(p^m)上的本原元就是其域中的一個元素,由這個元素的乘方可以得到該域內的所有元素。對於參數取自GF(p)GF(p),以本原元爲根的最小多項式就是該擴域上的本原多項式。注意到xpm11=(xb1)(xb2)...(xbpm1)x^{p^m-1}-1=(x-b_1)(x-b_2)...(x-b_{p^m-1}),其中b取自擴域上的全部非零元素,這樣利用因式分解可以得到本原元的每個次冪對應的最小多項式,一般來說,如果p=2,對應結果可以通過查表獲取。
說了這麼多,我自己都有些雲裏霧裏,生成上面的列表就是爲了生成我們想要的BCH碼,當我們想要編碼擁有t個糾錯的能力,我們就計算g(x)=LCM(f1(x),f2(x),...,f2t(x))g(x)=LCM(f_1(x),f_2(x),...,f_{2t}(x)),也就是獲取本原元前2t次冪對應的最小多項式的最小公倍多項式,假設我們想傳遞的信息爲m(x),其信息位爲k,那麼生成的編碼就爲c(x)=m(x)×xr+m(x) mod g(x)c(x)=m(x)\times x^r+m(x)\ mod\ g(x),其中r爲g(x)的階數,這樣生成的碼長爲n=k+r,同時我們也注意到生成的碼有一個可貴的品質,那就是所有g(x)的根都是c(x)的根。碼距?
下面來說BCH碼的譯碼。所謂糾錯能力,就是指找到碼中出現的錯誤以及對應錯誤的幅值。我們假設收到的碼爲r(x)=c(x)+e(x),e(x)就是出現的錯誤,e(x)=i=1vyixp(i)e(x)=\sum_{i=1}^vy_ix^{p(i)},也就是所有錯誤偏差的幅值乘以對應的位置,我們如果把g(x)的根代入r(x)可以得到r(αi)=c(αi)+e(αi)=0+e(αi)=e(αi)=Sir(\alpha_i)=c(\alpha_i)+e(\alpha_i)=0+e(\alpha_i)=e(\alpha_i)=S_i,另外,由於(Si)q=(i=1vyixp(i))q=i=1vyixp(i)+q=Siq(S_i)^q=(\sum_{i=1}^vy_ix^{p(i)})^q=\sum_{i=1}^vy_ix^{p(i)+q}=S_{iq},使我們只計算S1,S3,...S_1,S_3,...就可以通過平方的形式得到偶數下標的S,這下我們開心了,因爲我們可以得到2t個(αi,Si)(\alpha_i,S_i)個數對,又由於e(x)中有2v個未知數,這樣只要vtv\leq t我們就能解出所有錯誤出現的位置和對應幅值。然而,由於x與y均爲未知數,e(x)的並非線性函數,我們需要將其轉化爲線性函數進行計算。
注意到(xx1)(xx2)...(xxv)=xv+δ1xv1+...+δv(x-x_1)(x-x_2)...(x-x_v)=x^v+\delta_1x^{v-1}+...+\delta_v,用αi\alpha_i取代其中的x1、x2…,則當x=αi,i=1,2,...,vx=\alpha_i, i=1,2,...,v時右面的方程式爲0,進而有yixijδv+yixij+1δv1+...+yixij+v=0y_ix_i^j\delta_v+y_ix_i^{j+1}\delta_{v-1}+...+y_ix_i^{j+v}=0。使用αi,i=m0,m0+1,...,m0+v\alpha_i, i=m_0,m_{0+1},...,m_{0+v}代入後對得到的方程進行相加就可以得到Sm0δv+Sm0+1δv1+...+Sm0+v=0S_{m_0}\delta_v+S_{m_0+1}\delta_{v-1}+...+S_{m_0+v}=0,當m0=1,2,...,vm_0=1,2,...,v,我們就可以列出v個這樣的方程,只要vtv\leq t,這個方程就可以解出全部的δ\delta,求出δ\delta代回上面的公式,求出的根就是對應的出錯位置xp(i)x^{p(i)}。這裏要注意一個問題,我們可以將以上S轉化爲一個v×vv\times v的矩陣,如果生成的矩陣不是滿秩的,說明發生錯誤小於t,這時候需要通過去掉未知數的方法將矩陣降階。在得到錯誤位置後,通過把求出的X代回X*Y=S就能計算出對應的Y,如果是二值編碼則可以省掉這個步驟。
在這個協議中,當接收節點接收到(s0,s1,...,sn1)(s_0,s_1,...,s_{n-1})序列後,利用g(x)的根(w(t+1),w(t+2),...,w(n1))(w^{-(t+1)},w^{-(t+2)},...,w^{-(n-1)})進行校驗和糾錯,就可以保證擁有t-resilient的能力,所以這裏要求n3t+1n\geq 3t+1
有沒有一種碼可以在解碼的同時譯碼?

細節二:
整個協議的保密措施都是基於所有祕密被encode在各自的t階多項式中的,包括涉及到的計算也針對t階多項式進行了許多操作,因此數據owner需要在不透露自己數據的情況下證明自己發出的shares確實是依據協議由t階多項式生成的,爲了達成這個目的,協議使用了零知識證明(zero-knowledge proof)。
首先,owner生成一個f(x,y)的多項式,其中x和y均有t階,並且滿足f(0,0)=s,也就是他的原數據,這時owner就把fi(x)=f(x,wi)f_i(x)=f(x,w^i)gi(x)=f(wi,y)g_i(x)=f(w^i,y)發給第i個節點,這樣第i個節點就可以計算f(wj,wi)=fi(wj)f(w^j,w^i)=f_i(w^j)併發送給第j個節點,第j個節點比對收到的值和gj(wi)g_j(w^i),如果它有t+1個值都出現了不匹配的情況,那麼它就會請求公佈自己收到的信息,如果owner拒絕公佈或公佈後t+1個節點都對此報錯,說明數據有問題,那麼各個節點就會對這個owner節點的數據做一定的處理,例如取零。這個過程中,要麼公佈的數據是有問題的,要麼owner的數據就是有問題的,所以在這裏並沒有任何的隱私泄漏問題。
(如果正確的節點報錯導致泄漏怎麼辦)ECC

細節三:
owner利用f(x)和g(x)對數據a、b進行加密,假如他現在想利用c(x)分配一個祕密c=abc=a*b,並且希望它用的c(x)的參數是隨機分佈的,但同時又能證明裏面的祕密確實是c=abc=a*b
D(x)=A(x)×B(x)=c+c1x+...+c2tx2tD(x)=A(x)\times B(x)=c+c_1x+...+c_{2t}x^{2t}
Dt(x)=rt,0+rt,1x+...+rt,t1xt1+c2txtD_t(x)=r_{t,0}+r_{t,1}x+...+r_{t,t-1}x^{t-1}+c_{2t}x^{t}
Dt1(x)=rt1,0+rt1,1x+...+rt1,t1xt1+[c2t1rt,t1]xtD_{t-1}(x)=r_{t-1,0}+r_{t-1,1}x+...+r_{t-1,t-1}x^{t-1}+[c_{2t-1}-r_{t,t-1}]x^{t}

D1(x)=r1,0+r1,1x+...+r1,t1xt1+[ct+1rt,1rt1,r...r2,t1]xtD_1(x)=r_{1,0}+r_{1,1}x+...+r_{1,t-1}x^{t-1}+[c_{t+1}-r_{t,1}-r_{t-1,r}-...-r_{2,t-1}]x^t
在生成這些多項式後,得到C(x)=D(x)i=1txiDi(x)C(x)=D(x)-\sum_{i=1}^tx^i*D_i(x),把(wi,C(wi))(w^i,C(w^i))和相應Di(x)的值都發出去,就可以做到對C(x)的校驗了。

下面來介紹一下計算階段,在計算階段開始前,每個節點都已經檢驗確保了自己得到的shares是由數據owner遵守協議給出的。對於加法和常數乘法運算,多項式擁有很好的同態性質,例如f(x)和g(x)對a和b進行了加密,那麼h(x)=f(x)+g(x)就包含了a+b的信息,常數乘以一個函數也可以用這種方法進行運算。然而對於乘法的運算,會產生階數增加的問題,**兩個t階的多項式相乘會得到一個階數爲2t的多項式,對於n>2t的情況還勉強可以解決,**但每次的運算並不是只相乘一次的,並且這個2t多項式的參數相互之間不具有獨立性,這就需要我們進行降階(degree reduction)。
在進行插值前,假設某一節點收到了序列(s0,s1,...,sn1)(s_0,s_1,...,s_{n-1}),這一序列是由2t階的多項式產生的,我們想將這一序列轉化爲由t階多項式產生的序列(r0,r1,...,rn1)(r_0,r_1,...,r_{n-1})

H=(h1,h2,...,h2t,0,0,0...)1×nH=(h_1,h_2,...,h_{2t},0,0,0...)_{1\times n}
K=(h0,...,ht,0,0,0,...)1×nK=(h_0,...,ht,0,0,0,...)_{1\times n}
P是一個截取變換(truncation),P(x0,x1,...,xn1)=(x0,x1,...,xt,0,0,...)1×nP(x_0,x_1,...,x_{n-1})=(x_0,x_1,...,x_{t},0,0,...)_{1\times n}
B爲範德蒙特矩陣,
HB=SH·B=S
HP=KH·P=K
KP=RK·P=R
所以得到S(B1PB)=RS·(B^{-1}PB)=R,由於A=B1PBA=B^{-1}PB爲常數,這就爲degree reduction提供了很方便的計算方法。
爲了進一步消除2t多項式參數之間的獨立性,在各個節點將計算結果給到計算final stage的節點之前,這些節點會對給出的值做隨機化,也就是隨機生成一個沒有常數項的t階多項式,利用自己的wiw^i計算加到給出結果上,即h(x)=h(x)+j=0n1qj(x)h'(x)=h(x)+\sum_{j=0}^{n-1}q_j(x),且h(0)=h(0)h'(0)=h(0)

最後的結果階段,某個節點收到其他節點發來他們經過處理後的shares之後,利用編碼理論的方法對收到的值進行校驗和校正,利用得到的結果進行正確的插值計算。

發表評論
所有評論
還沒有人評論,想成為第一個評論的人麼? 請在上方評論欄輸入並且點擊發布.
相關文章