BUUCTF 雞藕椒鹽味 wp 海明校驗碼
根據題目,查到海明校驗碼,也是之前沒有接觸到的知識,所以在這裡整理以下,也供大家參考。
題目:公司食堂最新出了一種小吃,叫雞藕椒鹽味漢堡,售價八塊錢,為了促銷,上面有一個驗證碼,輸入後可以再換取一個漢堡。但是問題是每個驗證碼幾乎都有錯誤,而且列印的時候倒了一下。小明買到了一個漢堡,準備還原驗證碼,因為一個吃不飽啊驗證碼如下:1100 1010 0000 ,而且列印的時候倒了一下。把答案雜湊一下就可以提交了(答案為正確值(不包括數字之間的空格)的32位md5值的小寫形式)
1.分析校驗位數
從題目可知驗證碼為110010100000共12位,校驗位一般都是在2^n的位置,所以共有4位校驗碼在1,2,4,8位置
拓展:海明驗證碼公式:2^r≥k+r+1 (r為校驗位 ,k為資訊位),如本驗證碼本來有8位資訊碼,帶入公式可得r=4,所以在1,2,4,8位置新增相應校驗碼
2.畫表
題目中提到列印的時候倒了一下,所以將資訊位倒著填入表中
1 | 2 | 3 | 4 | 5 | 6 | 7 | 8 | 9 | 10 | 11 | 12 | 位數 |
0 | 0 | 1 | 0 | 0 | 0 | 1 | 1 | 資訊位(D) | ||||
R1 | R2 | R3 | R4 | 校驗位(R) |
3.求校驗位的值
例如:1由第一位R1來校驗;2由第二位R2來校驗;由於3=1+2(1和2指的是位數,都是2的n次方)所以3由第一位R1和第二位R2校驗,4由第四位R3校驗,5和3道理是一樣的,5=1+4(2^0+2^2);6=2+4;7=1+2+4,依次類推。得出下表:
海明碼位號 | 佔用的校驗位號 | 校驗位 |
1 | 1 | R1 |
2 | 2 | R2 |
3 | 1、2 | R1、R2 |
4 | 4 | R3 |
5 | 1、4 | R1、R3 |
6 | 2、4 | R2、R3 |
7 | 1、2、4 | R1、R2、R3 |
8 | 8 | R4 |
9 | 1、8 | R1、R4 |
10 | 2、8 | R2、R4 |
11 | 1、2、8 | R1、R2、R4 |
12 | 4、8 | R3、R4 |
進行彙總,看每個校驗位都確定了哪一位。
R1:1、3、5、7、9、11
R2:2、3、6、7、10、11
R3:4、5、6、7、12
R4:9、10、11、12
最後用異或運算求出R1、R2、R3、R4、R5的值(以R1為例):
R1=D1⊕D3⊕D5⊕D7⊕D9⊕D11=1
以此類推:R1=1,R2=0,R3=0,R4=0
可以看到P1P2P3P4=0001,R1R2R3R4=1000
可以求得監督位(異或):
0 | 0 | 0 | 1 | 驗證碼中的校驗碼 |
1 | 0 | 0 | 0 | 求得的校驗碼 |
1 | 0 | 0 | 1 | 監督位 |
監督位不為0000,說明接收方生成的校驗位和收到的校驗位不同,錯誤的位數是監督位的十進位制即9,所以把D9就是題目中提到的錯誤,得到正確驗證碼110110100000,然後根據提示MD5hash一下就出來了。
1 import hashlib 2 c="110110100000" 3 md=hashlib.md5() 4 md.update(c.encode("utf8")) 5 flag = md.hexdigest() 6 print(flag) 7 8 #d14084c7ceca6359eaac6df3c234dd3b
套入flag{}即可得到答案flag{d14084c7ceca6359eaac6df3c234dd3b}