Rand Protocol
الوثائق
برامج RISC-V

مترجم Solana

يترجم sbpf2rv برنامج Solana بصيغة sBPF إلى مجموعة تعليمات RISC-V الخاصة بـ Rand - ما هو، ونموذج الثقة وحارس ELF فيه، وما الذي يؤدي إلى الاعتراض (trap) وما الذي يُرفض، والأرقام المقيسة، وشرح تطبيقي كامل يترجم برنامج SPL Token الحقيقي ويطابق مفسِّر sBPF كلمةً بكلمة.

يأخذ sbpf2rv برنامج Solana مُجمَّعًا (ملف ELF بصيغة sBPF، أي ملف .so الذي ينتجه cargo build-sbf) ويحوّله إلى برنامج Rand. يكتب شيفرة C، ثم يجمّعها rand-guest build إلى صورة RV32IM. تنشر هذه الصورة كلمات المخرجات الثماني نفسها التي ينشرها ضيف مفسِّر sBPF في Rand، وهو sbpf.bin، لملف ELF نفسه وللتعليمة نفسها. تعرض هذه الصفحة المسار كاملًا على برنامج SPL Token الحقيقي.

ما هو

المدخلملف ELF بصيغة sBPF v1
المخرجحزمة C وسيطة (shim crate)؛ يحوّلها rand-guest build إلى حاوية صورة
مكان التشغيلخارج السلسلة، على جهاز المطوّر؛ ولا ترى السلسلة سوى الصورة
ما يجب أن يطابقهكلمات المخرجات الثماني في sbpf.bin، على شريطَي المدخلات نفسيهما
المستودعsbpf2rv/ في مستودع الدوائر (circuits)
سلسلة الأدوات المثبّتةRust 1.98.1 وclang 23.1.1 وحزمة cc الإصدار 1.4.6

يحتفظ البرنامج المترجَم بواجهة ABI الخاصة بالمفسِّر. فهو يقرأ الشريطين نفسيهما: ملف ELF على الشريط العام، والتعليمة المسلسلة (الحسابات ثم بيانات التعليمة) على الشريط الخاص. ويشغّل حول البرنامج حزمة sbpf-core نفسها: فيفكّ ترميز المدخلات، ويحمّل ملف ELF، ويتحقق من منطقة الحسابات، ويحسب تجزئة المدخلات والمخرجات. ولا يُستبدل سوى تنفيذ sBPF نفسه بشيفرة أصلية. ولذلك تساوي مخرجاته مخرجات المفسِّر كلمةً بكلمة.

نموذج الثقة

ثلاثة أمور تربط إثباتَ البرنامج المترجَم.

  1. يربط hc الشيفرة المترجَمة. تُجمَّع شيفرة C داخل الصورة، فيشملها hc الخاص بالصورة.
  2. يربط حارس ELF قيمة hc ببرنامج واحد. تحمّل الحزمة الوسيطة البرنامج من ملف ELF الموجود على الشريط، ومن دون فحص يمكن لصورة واحدة أن تشغّل ملف ELF آخر يختاره المستدعي تحت hc نفسه. لذلك ينتهي ملف program.c المولَّد بملخّص للبرنامج المحمَّل الذي تُرجم منه: النص (text)، والبيانات للقراءة فقط، وعناوينهما، ونقطة الدخول. وقبل تشغيل أي شيء، تحسب الحزمة تجزئة البرنامج المحمَّل من الشريط بالطريقة نفسها (Poseidon2) وتقارنها. ويتوقف أي برنامج آخر بالخطأ BadElf وبالحالة 2، فوق الحالة السابقة. فالإثبات الذي يتحقق مقابل هذا hc هو تشغيل لذلك البرنامج.
  3. يربط H_PUB بايتات ملف ELF. يسافر ملف ELF على الشريط العام، ويغطيه ملخّص المدخلات العامة للإثبات كلمةً بكلمة.

يُتحقق من كون hc ترجمةً أمينة لملف ELF معيّن بإعادة البناء. شغّل sbpf2rv المثبّت على ملف ELF، وابنِ بسلسلة الأدوات المثبّتة، وقارن قيمة hc. ولهذا السبب فإن البناء قابل لإعادة الإنتاج.

لا تسجّل السلسلة ملف ELF المصدر ولا تجزئته. إنها تخزّن الصورة ومعرّف برنامجها. ومن يريد أن يكون ملف ELF معروفًا فعليه أن ينشره بجانب البرنامج.

يربط الحارس البرنامج المحمَّل لا الملف. فملفا ELF يختلفان فقط في مواضع لا يطّلع عليها المحمِّل (حشو الترويسة، وجداول الرموز) يُحمَّلان إلى البرنامج نفسه ويعملان بالتطابق في الطرفين. أما ملف ELF يختلف ببايت واحد في .rodata، حتى لو لم تقرأه عملية التحويل قط، فترفضه الترجمة ويشغّله المفسِّر.

ما الذي يُنتج فخًا (trap) وما الذي يُرفض

لا شيء يُرفض عند الترجمة. يُرفض ملف ELF مشوّه برسالة المحمِّل نفسه، لكن لا تُرفض أي تعليمة في ملف ELF سليم البنية. يُبلغ الماسح عمّا قد يصادفه البرنامج في صورة تحذيرات، ويقع في البرنامج المترجَم فخٌّ وقت التشغيل في الموضع نفسه تمامًا الذي يقع فيه في المفسِّر:

التحذيرما هووقت التشغيل
UnknownSyscallتجزئة استدعاء نظام لا ينفّذها وقت التشغيلفخّ UnknownSyscall
Cpiاستدعاء بين البرامج (sol_invoke_signed*)فخّ UnknownSyscall نفسه؛ فاستدعاء CPI غير منفَّذ
RegisterOutOfRangeسجلّ من r11..r15، أو سجلّ callx أعلى من r10فخّ BadInsn
UnknownOpcodeرمز عملية لا فئة له في v1، ومنه عائلة sdiv/srem الخاصة بـ v2 فقط وhor64فخّ BadInsn
JumpOutOfTextقفزة أو استدعاء أو سقوط إلى ما بعد نص الدالةفخّ BadJump
BadCallImmSrcتعليمة call imm مع src في 2..=10 (في ملفات ELF المبنية يدويًا فقط)فخّ BadInsn

المترجِم الذي يرفض الشيفرة التي لا يُصل إليها كان سيرفض برامج يشغّلها المفسِّر اليوم. وبرنامج SPL Token منها: فهو يستدعي sol_set_return_data وsol_get_sysvar، ولا يبلغهما مسار Transfer.

ثلاثة اختلافات مقبولة. كل منها لا يجعل الترجمة إلا تتوقف حيث قد لا يتوقف المفسِّر؛ ولا تُكمل الترجمة أبدًا تشغيلًا يتوقف فيه المفسِّر.

  1. تعليمة callx خارج المجموعة الممسوحة تُنتج فخّ BadJump، بينما قد يشغّل المفسِّر شيفرة حقيقية في ذلك العنوان.
  2. قد تتأجل فحوص الميزانية كتلة أساسية واحدة. ولكي يتسع SPL Token تحت سقف 65,535 كلمة، تتخطى 1,505 كتلة من كتله البالغة 3,546 فحص حد التعليمات الخاص بها. وقد يختلف نوع التوقف داخل الكتلة الواحدة التي تتجاوز الحد. أما الحالة والكلمات الثماني فهي نفسها.
  3. لا يعمل سوى البرنامج المصدر. يُرفض أي ملف ELF آخر (الحارس، أعلاه).

Ed25519 وsecp256k1. توجد تنفيذات برمجية لـ sol_ed25519_verify وsol_secp256k1_recover في sbpf-rt/ لكنها غير مربوطة. يقع المفسِّر في فخّ عند كليهما، فتقع الترجمة في فخّ أيضًا حفاظًا على التطابق. وتكلّف كل استدعاء نحو 14.3M و15.7M دورة على التوالي، وهذا أعلى بكثير من أكبر فئة (2²⁰). وهما تحتاجان إلى جداول المعالج المساعد.

الأرقام

قِيست على SPL Token (guests-compiled/sbpf/programs/spl_token.so، وهو ملف الاختبار الخاص بالمفسِّر)، مع تفعيل حارس ELF.

الصورةكلمات البرنامجالسقفhc
SPL Token، مترجَم65,09665,535 (439 فائضة)8ca905ae…758b
sbpf.bin، المفسِّر8,31765,535059a7086…f476
المتجهالحالةتعليمات sBPFالدورات المترجَمةدورات sbpf.binالفئة (كلتاهما)
Transfer 2501143765,851694,49820
Transfer أكثر من الرصيد0133748,836679,81420
MintTo 2501120708,648634,42320
MintTo بسلطة خاطئة0134696,694627,24120
Burn 2501131710,245637,03820
Burn أكثر من الرصيد0121695,434624,78120
Transfer بحسابين069645,015569,65620
حسابات أكثر من اللازم (الحزمة ترفض)20303,933304,61620

أين تذهب الدورات في Transfer:

المرحلةالمترجَمsbpf.bin
قراءة الشريطين302,881302,880
تحميل ملف ELF177,012173,859
التحقق من منطقة الحسابات103,829103,824
تصفير مكدس sBPF وكومته49,18149,181
تجزئتا المخرجات والمدخلات، والكلمات العامة، والشيفرة اللاصقة51,09142,723
حارس ELF72,949—
برنامج sBPF نفسه8,90822,031
المجموع765,851694,498

تنفيذ البرنامج المترجَم نفسه أرخص بنحو 2.4 إلى 2.5 مرة لكل تعليمة sBPF (نحو 62 دورة مقابل 154). لكن نحو 98% من كل تشغيل هو الحزمة الثابتة، ويضيف الحارس 73k دورة. لذا فإن الصورة المترجَمة لبرنامج SPL Token أغلى بما بين 69k و75k دورة، وتبقى كلتاهما في الفئة 20.

لا تُجدي الترجمة إلا في البرامج كثيفة الحساب. فبتوفير نحو 90 دورة لكل تعليمة، يوفّر استدعاء ينفّذ 10,000 تعليمة sBPF نحو 0.9M دورة. أما SPL Token فينفّذ بين 120 و143.

الإرشاد التطبيقي: SPL Token، مترجَمًا ومطابَقًا

يُشغَّل كل أمر من جذر نسخة من مستودع الدوائر عند 7ef3220، مع سلسلة الأدوات من نشر برنامج Rust وclang 23.1.1 من نشر برنامج RISC-V. يُقتطع المخرج الطويل حيث يوجد ….

0. بناء الأدوات

(cd sbpf2rv && cargo +1.98.1 build --release)
(cd rand-guest && cargo +1.98.1 build --release)

1. الترجمة

يجب أن يكون --out دليلًا داخل نسخة مستودع الدوائر.

$ sbpf2rv/target/release/sbpf2rv guests-compiled/sbpf/programs/spl_token.so --out sbpf2rv/target/spl-token --name spl-token
entry pc 225: 30 function(s), 3546 block(s), 12061 instruction(s), 30 callx target(s), 0 refusal(s), 4 warning(s)
  fn 225: 2065 block(s)
  …                                                (30 functions in all)
  warning: UnknownSyscall { pc: 7803, hash: 2720453611 }
  warning: UnknownSyscall { pc: 9530, hash: 2720453611 }
  warning: UnknownSyscall { pc: 8698, hash: 2720453611 }
  warning: UnknownSyscall { pc: 11547, hash: 331461893 }
wrote sbpf2rv/target/spl-token/program.c (521757 bytes of C) and the spl-token shim crate: rand-guest build sbpf2rv/target/spl-token

0 refusal(s). التحذيرات الأربعة هي استدعاءات نظام حقيقية لا يبلغها Transfer قط: التجزئة 2720453611 هي sol_set_return_data (ثلاثة مواضع استدعاء) و331461893 هي sol_get_sysvar.

2. بناء الصورة

الصورة أكبر من سقف الكلمات الافتراضي البالغ 4,096، فمرِّر --max-words 65535.

$ rand-guest/target/release/rand-guest build sbpf2rv/target/spl-token --max-words 65535
…
65096 words against a cap of 65535 (fits); 2 ecall(s) with a non-static a7
OK
wrote sbpf2rv/target/spl-token/image.bin and its .sha256 (65096 words, hc 8ca905ae3c62f503de7de86829040f323e098b53dba5fffe09b42f1aad16758b, program id 65d234ce9ca4d082f487c038abfa76e67f41a0d91e10b9ac388f1e1541d59184)

$ rand-guest/target/release/rand-guest info sbpf2rv/target/spl-token/image.bin
form: image container
text 64819 words at 0x10000; data 102 words (101 non-zero) at 0x4f4cc; prologue 277 words; program 65096 words from base_pc 0xfbac
hc 8ca905ae3c62f503de7de86829040f323e098b53dba5fffe09b42f1aad16758b
program id 65d234ce9ca4d082f487c038abfa76e67f41a0d91e10b9ac388f1e1541d59184
65096 words against a cap of 4096: does not fit

كل من ينفّذ هاتين الخطوتين بسلسلة الأدوات نفسها يحصل على قيمة hc هذه.

3. تشغيل الاثنين والمقارنة

تأخذ عملية Transfer بمقدار 250 قائمتين من الكلمات، يبنيهما tests/parity.rs من ترميز الاستدعاء الخاص بالمفسِّر نفسه: 27,151 كلمة عامة (ملف ELF مرمَّزًا إلى كلمات) و10,458 كلمة خاصة (الحسابات، ثم معرّف Transfer والمبلغ). يأخذهما rand-guest run عبر --public و--input. مختصرتين إلى أول كلمات كل قائمة:

$ rand-guest run sbpf2rv/target/spl-token/image.bin \
    --public 108600 1179403647 65794 0 0 17235971 1 2088 …   (27 151 words)
    --input  41825 4 0 65791 0 50529027 50529027 50529027 …  (10 458 words)
out[0] = 1
out[1] = 2892832079
out[2] = 376091303
out[3] = 1311040261
out[4] = 2015764099
out[5] = 3682593600
out[6] = 3311553006
out[7] = 141115266
cycles 765851
tier 20

القائمتان نفسهما مقابل ضيف المفسِّر:

$ rand-guest run guests-compiled/bin/sbpf.bin \
    --public 108600 1179403647 65794 0 0 17235971 1 2088 …   (27 151 words)
    --input  41825 4 0 65791 0 50529027 50529027 50529027 …  (10 458 words)
out[0] = 1
out[1] = 2892832079
out[2] = 376091303
out[3] = 1311040261
out[4] = 2015764099
out[5] = 3682593600
out[6] = 3311553006
out[7] = 141115266
cycles 694498
tier 20

الكلمات الثماني متطابقة جميعها. out[0] = 1 هي الحالة (نجاح). وout[1..8] هي الملخّص الذي تعرّفه واجهة ABI الخاصة بالمفسِّر على المدخلات والمخرجات.

4. فحص المتجهات الثمانية بأمر واحد

يبني اختبار التكافؤ الصورة المترجَمة، ويشغّل كل متجه عبر rand-guest run على الصورتين، ويفشل عند أي فرق في الكلمات الثماني:

$ cd sbpf2rv && cargo +1.98.1 test --test parity the_spl_token -- --nocapture
…
translated SPL Token: 65096 program words (cap 65 535), hc 8ca905ae3c62f503de7de86829040f323e098b53dba5fffe09b42f1aad16758b
transfer 250: Ok(0), status 1; cycles translated 765851, interpreter guest 694498
transfer too much: Ok(1), status 0; cycles translated 748836, interpreter guest 679814
MintTo 250: Ok(0), status 1; cycles translated 708648, interpreter guest 634423
MintTo 250 signed by someone else: Ok(4), status 0; cycles translated 696694, interpreter guest 627241
Burn 250: Ok(0), status 1; cycles translated 710245, interpreter guest 637038
Burn 1 000 001 (balance 1 000 000): Ok(1), status 0; cycles translated 695434, interpreter guest 624781
transfer with two accounts: Ok(47244640256), status 0; cycles translated 645015, interpreter guest 569656
an account count above MAX_ACCOUNTS: Err(BadElf), status 2; cycles translated 303933, interpreter guest 304616
…
test the_spl_token_transfer_translates_and_matches_the_interpreter_word_for_word ... ok

test result: ok. 1 passed; 0 failed; 0 ignored; 0 measured; 8 filtered out; finished in 27.84s

5. النشر

rand program deploy sbpf2rv/target/spl-token/image.bin --public spl_token.so

تقرأ الصورة ملف ELF من الشريط العام، ولذلك يكون ELF هو المُدخل العام للبرنامج، ويثبت عند النشر. يأخذ الخيار --public ملف .so نفسه، وتُرمّز المحفظة كلماته إلى 27,151 كلمة نفسها الواردة في الخطوة 4.

يتطلب هذا سلسلة يضبط genesis فيها max_program_words على 65,096 على الأقل، وmax_program_public_words على 27,151 على الأقل. كانت السلسلة 12 تحدّ النشر بـ 4,096 كلمة ولا تقبل مُدخلًا عامًا، فرفضت المحفظة هذه الصورة عليها قبل أي إثبات. ضبطت السلسلة 13، وهي سلسلة الإصدار v0.4، القيمتين على 65,535 و32,768، وتحتفظ بهما كل سلسلة جاءت بعدها. أما السلسلة 20، وهي السلسلة الحية (genesis 6210cf071a390d7ac61d8cbea5dd9d139d1a493a862b54a45a498f36af2d5135)، فتحتفظ كذلك بحدود الكتلة وحدود غلاف الاستدعاء كما في السلسلة 13، وتخفض سقف الإثبات إلى النصف، أي 4 MiB (4,194,304 بايت، منذ السلسلة 17؛ وضعت السلاسل من 13 إلى 16 السقف عند 8 MiB). ولم تعد حدود الحجم هي العقبة الوحيدة. يضبط genesis السلسلة 20 الخيار hardening_v6، وبموجبه يكون نشر عدد من كلمات البرنامج يفوق ما يتسع له الاستدعاء عند سقف استدعاء المستوى 14 نشرًا غير صالح (ProgramUncallable): الحد الأقصى 8,180 كلمة دون مُدخل عام، وأقل من ذلك إذا رافقه مُدخل عام. تبلغ هذه الصورة 65,096 كلمة إلى جانب مُدخل عام من 27,151 كلمة، فترفض السلسلة 20 نشرها، وسترفض استدعاءها أيضًا: يعمل كل متجه من متجهات SPL عند المستوى 20، وهو أعلى من سقف استدعاء المستوى 14 (الحدود). تجميع الكتل معطّل في السلسلة 20 (لا يتضمن genesis فيها قسم aggregation)؛ وتُذكر عقد الإقلاع فيها في تشغيل مدقّق. تحتسب رسوم النشر الكلمات العامة مع كلمات الشيفرة: 0.001 + 0.0001 × (65,096 + 27,151) = 9.2257 RAND، وهي الرسوم التي دفعها النشر على السلسلة 13 أدناه.

جرى هذا النشر على السلسلة 13 في 2026-09-19، حين كانت السلسلة 13 هي السلسلة الحية (ملف FRI الإنتاجي، genesis 8123ccac1883a45750e4df6964fb7cd3f0b321798cde4c0ef406a0293939ece3)، من محفظة genesis المسماة shielded-1. أُنشئت كل سلسلة بعدها (من 14 إلى 19) سلسلةً جديدة دون برامج السلسلة 13، ولم تُعَد نشر الصورة على أي منها، فالمعاملة والارتفاع المذكوران أدناه يعودان إلى السلسلة 13 ولم يعودا يُحلّان في المستكشف. يُشتق معرّف البرنامج بتجزئة base_pc والكلمات والكلمات العامة وحدها، فتحصل الصورة نفسها وELF نفسه على المعرّف نفسه في أي سلسلة تقبل النشر. مخرجات المحفظة، مع حذف أسطر التقدّم (…):

$ rand program deploy <image.bin> --public spl_token.so
program id: 740236918310f8e52bb0c1ef49b2b0e0c018762e289666660685b0694c8dd00a (65096 words, hc ae05a98c03f5623c68e87dde320f0429538b093efeffa5db1a2fb4098b7516ad, public input 27151 words, digest ec57b10ed6f3a3d5fe87ec072f691322ad747377ba2f0a1788bcfe3e7334d67e)
…
proved in 94.3s: tier 14, 1418406 bytes
submitted deploy 626fc9387ecc1f6b39f44184807303ac2843029d8fb8e28338bf186445927530
…
معرّف البرنامج740236918310f8e52bb0c1ef49b2b0e0c018762e289666660685b0694c8dd00a
الصورة65,096 كلمة؛ hc 8ca905ae… بصيغة rand-guest، وae05a98c… بصيغة المحفظة
المُدخل العام27,151 كلمة (ELF)، الملخّص ec57b10ed6f3a3d5fe87ec072f691322ad747377ba2f0a1788bcfe3e7334d67e
حزمة الرسوم (حزمة السلسلة 13 بدخلين وخرجين)المستوى 14، 1,418,406 بايت، أُثبتت في 94.3 s
معاملة النشر (السلسلة 13)626fc9387ecc1f6b39f44184807303ac2843029d8fb8e28338bf186445927530
ثُبّتت عند الارتفاع (السلسلة 13)400
الرسوم9.2257 RAND

منذ السلسلة 14 صارت الحزمة الدافعة هي حزمة الأصول المخفية الواحدة بأربعة مدخلات وأربعة مخرجات التي تحملها كل معاملة، وتُثبت مقابل ارتباط المعاملة. وما زالت عند المستوى 14: نحو 100 s ونحو 1.42 MB عند الملف الإنتاجي على السلسلتين 14 و15. ومنذ السلسلة 17 تحمل الحزمة أيضًا إثبات تفويض من المستوى 10 (تفويض مجزّأ)، فعلى السلسلتين 18 و19 تبلغ حزمة الرسوم في المعاملة نحو 1.49 MB من إثبات الحزمة ونحو 1.37 MB من إثبات التفويض.

يرتبط معرّف البرنامج بـ ELF، فيختلف عن المعرّف الذي يطبعه rand-guest info للصورة المجرّدة. استدعِ المعرّف الذي طبعه deploy.

الحدود

  • لم يُثبت أي استدعاء للبرنامج، وهو غير منشور على السلسلة 20، وترفض السلسلة 20 النشر والاستدعاء كليهما. جرى النشر أعلاه على السلسلة 13. وبموجب hardening_v6 في السلسلة 20، يكون نشر عدد من الكلمات يفوق ما يتسع له استدعاء من المستوى 14 نشرًا غير صالح (ProgramUncallable؛ 8,180 كلمة على الأكثر)، وتبلغ الصورة 65,096. أما جانب المُدخلات فيتسع: ELF هو المُدخل العام للنشر، ويجلبه rand call بنفسه، وتتسع الكلمات الخاصة البالغة 10,458 لسقف المُدخلات البالغ 16,071 الذي تحتفظ به السلسلة 20. لكن كل متجه من متجهات SPL من المستوى 20، ومنذ fullnode v0.5.6 (2026-09-25) ترفض العقدة أي إثبات استدعاء أعلى من المستوى 14 (CallTierTooHigh)، قبل أن تبني مفتاح المُحقِّق. ويحدّ الفحص نفسه جداول التجزئة التي يجوز للاستدعاء أن يعلنها: 2¹³ صفًا لـ SHA-256 (128 عملية ضغط) و2¹² صفًا لـ Keccak (128 تبديلًا). لا يمكن إثبات استدعاء من المستوى 20 إلا خارج السلسلة، ولا يوجد حتى الآن إثبات من المستوى 20 (النقطة التالية).
  • لم يُنتَج بعد أي إثبات عند المستوى 20. أُنهي إثبات من المستوى 20 قسرًا على حاسوب محمول بذاكرة 48 GB عند نحو 31 GB، وقتله نظام التشغيل لنفاد الذاكرة على droplet بذاكرة 64 GB عند 65.1 GB بعد 10 m 41 s. وبالاستقراء من قياسات التدرّج بين المستويين 16 و18 (الذاكرة نحو ×3.9 والزمن نحو ×4.1 لكل +2 مستوى)، يحتاج المستوى 20 إلى نحو 330 GB ونحو 3.6 h، وهو أكثر من أكبر droplet ذاكرةً لدى DigitalOcean (m-32vcpu-256gb، بذاكرة 256 GB). وعمل المُثبِت بخيط واحد: بقي جهاز بـ 16 vCPU عند 99% من نواة واحدة. انظر ذاكرة الإثبات.
  • لا CPI. تؤدي الاستدعاءات بين البرامج إلى فخّ (trap).
  • sBPF v1 فقط. تؤدي شيفرات العمليات الخاصة بـ v2 إلى فخّ.
  • تؤدي استدعاءات النظام Ed25519 وsecp256k1 إلى فخّ إلى أن تتوفر لها جداول المعالج المساعد.
  • تسجّل السلسلة ELF بوصفه مُدخلًا عامًا فحسب. يخزّن النشر مع --public كلمات ELF وملخّصها، ويخدمها rand_getProgramPublic. ولا تسجّل السلسلة كيف بُنيت الصورة منه: انشر مُدخلات البناء ليتمكن الآخرون من إعادة بناء hc.

آخر تحقق مقابل الإيداع c0878c3f في fullnode (السلسلة 21) بتاريخ 2026-10-12، وcircuits `7ef3220` (`sbpf2rv/README.md`, `docs/superpowers/specs/2026-09-18-sbpf-to-rv32-translator-design.md`); steps 1, 2 and the parity test re-run on 2026-09-19. إذا اختلف الكود عن هذه الصفحة فالكود هو الصحيح؛ أبلغونا بذلك.