diff --git "a/text/0000-\330\252\330\256\330\262\331\212\331\206-\330\263\330\247\331\203\331\206-\331\205\330\263\331\205\331\221\331\211-\331\210\330\263\331\205\330\247\330\252-\330\247\331\204\330\252\330\256\330\262\331\212\331\206.md" "b/text/0000-\330\252\330\256\330\262\331\212\331\206-\330\263\330\247\331\203\331\206-\331\205\330\263\331\205\331\221\331\211-\331\210\330\263\331\205\330\247\330\252-\330\247\331\204\330\252\330\256\330\262\331\212\331\206.md" new file mode 100644 index 0000000..13b5773 --- /dev/null +++ "b/text/0000-\330\252\330\256\330\262\331\212\331\206-\330\263\330\247\331\203\331\206-\331\205\330\263\331\205\331\221\331\211-\331\210\330\263\331\205\330\247\330\252-\330\247\331\204\330\252\330\256\330\262\331\212\331\206.md" @@ -0,0 +1,203 @@ +- **عنوان المقترح:** تخزين ساكن مسمّى + سمات التخزين (`@رمز`/`@متطاير`/`@محزوم`) + بيانات مضمَّنة +- **النطاق:** لغة `text/` +- **تاريخ البدء:** 2026-07-21 +- **رقم الـ RFC:** (يُترك فارغاً حتى الدمج) +- **الحالة:** مقترَح (PR مفتوح) +- **Issue التتبُّع:** (يُترك فارغاً حتى القبول) + +# ملخّص + +تمكين برامج ص من تعريف **مخزن ساكن مسمّى برمز رابط مستقرّ ومُصدَّر** يعيش في +`.bss`/`.rodata`، مع سمات تخزين: `@رمز("اسم")` (رمز رابط ثابت مُصدَّر)، تفعيل +`@متطاير` على التصريح (مكسور حاليًّا)، `@محزوم` (رصّ)، وحرفيّة **بيانات مضمَّنة** +(كتلة بايتات ثابتة في `.rodata`). الهدف المباشر: أن تملك نواة النحلة عدّاداتها +وخريطتها البتّيّة وأرشيفها بلغة ص بدل مخازن C، مكمِّلةً مدمج `عنوان_رمز` (اللبنة +3.13) الذي صار يأخذ عناوينها. + +# الدافع (Motivation) + +بعد اللبنة 3.13 (`عنوان_رمز`) صارت ص تأخذ عنوان رمز رابط خارجيّ، فأُطفئت جالبات +العنونة. لكنّ **المخازن نفسها ما زالت في C**: عدّادات المقاطعات (`bee_probe_hits` +وأخواتها، `volatile`)، الخريطة البتّيّة لمدير الذاكرة (`bee_pmm_bitmap`)، أرشيف +نظام الملفّات وخرائط المفاتيح (`bee_initrd`/`bee_kbd_set1_map`، بيانات جدول في +`.rodata`). حلّل تقرير أميليا أنّ هذه ثاني أكبر رافعة لإطفاء C بعد `عنوان_رمز`. + +ص **تملك** تقنيًّا مسار globals (المتغيّر على مستوى الوحدة يصير `GlobalVariable` +حقيقيًّا في `.bss`/`.data`/`.rodata`)، لكن ينقصها الغلاف اللغويّ المستقرّ: + +1. **رمز مستقرّ مُصدَّر:** الـglobal اليوم `InternalLinkage` باسم عربيّ خام غير + مستقرّ. النواة تحتاج رمزًا ثابتًا مُصدَّرًا (`ExternalLinkage`) كي: + - يكتبه سياق المقاطعة (أكعاب ISR في C/أسمبلي) بالاسم، + - وتأخذ ص عنوانه عبر `عنوان_رمز("bee_probe_hits")`، + - ويبقى الاسم مطابقًا لعقد ABI المتّفَق عليه. +2. **`@متطاير` معطوبة على التصريح:** العدّادات يكتبها معالج مقاطعة ويقرؤها منطق + الفحص — تلزمها دلالة volatile. السمة موجودة اسميًّا لكنّ علمها يُسقَط ولا يصل + إلى `GlobalVariable::setVolatile`. +3. **`@محزوم` غائبة:** الواصفات الزائفة (نمط `bee_idtr`) وبنى العتاد تحتاج رصًّا + دقيقًا؛ لا كلمة لطلبه. +4. **بيانات مضمَّنة:** لا صياغة لكتلة بايتات ثابتة كبيرة (أرشيف SFA1، خريطة + set-1) برمز مستقرّ في `.rodata`. + +حالة استخدام واقعيّة (نهلة، بعد هذا المقترح): + +```sad +# عدّاد يكتبه معالج المقاطعة ويقرؤه الفحص — .bss، رمز مُصدَّر، متطاير +@رمز("bee_probe_hits") @متطاير متغير عداد_المسبار = 0 + +# أرشيف قرص البدء — .rodata، رمز مُصدَّر، بيانات مضمَّنة +@رمز("bee_initrd") ثابت أرشيف = بايتات(0x53، 0x41، 0x44، 0x46، 0x53، 0x31، 0x36) +``` + +# الشرح التوجيهي (Guide-level explanation) + +## `@رمز("اسم")` — رمز رابط مستقرّ مُصدَّر + +توجيه يسبق تصريح متغيّر/ثابت على مستوى الوحدة، فيمنح المخزن اسم رمز رابط ثابتًا +بربط خارجيّ (بدل الاسم العربيّ الخام الداخليّ). نظير `دالة خارجية("اسم")` لكن +لجهة **التعريف** (تصدير) لا الاستيراد. + +```sad +@رمز("bee_pmm_bitmap") متغير الخريطة_البتية = 0 # رمز عالميّ bee_pmm_bitmap في .bss +``` + +يصبح الرمز مرئيًّا للرابط، فيستطيع كود C/أسمبلي خارجيّ (أكعاب ISR) الإشارة إليه +`extern`، وتأخذ ص عنوانه عبر `عنوان_رمز("bee_pmm_bitmap")`. + +## `@متطاير` — دلالة volatile على المخزن (إصلاح) + +يجعل كلّ قراءة/كتابة للمخزن `volatile` (لا يحذفها/يعيد ترتيبها المُحسِّن). مطلوب +لأيّ مخزن يشترك فيه سياق مقاطعة ومنطق عاديّ. + +```sad +@رمز("bee_pit_ticks") @متطاير متغير نبضات = 0 +``` + +## `@محزوم` — رصّ (packed) + +يزيل الحشو بين الحقول (محاذاة 1)، لبنى العتاد/الواصفات ذات التخطيط الدقيق. + +## `بايتات(...)` — بيانات مضمَّنة (كتلة `.rodata`) + +حرفيّة كتلة بايتات ثابتة تُصدَر كـ`ConstantDataArray` في `.rodata`. مع `ثابت` +و`@رمز` تعطي جدول بيانات نواة مملوكًا لـص. + +```sad +@رمز("bee_kbd_set1_map") ثابت خريطة_المفاتيح = بايتات(0، 27، 49، 50، ...) +متغير أوّل = اقرأ_ذاكرة(عنوان_رمز("bee_kbd_set1_map")) +``` + +# الشرح المرجعي (Reference-level explanation) + +## مصدر الحقيقة (`language-truth/`) + +- توجيهات جديدة في `directives.yaml`: `@رمز("اسم")` (وسيط سلسلة) و`@محزوم`. + `@متطاير` موجود (سطر 54) — لا إضافة، بل إصلاح توصيل. +- كلمة/مدمج `بايتات` لحرفيّة البايتات (أو صياغة مصفوفة بايتات ثابتة) في + `builtins`/`keywords`. + +## المحلل المعجمي/النحوي (Lexer/Parser) + +- `@رمز("اسم")`: توجيه بوسيط سلسلة حرفيّة (نمط `@متطاير` + استخراج سلسلة كـ + `دالة خارجية`). +- `@محزوم`: توجيه بلا وسيط. +- `بايتات(...)`: استدعاء يُحلَّل كقائمة ثوابت رقميّة (0–255). + +## الشجرة المجردة (AST) + +- `VarDeclStmt` يكتسب حقول: `linkSymbol` (اسم `@رمز`)، `isVolatile` (موصول)، + `isPacked`. (الحقل `isVolatile` موجود في `VariableInfo` لكن لا يُملأ من مسار + `@متطاير` — يُوصَل.) +- عقدة `ByteBlobLiteral` (أو إعادة استخدام تمثيل المصفوفة الثابتة). + +## المفسّر + +- `@رمز`: لا أثر دلاليّ في المفسّر (لا رموز رابط)؛ المخزن يبقى متغيّرًا عاديًّا. +- `@متطاير`: المفسّر أحاديّ الخيط الدلالة ⇒ لا أثر مرئيّ (يُقبَل ويُتجاهَل). +- `بايتات(...)`: تُمثَّل كمصفوفة أرقام عاديّة في المفسّر. + +## المترجم (sadc): SIR / LLVM IR codegen + +1. **`@رمز`**: في `emitGlobalVariables` (`classes_vtables_ops.cpp`)، إن كان + `linkSymbol` غير فارغ ⇒ استعمله اسمًا للـ`GlobalVariable` مع + `ExternalLinkage` بدل `InternalLinkage` + الاسم الخام. +2. **`@متطاير`**: أصلِح `statement_advanced.cpp` كي ينقل `isVolatile` إلى + `SIRGlobalVariable`، ثمّ في الإصدار اضبط سمة على المخزن ووسم قراءاته/كتاباته + `setVolatile(true)` (البنية قائمة في `llvm_volatile_ops.cpp`). +3. **`@محزوم`**: مرّر `isPacked=true` إلى `StructType::create` (اليوم مقيَّد + `false` في `llvm_type_mapper_composite.cpp:82`) + `Align(1)`. +4. **`بايتات`**: أصدِر `ConstantDataArray::get(...)` في `.rodata` (البنية قائمة، + مستعملة داخليًّا في `arabic_string_pool.cpp`) كمخزن مسمّى. +5. **القسم الصريح (مؤجَّل/ثانويّ):** البنية `LLVMCustomSections::placeGlobal` + قائمة لكن يتيمة؛ يمكن ربط `@قسم(".name")` بها لاحقًا (خارج نطاق هذا المقترح). + +## نظام الأخطاء + +- خطأ SEM جديد: `@رمز` بوسيط غير ثابت/فارغ (نظير SEM021 لـ`عنوان_رمز`). +- خطأ SEM: `بايتات` بقيمة خارج [0,255]. + +## الأدوات + +- LSP/الإكمال: التوجيهات الجديدة مولَّدة من `directives.yaml`. + +## التوافق الخلفي + +توجيهات/صياغة جديدة بأسماء غير مستعملة ⇒ **لا كسر**. إصلاح `@متطاير` يغيّر +سلوكًا كان صامتًا (السمة تُتجاهَل اليوم) إلى فعّال — تحسين لا كسر. + +# السلبيات (Drawbacks) + +- **توسيع سطح اللغة:** أربع سمات/صيغ جديدة دفعةً. يمكن التدرّج (انظر البدائل). +- **`@رمز` يوسّع الربط:** رمز مُصدَّر يفتح احتمال تصادم أسماء عالميّة — مقبول في + سياق نواة/برنامج واحد، لكنّه مسؤوليّة المستخدم. +- **الثبات المحسوب:** ثابت بقيمة محسوبة (لا حرفيّة) يفقد `isConstant` في LLVM + اليوم (يُكتب عبر `__sad_main`) — قيد قائم لا يحلّه هذا المقترح؛ `بايتات` + الحرفيّة تتفاداه. +- **`@محزوم` و`@متطاير` سهلتا إساءة الاستعمال:** الرصّ يكسر المحاذاة على بعض + المعماريّات؛ محصور بحالات العتاد. + +# المبرّرات والبدائل (Rationale and alternatives) + +**لماذا `@رمز` توجيهًا؟** يحاكي `دالة خارجية("اسم")` (تصدير رمز مسمّى) وأدنى سطح +تغيير: يعيد استخدام مسار globals القائم (يبدّل الاسم والربط فقط). يتكامل مباشرةً +مع `عنوان_رمز` (3.13): ص تعرّف المخزن وتأخذ عنوانه بالاسم نفسه. + +**البدائل:** +- **تصريح مخزن مخصَّص جديد (`مخزن ساكن ...`):** أوسع وأبعد عن صياغة ص القائمة؛ + `@رمز متغير` يعيد استخدام `متغير`/`ثابت` المألوفين. +- **التدرّج (تقسيم لـRFCات):** يمكن فصل `@رمز` (الرافعة الأساس) عن `@محزوم`/ + `بايتات`. لكنّها متلازمة لإطفاء مخازن النواة (العدّادات تحتاج `@رمز`+`@متطاير`، + الجداول تحتاج `@رمز`+`بايتات`)، فجمعها يخدم هدفًا واحدًا متماسكًا. `@محزوم` + أضعفها ترابطًا ويمكن تأجيله. +- **لا فعل شيء:** تبقى مخازن `.bss`/`.rodata` في C، فيتوقّف إطفاء C عند سقف أعلى + بكثير من الأرضيّة الدائمة (~600 سطر). + +# أعمال سابقة (Prior art) + +- **C:** `static`/`__attribute__((section))`/`volatile`/`__attribute__((packed))` + + مُهيّئات مصفوفات — بالضبط ما تحتاجه النواة، وهو ما يُهاجَر منه. +- **Rust:** `static X: T = ...` (رمز مُصدَّر عبر `#[no_mangle]`)، `#[repr(packed)]`، + `#[link_section = "..."]`، `read_volatile`/`write_volatile`، `include_bytes!` + للبيانات المضمَّنة. مقترحنا نظير عربيّ مباشر لهذه المجموعة. +- **Zig:** `export var`، `packed struct`، `linksection`، `@embedFile`. + +الدرس: تعريف مخزن ساكن مسمّى/مُصدَّر بسمات (volatile/packed/section) وبيانات +مضمَّنة نمط قياسيّ لبرمجة الأنظمة، بلا مكتبة قياسيّة. + +# أسئلة غير محسومة (Unresolved questions) + +- **صياغة `بايتات`:** مدمج `بايتات(...)` أم صياغة مصفوفة ثابتة (`ثابت س: بايت[] = + [...]`)؟ يُحسم بالنقاش. +- **`@رمز` على المحلّيّ:** هل يُقبَل فقط على مستوى الوحدة (المنطقيّ)، أم داخل + الدوالّ (statics محلّيّة)؟ المقترح: مستوى الوحدة فقط أوّلًا. +- **القسم الصريح `@قسم(".name")`:** خارج نطاق هذا المقترح (البنية يتيمة)؛ يُبنى + لاحقًا فوقه. +- **`@محزوم`:** ضمن هذا المقترح أم يُفصَل؟ (أضعفها ترابطًا بإطفاء المخازن.) +- **الثبات المحسوب الحقيقيّ:** خارج النطاق (قيد `__sad_main` قائم). + +# إمكانات مستقبلية (Future possibilities) + +- **`@قسم(".name")`**: ربط الصياغة بالبنية القائمة `LLVMCustomSections` لوضع + مخازن في أقسام مخصَّصة (نمط `.multiboot`/`.page_tables`). +- **statics محلّيّة** داخل الدوالّ (رمز مستقرّ لكن نطاق معجميّ محلّيّ). +- **`@محاذاة(n)`**: ضبط محاذاة صريح للمخزن. +- **تهيئة ثابتة محسوبة**: نموذج تهيئة ثابتة حقيقيّة يتجاوز قيد `__sad_main`.