Điểm:0

Kết nối trong cây Merkle

lá cờ in

Hãy xem xét một Merkle Tree đơn giản với lá alice +100nhấp nhô +50. Sử dụng thuật toán băm SHA256, tóm tắt của các chuỗi tương ứng là:

# alice +100
dc2cac4a8aaeccc0199eeb77df68b22eaa6e319d3f2b425d078dbd73419e28ac

# bo +50
7e15e5bc1b84f458db7ced4df762ba70204f19e3a613738756f9b00653f0aee1

Là một hàm băm, SHA-256 mang tính xác định, vì vậy việc chúng ta triển khai hàm này trong ngôn ngữ lập trình nào không quan trọng. Để hoàn thiện, điều này có thể được thực hiện thông qua tiền điện tử-js thư viện:

const hash256 = (chuỗi) => {
  hằng số giá trị = 
  require('crypto').createHash('sha256').update(string).digest('hex');
  trả lại giá trị;
}

# áp dụng
hash256('alice +100')
# kết quả:
dc2cac4a8aaeccc0199eeb77df68b22eaa6e319d3f2b425d078dbd73419e28ac

Khi một người đề cập đến Thực hiện cây Merkle, người ta xem mô tả sau:

Cây băm là một cây gồm các giá trị băm trong đó các lá là giá trị băm của các khối dữ liệu trong một tệp hoặc tập hợp các tệp chẳng hạn. Các nút xa hơn trong cây là giá trị băm của các nút con tương ứng của chúng. Ví dụ: trong hình trên, hàm băm 0 là kết quả của phép băm nối hàm băm 0-0 và hàm băm 0-1. Nghĩa là, hàm băm 0 = hàm băm( hàm băm(0-0) + hàm băm(0-1) ) trong đó + biểu thị nối.

nhập mô tả hình ảnh ở đây

Tôi đã thấy các bản tóm tắt thư viện cấp cao hơn thực hiện phép nối này trong trường hợp Bộ đệm.concat(), nhưng tôi muốn biết chính xác cách thực hiện điều này từ quan điểm toán học thuần túy.

Người ta sẽ cho rằng (không chính xác):

alice_hash = hash256('alice +100')
bob_hash = hash256('bob +50')
# Sai lầm
hash256(alice_hash + bob_hash)
# cũng sai: thêm tiền tố 0x
băm256(
  '0xdc2cac4a8aaeccc0199eeb77df68b22eaa6e319d3f2b425d078dbd73419e28ac'
  + 
  '0x7e15e5bc1b84f458db7ced4df762ba70204f19e3a613738756f9b00653f0aee1' 
)

Vì vậy, nếu không có bất kỳ sự trừu tượng nào, làm thế nào một người có thể nối hai giá trị băm để có được nút cha kết quả?

Đối với bất kỳ ai đang cố gắng trợ giúp, giá trị chính xác của hash(hash(alice) + hash(bob)) phải là edf9a9a0e56b58fc9caccb97d85c628d5b9dc50cb94dfc41e83026d37704400f. Tôi đã thử thêm/xóa 0x tiền tố, thêm một ký tự khoảng trắng giữa chúng và không có nỗ lực nào trong số này có kết quả.Tôi cũng đã đọc các bài báo mà tôi có thể thực hiện được, nhưng chưa bao giờ đi xa hơn là "nối chúng để lấy giá trị cho nút cha" với rất ít tham chiếu triển khai.

kelalaka avatar
lá cờ in
Cả câu trả lời và bạn và nguồn của bạn đã quên sử dụng Cây Merkle đúng cách 0s 1s. [Xem trong câu trả lời này](https://crypto.stackexchange.com/a/71313/18298)
Morrolan avatar
lá cờ ng
Để giải thích ý nghĩa của @kelalaka muốn truyền đạt - việc triển khai cây Merkle đúng cách thường sẽ thêm một mã định danh *ở đâu trong cây* phần tử được băm vào dữ liệu được băm. Điều này giúp ngăn chặn một số loại tấn công. Có nhiều cách khác nhau để làm điều này. Một cái được nhìn thấy trong câu trả lời được liên kết, một cái khác trong [RFC 6962](https://www.rfc-editor.org/rfc/rfc6962.html#section-2.1) nơi chúng chỉ đơn giản là phân biệt giữa các nút lá và không phải lá.
onlyphantom avatar
lá cờ in
Tôi hiểu và thực sự đánh giá cao phản hồi và liên kết ở đây.Tôi bỏ qua các chi tiết khác để tập trung vào phần "ghép nối". Nhưng sau câu trả lời của bạn @Morrolan, tôi đã có thể tìm ra nó và triển khai nó một cách chính xác trong python. Bài học rút ra là xem chuỗi thập lục phân chỉ là một đại diện. Thay vào đó, hãy thực hiện dấu + trên chuỗi nhị phân. Cảm ơn vì câu trả lời!
Điểm:1
lá cờ ng

Vấn đề hiện tại bắt nguồn từ việc trộn lẫn biểu diễn chuỗi thập lục phân ('hexdigest') của giá trị băm với giá trị nhị phân thực của nó.

Trước tiên, hãy nhớ lại rằng một hàm băm lấy một chuỗi bit có độ dài tùy ý (cho các mục đích thực tế) làm đầu vào và xuất ra một chuỗi bit có độ dài cố định. Đó là, nó hoạt động trên nhị phân các giá trị.

Như vậy, giá trị băm thực tế của chuỗi đầu vào (được mã hóa ASCII) alice +100 là một chuỗi 32 byte. dc2cac4a8aaeccc0199eeb77df68b22eaa6e319d3f2b425d078dbd73419e28ac chuỗi byte đó được biểu diễn dưới dạng 'hexdigest', trong đó mỗi hai ký tự thập lục phân mã hóa một byte.

Đối với thao tác nối, bạn phải nối các chuỗi byte, thay vì các chuỗi hexdigest của chúng.

Một ví dụ trong Ruby:

yêu cầu 'tiêu hóa'

m1 = 'alice +100'
m2 = 'bob +50'

d1 = Thông báo::SHA256.new
d2 = Thông báo::SHA256.new

d1 << m1
d2 << m2

đặt "Alice hexdigest: #{ d1.hexdigest }"
đặt "Bob hexdigest: #{ d2.hexdigest }"

d3 = Thông báo::SHA256.new
d3 << d1.digest
d3 << d2.digest                                                                                                                                                

đặt "Nối hexdigest: #{ d3.hexdigest }"

Sẽ mang lại, khi thực hiện:

Alice hexdigest: dc2cac4a8aaeccc0199eeb77df68b22eaa6e319d3f2b425d078dbd73419e28ac
Bob hexdigest: 7e15e5bc1b84f458db7ced4df762ba70204f19e3a613738756f9b00653f0aee1
Nối hexdigest: edf9a9a0e56b58fc9caccb97d85c628d5b9dc50cb94dfc41e83026d37704400f

Trong ví dụ của bạn, khi bạn tính hàm băm của phép nối hai chuỗi hexdigest, ngôn ngữ lập trình của bạn sẽ nối hai chuỗi này, mã hóa chúng thành một chuỗi nhị phân (sử dụng bất kỳ mã hóa ký tự nào mà nó mặc định) và băm chuỗi đầu vào đó.

Đăng câu trả lời

Hầu hết mọi người không hiểu rằng việc đặt nhiều câu hỏi sẽ mở ra cơ hội học hỏi và cải thiện mối quan hệ giữa các cá nhân. Ví dụ, trong các nghiên cứu của Alison, mặc dù mọi người có thể nhớ chính xác có bao nhiêu câu hỏi đã được đặt ra trong các cuộc trò chuyện của họ, nhưng họ không trực giác nhận ra mối liên hệ giữa câu hỏi và sự yêu thích. Qua bốn nghiên cứu, trong đó những người tham gia tự tham gia vào các cuộc trò chuyện hoặc đọc bản ghi lại các cuộc trò chuyện của người khác, mọi người có xu hướng không nhận ra rằng việc đặt câu hỏi sẽ ảnh hưởng—hoặc đã ảnh hưởng—mức độ thân thiện giữa những người đối thoại.