Parameters
جزء من قسم الأساسيات في رحلة Verilog على Coddy — الدرس 11 من 90.
يمكنك إنشاء نسخ عديدة من نفس الوحدة (module) واستخدامها في أماكن مختلفة — وهذا ما يسمى **بالنسخ المتعددة (multiple instances)**. فبدلاً من كتابة الكود نفسه مراراً وتكراراً، يمكنك كتابته مرة واحدة وإعادة استخدامه لعدد المرات التي تحتاج إليها. وتعد كل نسخة (instance) بمثابة نسخة منفصلة من ذلك العتاد على الرقاقة.
ولكن ماذا لو كنت بحاجة إلى أن تكون كل نسخة مختلفة؟ على سبيل المثال، عداد واحد بسعة 8 بت، وعداد واحد بسعة 16 بت، وعداد واحد بسعة 32 بت. بدون المعاملات (parameters)، ستحتاج إلى كتابة ثلاث وحدات (modules) منفصلة.
المعاملات تحل هذه المشكلة.
المعامل (parameter) هو قيمة ثابتة يمكنك تعيينها عند إنشاء مثيل (instance). يتيح لك ذلك تهيئة كل نسخة من الوحدة (module) بشكل مختلف.
التصريح عن المعاملات (Parameters)
module counter #(
parameter WIDTH = 8
)(
input clk,
output reg [WIDTH-1:0] count
);
always @(posedge clk) count <= count + 1;
endmoduleيحدد #(parameter WIDTH = 8) معلمة تسمى WIDTH بقيمة افتراضية قدرها 8.
عند التصريح عن المعاملات (parameters)، نستخدم الرمز # مباشرة بعد اسم الوحدة (module name) و قبل قائمة المنافذ (port list). يخبر الرمز # لغة Verilog أن ما يليه هو قائمة من المعاملات التي تقوم بتهيئة الوحدة. إذا لم تكن وحدتك تحتوي على معاملات، فببساطة يمكنك حذف # تماماً.
استخدام المعاملات (Parameters)
يمكن استخدام المعاملات في أي مكان يلزم فيه وجود ثابت:
reg [WIDTH-1:0] data; // حجم المتجه
count <= count + 1; // يعمل مع أي عرض
assign out = data[WIDTH-1]; // موقع MSBتجاوز المعلمات
عند استخدام الوحدة (module)، يمكنك تغيير قيمة المعلمة (parameter):
// العرض الافتراضي (8 بت)
counter u1 (.clk(clk), .reset(reset), .count(count1));
// التجاوز إلى 16 بت
counter #(.WIDTH(16)) u2 (.clk(clk), .reset(reset), .count(count2));معلمات متعددة
يمكنك الحصول على معلمات متعددة:
module fifo #(
parameter DEPTH = 16,
parameter WIDTH = 8
)(
input clk, wr_en, rd_en,
input [WIDTH-1:0] data_in,
output [WIDTH-1:0] data_out
);
reg [WIDTH-1:0] memory [0:DEPTH-1];
endmoduleLocalparam
الـ localparam مشابه ولكنه لا يمكن تجاوزه من الخارج:
module example;
localparam STATE_IDLE = 2'b00;
localparam STATE_RUN = 2'b01;
localparam STATE_STOP = 2'b10;
// هذه القيم ثابتة داخل هذا الـ module
endmoduleاستخدم localparam للثوابت التي لا ينبغي أن تتغير.
التحدي
أضف بارامتر يسمى WIDTH بقيمة افتراضية هي 4.
ما يجب فعله:
- أضف بارامتر باسم
WIDTH - اضبط قيمته الافتراضية على
4 - يوضع البارامتر داخل
#( )بعد اسم الـ module
ورقة مرجعية
تسمح المعاملات (Parameters) بتهيئة مثيلات الوحدة (module instances) بشكل مختلف دون إعادة كتابة الكود.
الإعلان عن المعاملات
module counter #(
parameter WIDTH = 8 // default value
)(
input clk,
output reg [WIDTH-1:0] count
);
always @(posedge clk) count <= count + 1;
endmoduleتجاوز المعاملات عند إنشاء المثيل (Instantiation)
counter u1 (.clk(clk), .count(count1)); // uses default (8)
counter #(.WIDTH(16)) u2 (.clk(clk), .count(count2)); // overridden to 16معاملات متعددة
module fifo #(
parameter DEPTH = 16,
parameter WIDTH = 8
)( ... );Localparam (ثابت غير قابل للتجاوز)
localparam STATE_IDLE = 2'b00;
localparam STATE_RUN = 2'b01;استخدم localparam للثوابت الداخلية التي يجب عدم تغييرها من خارج الوحدة.
جرّب بنفسك
module counter #(
// أضف المعامل WIDTH هنا بالقيمة الافتراضية 4
)(
input clk,
input reset,
output reg [WIDTH-1:0] count
);
endmoduleيتضمن هذا الدرس اختبارًا قصيرًا. ابدأ الدرس للإجابة عليه وتتبّع تقدمك.
جميع دروس الأساسيات
4المعاملات - الجزء الأول
المعاملات الحسابيةمعامل باقي القسمة (Modulo)معاملات المقارنةملخص - رياضيات بسيطةمعاملات Bitwise7التعيين والبوابات المنطقية
التعيين المستمرالتعيين باستخدام العملياتالبوابات الأساسية المدمجةبوابات AND و OR و NOTبوابات XOR و XNORمراجعة - دارة البوابات المنطقية5المعاملات - الجزء الثاني
المعاملات المنطقيةمعاملات الاختزالمعاملات الإزاحةمعامل الدمجالمعامل الشرطيمراجعة - تحدي المعاملات3أنظمة العد
التمثيل الثنائيالأعداد محددة الحجمالأعداد غير محددة الحجمالأعداد السالبةالقيم الخاصة X و Zمراجعة - تنسيقات الأعداد6الوحدات
هيكل الوحدةمنافذ الإدخال والإخراجمنافذ Inoutاستدعاء الوحداتربط المنافذ بالاسمربط المنافذ بالترتيبمراجعة - بناء وحدة