Ana içeriğe atla
Change page

Ethash

Ethash, Ethereum'un iş ispatı madencilik algoritmasıydı. İş ispatı artık tamamen devre dışı bırakıldı ve Ethereum artık bunun yerine hisse ispatı kullanılarak güvence altına alınıyor. Birleşim, hisse ispatı ve hisseleme hakkında daha fazlasını okuyun. Bu sayfa sadece tarihsel ilgi içindir!

Ethash, Dagger-Hashimoto algoritmasının değiştirilmiş bir versiyonudur. Ethash iş ispatı bellek ağırlıklıdır (opens in a new tab), bunun algoritmayı ASIC'e dayanıklı yaptığı düşünülüyordu. Sonunda Ethash ASICleri geliştirildi fakat GPU madenciliği iş ispatı durdurulana kadar hâlâ geçerli bir seçenekti. Ethash, Ethereum olmayan iş ispatı ağlarında hâlâ diğer paraların madenciliğini yapmak için kullanılmaktadır.

Ethash nasıl çalışır?

Bellek sertliği, nonce ve blok başlığına bağlı olarak sabit bir kaynağın alt kümelerinin seçilmesini gerektiren bir iş kanıtı algoritması ile elde edilir. Bu kaynağa (birkaç gigabayt boyutunda) DAG adı verilir. DAG, her 30000 blokta bir değiştirilir, bu devir olarak adlandırılan 125 saatlik bir penceredir (kabaca 5,2 gün) ve oluşturulması biraz zaman alır. DAG yalnızca blok yüksekliğine bağlı olduğundan, önceden oluşturulabilir, ancak böyle değilse, müşterinin bir blok oluşturmak için bu sürecin sonuna kadar beklemesi gerekir. İstemciler DAG'leri önceden oluşturup önbelleğe almazsa, ağ her bir dönem geçişinde büyük blok gecikmesi yaşayabilir. DAG'nin, hem düşük CPU hem de küçük bellek ile doğrulamaya izin veren iş kanıtının doğrulanması için oluşturulması gerekmediğini unutmayın.

Algoritmanın izlediği genel rota aşağıdaki gibidir:

  1. O noktaya kadar blok başlıklarının taranmasıyla her blok için hesaplanabilen bir tohum mevcuttur.
  2. Tohumdan 16 MB'lık bir sözde rastgele önbellek hesaplanabilir. Hafif istemciler önbelleği depolar.
  3. Önbellekten, her bir öğenin önbellekteki az sayıda öğeye bağlı olduğu 1 GB'lık bir veri kümesi oluşturabiliriz. Tam istemciler ve madenciler veri kümesini depolar. Veri kümesi, zamanla doğrusal olarak büyür.
  4. Madencilik, veri setinin rastgele dilimlerini alıp bunları bir araya getirmeyi içerir. Doğrulama, ihtiyacınız olan veri kümesinin belirli parçalarını yeniden oluşturmak için önbelleği kullanarak düşük bellekle yapılabilir, böylece yalnızca önbelleği saklamanız gerekir.

Büyük veri kümesi her 30000 blokta bir güncellenir, bu nedenle bir madencinin çabasının büyük çoğunluğu veri kümesini okumak olacak, değişiklik yapmak değil.

Tanımlar

Aşağıdaki tanımları kullanıyoruz:

'SHA3' kullanımı

Ethereum'un gelişimi, SHA3 standardının geliştirilmesiyle çakıştı ve standartlar süreci, sonlandırılmış karma algoritmanın dolgusunda geç bir değişiklik yaptı, böylece Ethereum'un "sha3_256" ve "sha3_512" karmaları standart sha3 karmaları değil, diğer bağlamlarda "Keccak-256" ve "Keccak-512" olarak genellikle atıfta bulunulan bir değişkendir. Tartışma için bkz. ör. burada (opens in a new tab), burada (opens in a new tab) veya burada (opens in a new tab).

Lütfen aşağıdaki algoritmanın açıklamasında "sha3" karmalarına atıfta bulunulduğunu unutmayın.

Parametreler

Ethash'in önbelleği ve veri kümesi parametreleri, blok numarasına bağlıdır. Önbellek boyutu ve veri kümesi boyutu doğrusal olarak büyür; bununla birlikte, döngüsel davranışa yol açan tesadüfi düzenlilik riskini azaltmak için her zaman doğrusal olarak büyüyen eşiğin altındaki en yüksek asal değeri alırız.

Veri kümesi ve önbellek boyutu değerleri tabloları ekte verilmiştir.

Önbellek oluşturma

Şimdi, bir önbellek üretme fonksiyonunu belirtiyoruz:

Önbellek üretim süreci, önce 32 MB belleğin sıralı olarak doldurulmasını ve ardından Sergio Demian Lerner'in Strict Memory Hard Hashing Functions (2014) (opens in a new tab) çalışmasındaki RandMemoHash algoritmasının iki geçişte çalıştırılmasını içerir. Çıktı, 524288 64 baytlık bir değer kümesidir.

Veri birleştirme işlevi

Bazı durumlarda, XOR'un birleşmeli olmayan bir alternatifi olarak FNV karmasından (opens in a new tab) esinlenen bir algoritma kullanırız. Asal değeri sırayla bir bayt (sekizli) ile çarpan FNV-1 spesifikasyonunun aksine, asal değeri tam 32 bit girişle çarptığımızı unutmayın.

FNV_PRIME = 0x01000193

def fnv(v1, v2):
    return ((v1 * FNV_PRIME) ^ v2) % 2**32

Lütfen sarı kağıdın fnv'yi v1*(FNV_PRIME ^ v2) olarak belirttiğine dikkat edin, tüm mevcut uygulamalar tutarlı bir şekilde yukarıdaki tanımı kullanır.

Tam veri kümesi hesaplaması

Tam 1 GB veri kümesindeki her 64 baytlık öğe aşağıdaki gibi hesaplanır:

Esasen, sözde rasgele seçilmiş 256 önbellek düğümünden gelen verileri birleştirir ve veri kümesi düğümünü hesaplamak için bunu kararız. Tüm veri kümesi daha sonra şu şekilde oluşturulur:

def calc_dataset(full_size, cache):
    return [calc_dataset_item(cache, i) for i in range(full_size // HASH_BYTES)]

Ana döngü

Şimdi, belirli bir başlık ve nonce için nihai değerimizi üretmek için tüm veri kümesinden verileri topladığımız ana "hashimoto" benzeri döngüyü belirtiyoruz. Aşağıdaki kodda header, mixHash ve nonce alanları hariç bir başlığın, yani kısaltılmış bir blok başlığının RLP gösteriminin SHA3-256 karmasını temsil eder. nonce, büyük endian düzenindeki 64 bitlik işaretsiz bir tam sayının sekiz baytıdır. Yani nonce[::-1] bu değerin sekiz baytlık küçük endian gösterimidir:

Esasen, 128 bayt genişliğinde bir "mix" tutarız ve tam veri kümesinden tekrar tekrar sıralı olarak 128 bayt alırız ve fnv işlevini kullanarak mix ile birleştiririz. 128 bayt sıralı erişim kullanılır, böylece algoritmanın her turu, her zaman RAM'den tam bir sayfa alır ve ASIC'lerin teorik olarak kaçınabileceği çeviriye bakılan arabellek kayıplarını en aza indirir.

Bu algoritmanın çıktısı istenen hedefin altındaysa nonce geçerlidir. Sondaki fazladan sha3_256 uygulamasının, en azından az miktarda iş yapıldığını kanıtlamak için sağlanabilecek bir ara nonce'nin var olmasını sağladığını unutmayın; bu hızlı dış PoW doğrulaması, DDoS karşıtı amaçlar için kullanılabilir. Ayrıca sonucun tarafsız, 256 bitlik bir sayı olduğuna dair istatistiksel güvence sağlamaya da hizmet eder.

Madencilik

Madencilik algoritması şu şekilde tanımlanır:

def mine(full_size, dataset, header, difficulty):
    # hedefi, aynı basamakta karma ile karşılaştırmak için sıfırla doldurun
    target = zpad(encode_int(2**256 // difficulty), 64)[::-1]
    from random import randint
    nonce = randint(0, 2**64)
    while hashimoto_full(full_size, dataset, header, nonce) > target:
        nonce = (nonce + 1) % 2**64
    return nonce

Tohum karmasını tanımlama

Belirli bir bloğun üzerinde madencilik yapmak için kullanılacak tohum karmasını hesaplamak için aşağıdaki algoritmayı kullanırız:

 def get_seedhash(block):
     s = '\x00' * 32
     for i in range(block.number // EPOCH_LENGTH):
         s = serialize_hash(sha3_256(s))
     return s

Sorunsuz madencilik ve doğrulama için, gelecekteki tohum karmalarını ve veri kümelerini ayrı bir iş parçacığında önceden hesaplamanızı öneririz.

Daha fazla kaynak

Size yardımcı olan bir topluluk kaynağı mı biliyorsunuz? Bu sayfayı düzenleyin ve onu ekleyin!

Ek

Yukarıdaki python spesifikasyonunu kod olarak çalıştırmakla ilgileniyorsanız, aşağıdaki kod, başa eklenmelidir.

Veri Boyutları

Aşağıdaki arama tabloları, yaklaşık 2048 veri ve önbellek boyutlu dönemleri sunar.

Sayfanın son güncellenme tarihi: 15 Nisan 2026

Bu makale faydalı oldu mu?