SHA-256算法詳解——Github工程結合示例和動畫演示

近日筆者在學習區塊鏈的相關知識,接觸到SHA-256算法,這里做一個知識梳理和總結。

強烈推薦大家自行去學習下面鏈接github上的工程,作者的動畫演示和解釋做的非常出色,邏輯非常清晰,B站搬運的對應的油管的講解視頻也放在下面,本文也是基于此github工程和作者學習過程的思路進行呈現。

github:

https://github.com/in3rsha/sha256-animation

B站講解視頻:

https://www.bilibili.com/video/BV1Jg411G7tc

ruby(windows)安裝教程:

https://www.cnblogs.com/minisayo/p/14015747.html

可以先將github工程下載到本地,因為作者是用的ruby進行動畫展示,所以需要再windows/Linux系統上安裝ruby,之后在工程目錄下調用ruby xxx.rb指令即可啦。

下面是整個工程的流程圖,也對應著SHA-256算法的設計思路。

一、運算定義

為了后續分析思路與流程的連貫性,在這里先統一聲明一下一些運算的定義,后續一些函數會直接對這些運算進行封裝使用。

1、右移Right Shift?(shr.rb)

這里的右移會產生兩種結果,第一種結果是左側移動完之后位為0,右側被移走的位丟失,如上圖所示SHR 32的操作,原數據為32位,在右移32位之后原數據都被右移丟失,剩下的左側移動完的位全為0。

2、旋轉右移Right Shift?(rotr.rb)

這里要尤其注意和SHR右移的區別,觀察演示圖可以發現對于旋轉右移而言數據組成了一個環形,移動位數只是改變位的絕對位置,并不會丟棄數據,所以原數據32位,再進行ROTR 32的操作實際上就是所有數據位旋轉了一整圈,又回到了原來的位置。

3、異或XOR (xor.rb)

按位異或,0^0 = 0,1^0 = 1,0^1 = 1,1^1 = 0。

4、加法Addition (add.rb)?

這里和二進制加法一樣,但是由于多個32位的數據相加,最終的存在著溢出的風險,因此最終的結果進行取模2*32將其約束在32位輸出。

二、函數定義

第一部分的運算被封裝組合起來就是這部分的函數,在這里先列出一些后續算法流程分析會用到的函數,讀者可以先有個大概印象,后面第三部分算法流程分析的時候再回看也可以。

前四個函數使用希臘符號 Sigma(小寫 σ,大寫 Σ)命名。這些名稱沒有特殊含義,只是為了方便給一些組合運算命名。

1、σ0 (sigma0.rb)

σ0(x) = ROTR7(x) ^ ROTR18(x) ^ SHR3(x)

先分別計算ROTR 7位和ROTR18位和SHR 3位,再將三者異或

2、σ1 (sigma1.rb)

σ1(x) = ROTR17(x) ^ ROTR19(x) ^ SHR10(x)

先分別計算ROTR 17位和ROTR 19位和SHR 10位,再將三者異或

3、Σ0 (usigma0.rb)

Σ0(x) = ROTR2(x) ^ ROTR13(x) ^ ROTR22(x)

先分別計算ROTR 2位和ROTR 13位和ROTR?22位,再將三者異或

4、Σ1 (usigma1.rb)?

Σ1(x) = ROTR6(x) ^ ROTR11(x) ^ ROTR25(x)

先分別計算ROTR 6位和ROTR 11位和ROTR?25位,再將三者異或

5、Choice (ch.rb)

這個函數使用x位在y位和z位之間進行選擇。如果x=1,則選擇y位;如果x=0,則選擇z位。

6、Majority (maj.rb)??

這個函數返回三位中的多數位。

7、常量Constants (constants.rb)

SHA-256 使用六十四個常量?Kt?來幫助在主哈希計算過程中混合比特。

首先計算前64個質數的立方根,然后取其小數部分乘2^32,將得到的常量作為Kt使用,其中t表示第t個質數運算后的結果。

這些立方根的小數部分是無理數(它們無限延伸),因此它們是用于常量的良好隨機比特選擇。這比使用特別選擇的常量更好,因為這降低了哈希函數被設計成具有后門的可能。

三、算法流程分析?

在這里message的內容是可以自己指定的,我們以message = dyq 為例(在每個rb文件的開頭可以自定義默認輸入)

1、message.rb?

輸入一個message字符串時,我們將每個字符轉換為 ASCII 表中的對應數字。這些數字被轉換為二進制,我們使用這些二進制數據作為哈希函數的輸入。?

2、padding.rb

SHA-256 哈希函數以 512 位的block數據塊為單位進行操作,因此所有消息都需要用零填充至最接近的 512 位的倍數,可以是512、1024等,這里先填充到448位,后64位預留出用來表示message的比特位數。

為了防止相似輸入哈希到相同的結果,我們用?1?位將消息與零分隔開,并在填充的最后 64 位中包含消息的大小。?

以上這種用?1?分隔消息并在填充中包含消息大小的方法被稱為 Merkle–Damg?rd 加強(MD 加強)。?

3、blocks.rb

消息經過填充后,我們將其切割成等長的 512 位消息塊?Mi?以便哈希函數處理。

每個消息塊也可以進一步分成 16 個詞Wj (?512 / 32 = 16 words?),每個詞的長度為32bit,這將在后續使用。?

4、schedule.rb

?對于前16個word,每個word有32個bit,相當于是把原本的block0分為了32*16。

從第17個word開始根據下面的公式進行計算

Wt = σ1(Wt-2) + Wt-7 + σ0(Wt-15) + Wt-16

其中σ1和σ0在第二部分可以找到函數的定義。

5、expansion.rb

這一步展示的是上面最后一個word W63生成的運算過程。?

6、initial.rb

初始哈希值使用了前八個質數的平方根的小數部分。我們將這八個字母作為狀態寄存器,我們可以將其作為開始哈希計算的起點(初始狀態)

7、t1.rb t2.rb

我們需要先使用狀態寄存器中的當前值來計算兩個新的臨時詞(?T1?和?T2?),為后續的壓縮過程做準備。

T1 = Σ1(e) + Ch(e, f, g) + h + Kt + Wt

其中Σ1和Ch函數在第二部分,h為h狀態寄存器存儲的值,Kt為第二部分的64個常數值,Wt為schedule.rb求得的word。

T2 = Σ0(a) + Maj(a, b, c)

其中Σ0函數和Maj函數均在第二部分。

8、compression.rb

壓縮是整個算法的核心。我們再將其細化進行分析

(1) step1:計算出T1和T2

?(2) step2:所有寄存器下移一個

?(3) step3:更新a和e寄存器的值

以上三步可以概括為計算T1,T2;下移寄存器;更新a和e值,至此我們稱為完成一輪壓縮。這樣的壓縮要對一共64個word都進行一遍。

以上就是第二輪的step1開始以此類推。?

壓縮完64輪之后,將最終的abcdefgh寄存器的值和initial.rb中的abcdefgh中的值相加得到最后的寄存器值

如果還有進一步要處理的消息塊(block1,block2……),按照下圖當前的哈希值將作為下一個壓縮的初始哈希值。?

9、final.rb

?最終將8個32位的寄存器值轉化為8個16進制的哈希值并拼接在一起,最終得到message的哈希值

?

使用哈希計算器驗證一下是沒問題的

10、sha256.rb?

# 直接進行哈希運算
ruby sha256.rb abc# 也可以輸出二進制和十六進制數據
ruby sha256.rb 0b01100001
ruby sha256.rb 0xaabbccdd# 哈希一個文件 (請注意,文件末尾將有一個換行符)
ruby sha256.rb file.txt# 添加不同的命令行參數
ruby sha256.rb abc normal # 默認
ruby sha256.rb abc fast   # 加速演示
ruby sha256.rb abc enter  # 每按一次回車,步進一次動畫

sha256.rb是一個集成上述功能的完整代碼,除此之外,還可以指定命令行參數實現不同操作。

將sha-256.rd的輸出改成可分為多個block的長message,測試多個block條件下hash算法?

觀察以上代碼運行后的結果發現,進行了多個block的流水線運算,最終的結果正確,真是太吊了。但是這里注意改變輸入時不能直接在命令行輸入段落,因為作者的代碼中不能識別空格,所以只能在rb文件里改變input,但是也無傷大雅,筆者有時間會完善一下這個小bug的。

本文來自互聯網用戶投稿,該文觀點僅代表作者本人,不代表本站立場。本站僅提供信息存儲空間服務,不擁有所有權,不承擔相關法律責任。
如若轉載,請注明出處:http://www.pswp.cn/bicheng/88293.shtml
繁體地址,請注明出處:http://hk.pswp.cn/bicheng/88293.shtml
英文地址,請注明出處:http://en.pswp.cn/bicheng/88293.shtml

如若內容造成侵權/違法違規/事實不符,請聯系多彩編程網進行投訴反饋email:809451989@qq.com,一經查實,立即刪除!

相關文章

C語言模塊化編程思維以及直流電機控制(第四天)

👨?💻個人主頁:開發者-削好皮的Pineapple! 👨?💻 hello 歡迎 點贊👍 收藏? 留言📝 加關注?! 👨?💻 本文由 削好皮的Pineapple! 原創 👨?&#x1f4…

【PTA】數據結構與算法0001:1025 反轉鏈表

文章大綱寫在前面測試用例ac代碼學習代碼知識點小結寫在前面 實現思路 結構體封裝數據 根據order重新排序k區間值迭代翻轉 n整除k,則最后地址輸出"-1"非整除,最后剩余區間,原序輸出。最后地址輸出"-1" 題目有難度&…

深入解析 .NET 泛型:從原理到實戰優化

在現代軟件開發中,代碼復用性和性能優化是開發者永恒的追求。.NET 泛型作為一項強大的語言特性,不僅能夠幫助我們消除重復代碼,還能顯著提升代碼的類型安全性和運行效率。本文將帶你全面了解 .NET 泛型,從基本概念到高級用法&…

Excel 處理軟件 內容復制工具:工作表批量復制 + 合并拆分簡潔操作零門檻

各位辦公小能手們!今天給你們介紹一款超牛的軟件——Excel內容復制工具。軟件下載地址安裝包 這可是專門為了讓Excel數據處理效率蹭蹭往上漲而設計的輔助軟件呢!它的主要功能可多啦,能批量復制工作表,還能把好多表格合并到同一個…

【機器學習實戰筆記 14】集成學習:XGBoost算法(一) 原理簡介與快速應用

《XGBoost算法》 推薦的學習路徑: 【快速實現XGBoost、跑通代碼】- 第一部分 【快速掌握XGBoost應用、達到自由調參水平】- 第一部分~第三部分 【快速掌握XGBoost原理、面試得以通關】- 第一部分1 第二部分1.2、2.2 第四部分 目錄《XGBoost算法》一 XGBoost的基…

.NET AI 模板

引言 隨著人工智能技術的快速發展,AI應用開發已成為開發者必備的技能之一。然而,對于許多.NET開發者來說,如何快速上手AI開發仍然是一個挑戰。微軟推出的.NET AI模板預覽版正是為了解決這一問題而生,為開發者提供了構建智能聊天應…

EFK9.0.3 windows搭建

背景 最近某個功能要使用到ELK(ElasticSearch、Logstash、Kibana)采集日志,對數據進行分析,網上百度了一下,目前推薦不使用Logstash而使用Filebeat ,即EFK。 下載鏈接 Elasticsearch Kibana Filebeat 安裝前提 …

上海新華醫院奉賢院區:以元宇宙技術重構未來醫療生態

引言:當醫療遇上元宇宙在數字化轉型的浪潮中,上海新華醫院奉賢院區以"智慧醫院"為定位,率先構建了"元宇宙醫院"雛形。通過AI大模型、三維影像分析、AR手術導航等前沿技術的深度融合,醫院正在打造一個覆蓋全周…

知識競賽答題pk小程序用戶操作手冊

知識競賽答題 PK 小程序用戶操作手冊 一、注冊與登錄 用戶首次使用答題pk小程序需上傳頭像,輸入昵稱,并選擇加入團隊。如果是企業內部人員使用可開啟白名單功能。二、進入答題 PK 模式 登錄后,在小程序首頁,您可以看到 “單人挑戰…

等大小譜聚類

聚類是一種將具有相似特征的數據點進行分組的方法。它廣泛應用于探索性數據分析,并已被證明在模式識別、市場和客戶細分、推薦系統、數據壓縮以及生物數據分析等許多應用中都發揮著重要作用。 盡管聚類算法種類繁多,但沒有一種能夠生成點數均衡的聚類。…

〔從零搭建〕數據湖平臺部署指南

🔥🔥 AllData大數據產品是可定義數據中臺,以數據平臺為底座,以數據中臺為橋梁,以機器學習平臺為中層框架,以大模型應用為上游產品,提供全鏈路數字化解決方案。 ?杭州奧零數據科技官網&#xff…

Java 導出pdf 寫出demo 1、需要設置自定義頁眉和文字 2、可以插入表格 3、可以插入圖片

以下是一個使用 iText 7 庫實現 PDF 導出的 Java 示例&#xff0c;包含自定義頁眉、文字、表格和圖片功能&#xff1a; 添加 Maven 依賴 <dependencies><!-- iText 7 Core --><dependency><groupId>com.itextpdf</groupId><artifactId>ite…

Ntfs!LfsReadRestart函數分析得到Ntfs!LFS_RESTART_PAGE_HEADER

第一部分&#xff1a;0: kd> p Ntfs!LfsPinOrMapData0x8c: f71797f6 ff15a40016f7 call dword ptr [Ntfs!_imp__CcPinRead (f71600a4)] 0: kd> t nt!CcPinRead: 80bf9a5a 6a2c push 2Ch 0: kd> kc# 00 nt!CcPinRead 01 Ntfs!LfsPinOrMapData 02 N…

skywalking-agent-docker鏡像

FROM centos:7.9.2009 USER root# 定義 Arthas 目錄環境變量 ENV ARTHAS_HOME/opt/arthas# 更改 YUM 源并清理緩存 RUN mv /etc/yum.repos.d/CentOS-Base.repo /etc/yum.repos.d/CentOS-Base.repo_bak && \rm -rf /etc/yum.repos.d/* && \curl -o /etc/yum.rep…

數據庫開發運維的集成:彌合開發與運維之間的鴻溝

在傳統的軟件開發工作流程中&#xff0c;數據庫變更往往是事后才考慮的問題。應用程序代碼遵循定義明確的開發運維實踐&#xff0c;包括版本控制、自動測試和持續部署&#xff0c;而數據庫變更則經常是由數據庫管理員手動執行的高風險操作。這種脫節造成了瓶頸&#xff0c;帶來…

PiscTrace應用:從 YOLO-Pose 到深蹲與引體向上計數:實時健身動作分析與實現

隨著健身行業的發展&#xff0c;越來越多的智能應用涌現&#xff0c;用于幫助健身者更好地記錄和分析運動情況。特別是在體能訓練中&#xff0c;俯臥撐和引體向上是兩個非常常見的動作&#xff0c;它們通常用來鍛煉上半身力量和耐力。為了使訓練更加科學和高效&#xff0c;實時…

【unity】webCanvas.enabled = false;和webCanvas.gameObject.SetActive(false);的優缺點比較

在 Unity 中&#xff0c;webCanvas.gameObject.SetActive(false) 和 webCanvas.enabled false 是兩種不同的隱藏 UI 的方式&#xff0c;它們的核心區別在于作用范圍和對組件狀態的影響。理解這些差異能幫助你避免初始化失敗、性能問題和邏輯錯誤。 1核心區別 gameObject.SetAc…

深入探索 pnpm:高效磁盤利用與靈活的包管理解決方案

引言 在現代 JavaScript 開發中&#xff0c;依賴管理效率直接影響開發體驗。傳統工具如 npm 和 yarn 在大型項目中常面臨磁盤冗余和性能瓶頸。pnpm&#xff08;Performant npm&#xff09;通過創新的硬鏈接和符號鏈接機制&#xff0c;解決了這些痛點。本文將深入解析 pnpm 的核…

Hive MetaStore的實現和優化

在大數據領域&#xff0c;數據管理與存儲至關重要&#xff0c;Hive MetaStore&#xff08;HMS&#xff09;作為 Hive 數據倉庫的核心組件&#xff0c;承擔著元數據管理的關鍵職責。隨著數據規模不斷膨脹&#xff0c;其性能與穩定性面臨挑戰。本文將深入剖析 HMS 的實現機制&…

一文讀懂動態規劃:多種經典問題和思路

一、動態規劃算法的思想與核心概念框架 1. 動態規劃的基本思想 動態規劃&#xff08;Dynamic Programming, DP&#xff09;是一種通過將復雜問題分解為重疊子問題&#xff0c;并利用子問題的解來高效解決原問題的方法。其核心思想是避免重復計算&#xff0c;通過存儲中間結果&a…