1 - سطح گیت
جلسه اول (ماژول ها) جلسه دوم (گیت ها) جلسه سوم (نوع سیگنال) جلسه چهارم (پایان فصل)2 - مقداردهی مداوم
جلسه پنجم (اُپراتور ها) جلسه ششم (آرایه ها) جلسه هفتم (شرط ها) جلسه هشتم (فراخوانی ماژول) جلسه نهم (تست بنچ) جلسه دهم (نگاشت حافظه)3 - سطح رفتاری (ترکیبی)
جلسه یازدهم (بلاک Always) جلسه دوازدهم (ابزار ها) جلسه سیزدهم (نوع پردازش) جلسه چهاردهم (نکات تکمیلی) جلسه پانزدهم (پایان فصل)4 - سطح رفتاری (ترتیبی)
جلسه شانزدهم (لبه ها) جلسه هفدهم (تست بنچ 2) جلسه هجدهم (شمارنده ها) جلسه نوزدهم (ضرب و شیفت) جلسه بیستم (استیت ماشین) جلسه بیست و یکم (کشف رشته) جلسه بیست و دوم (فرکانس) جلسه بیست و سوم (نان بلاک) جلسه بیست و چهارم (پایان)5 - جلسات تمرینی
جلسه تمرین اول (تاخیر ها) جلسه تمرین دوم (الحاق-منطق) جلسه تمرین سوم (شیفت ها) جلسه تمرین چهارم (استیت)6 - مثال های پروژه محور
پروژه طراحی پردازنده RTL پروژه پردازنده Maano پروژه پردازنده MIPS7 - ارتباط و گفتگو
ارتباط با نویسنده گروه تلگرام تبلیغات و آگهیآموزش وریلاگ آموزش Verilog
این جلسه قرار نیست چیز جدیدی یاد بگیریم ، فقط میخایم مسئله جدیدی رو حل کنیم . گاهی وقتا از ما میخوان مقدار یک ورودی تک بیتی رو در هر لبه کلاک بررسی کنیم و اگه الگوی خاصی تشکیل شد ، خروجی رو فعال کنیم . یعنی چی ؟ مثلا میگن اگه توی ورودی الگوی 1100 رو دیدی خروجی رو فعال کن ، این یعنی توی کلاک اول ورودی من 1 باشه ، توی کلاک دوم ورودی من 1 باشه و توی کلاک سوم ورودی من 0 باشه و در کلاک چهارم ورودی من 0 باشه ، در اینصورت خروجی رو فعال کنم . یجورایی میشه گفت قراره یک رشته یا دنباله مشخصی رو کشف یا آشکارسازی کنیم . به شکل زیر نگاه کنید :
یه ورودی داریم که اگه بصورت متوالی 1 و 1 و 0 و 0 باشه خروجی ما هم یک میشه . مثلا اگه ورودی من به ترتیب 0 و 0 و 0 و 0 و 1 و 1 و 1 و 0 و 0 باشه ، توی کلاک 9 خروجی یک میشه ، چون توی 4 کلاک اول ورودی 0 هست که خب هیچی ولی توی کلاک 6 و 7 و 8 و 9 مقدار ورودی ما 1 و 1 و 0 و 0 هست . توجه کنید که الگوی مورد نظر باید بصورت متوالی ظاهر شده باشه .
1- 2- 3- 4- 5- 6- 7- 8- 9- 10- 11- 12- 13- 14- 15- 16- 17- 18- 19- 20- 21- 22- 23- 24- 25- 26- 27- 28- 29- 30-
module Detection1( input Clk, input Rst, input x, output y ); //Target : > 1,1,0,0 reg [2:0] Level; assign y = (Level==4)? 1 : 0; always @(posedge Clk or negedge Rst) begin if (~Rst) Level=0; else begin case(Level) 0 : begin if(x) Level=1; else Level=0; end 1 : begin if(x) Level=2; else Level=0; end 2 : begin if(x) Level=2; else Level=3; end 3 : begin if(x) Level=1; else Level=4; end 4 : begin if(x) Level=1; else Level=0; end endcase end end endmodule
برای آشکارسازی رشته 1100 (از چپ به راست) ، یه متغییر Level تعریف کردم ، هر بار که یه رقم ازین رشته رو پیدا کردم یدونه به Level اضافه میکنم ، البته اگه وسط کار توالی بهم خورد ارقام به ترتیب ظاهر نشد ، Level رو صفر میکنم و از ابتدا کار رو شروع میکنم . هروقت هم که Level برابر 4 شد ، یعنی چهارمین رقم هم ظاهر شده و الگوی من بطور کامل توی ورودی دیده شده بنابراین خروجی رو یک میکنم (خط 12 برنامه) در حالت ریست گفتم توی Level صفر هستم ، حالا روی Level یه کیس زدم و گفتم اگه توی مرحله صفر بودم و مقدار ورودی من 1 بود ، اولین رقم ظاهر شده پس Level رو یک میکنم . حالا توی مرحله یک ، اگه مجددا ورودی من 1 بود ، دومین رقم هم ظاهر شده و تا اینجا داریم 1 1 پس Level رو دو میکنم . توی مرحله دوم اگه ورودی 0 بود سومین رقم من ظاهر شده و 110 رو تا اینجا دارم بنابراین Level رو سه میکنم اما اگه ورودی من 0 نبود بلکه 1 بود ، Level رو 2 میکنم به این معنی که من توی مرحله ای هستم که 1 1 رو در مشت خودم دارم . اگه Level سه بودم و ورودی 0 بود رشته من تکمیل شده و من 1100 رو دیدم بنابراین باید Level رو مساوی چهار قرار بدم و البته خروجی رو هم فعال کنم . حالا در Level چهار ، دوباره این ماجرا تکرار میشه ، اگه 0 اومد باید به مرحله صفر برم و اگه ورودی 1 اومد باید به مرحله 1 برم چون اولین رقم رو مجددا مشاهده کردم و باید Level یک بشه و ... تکرار این ماجرا . اگه متوجه نمیشید حق دارید اصلا توی متن نمیشه بیان کرد حتما باید تصویری بهتون بگم ، بنابراین ویدئو این جلسه رو دانلود کنید ببینید چیشد . خب حالا این مسئله رو میشد با استراتژی استیت ماشین هم حل کرد ، که شکل زیر یک مدل استیت ماشین از مسئله کشف دنباله 1100 هست :
ورودی x مشخص میکنه که ما هر لحظه به چه استیتی منتقل بشیم ، در نهایت اگر به استیت 4 رسیدیم یعنی الگوی 1100 ظاهر شده و باید خروجی یک بشه .
1- 2- 3- 4- 5- 6- 7- 8- 9- 10- 11- 12- 13- 14- 15- 16- 17- 18- 19- 20- 21- 22- 23- 24- 25- 26- 27- 28- 29- 30- 31- 32-
module Detection2( input Clk, input Rst, input x, output reg y ); //Target : > 1,1,0,0 reg [2:0] State; reg [2:0] Nx_St; always @(posedge Clk or negedge Rst) begin if (~Rst) State=0; else State=Nx_St; end always @(*) begin case(State) 0 : begin y=0; if(x) Nx_St=1; else Nx_St=0; end 1 : begin y=0; if(x) Nx_St=2; else Nx_St=0; end 2 : begin y=0; if(x) Nx_St=2; else Nx_St=3; end 3 : begin y=0; if(x) Nx_St=1; else Nx_St=4; end 4 : begin y=1; if(x) Nx_St=1; else Nx_St=0; end endcase end endmodule
کد وریلاگ شو دیگه توضیح نمیدم ، مثل جلسه قبلی هستش که برای استیت ماشین ها مفصل بحث کردیم و کد نوشتیم . حالا میخوام به یه روش دیگه این مسئله رو حل کنم ، تا ببینید هزاران روش برای حل یک مسئله وجود داره ، من یه ظرف 4 بیتی تعریف میکنم و هر دفعه که لبه کلاک میاد ، ورودی جدید رو میندازم توی ظرف و از طرف دیگه ی ظرف یه بیت خارج میکنم . بدین ترتیب ظرف من همیشه آخرین 4 بیت رو توی دل خودش داره . شکل زیر رو ببینید :
از راست به چپ ، ورودی به ازای هر کلاک یه مقداری داره ، هر بار که این مقدار رو میخونیم ، میندازیمش توی ظرف مون و از طرف دیگه ظرف مون بیت قدیمی تر رو خارج میکنیم . این کار با شیفت قابل انجامه . کافیه محتوای ظرف رو یک بیت به چپ شیفت لاجیکال بدیم سپس بیت سمت راست ظرف رو مساوی با ورودی جدید مون قرار بدیم .
1- 2- 3- 4- 5- 6- 7- 8- 9- 10- 11- 12- 13- 14- 15- 16- 17- 18- 19- 20- 21- 22- 23- 24- 25- 26- 27- 28- 29- 30- 31- 32- 33- 34-
module Detection3( input Clk, input Rst, input x, output y ); //Target : > 1,1,0,0 reg [3:0] Zarf; reg [2:0] i; reg Led; always @(posedge Clk or negedge Rst) begin if (~Rst) begin Zarf=0; i=0; Led=0; end else begin Zarf=Zarf<<1; Zarf[0]=x; i=i+1; if(i>3) Led=1; end end assign y = (Zarf==4'b1100 && Led==1)? 1 : 0; endmodule
در حالت ریست گفتم ظرف من 0000 باشه ، بعدش که هر بار کلاک بیاد ظرف من از سمت چپ یه بیت رو خارج میکنه و از سمت راست ورودی جدید رو میگیره (خط 24 و 25) ، توی خط 32 هم یه شرط گذاشتم که هر گاه محتوای ظرف من 1100 شد یعنی 4 بیت آخر من 1100 شده و الگوی من ظاهر شده و خروجی رو یک میکنم . حالا داستان i و Led چیه ؟ ببینین فرض کنین صورت سوال الگوی 1100 رو نداده باشه مثلا الگوی 0000 رو داده باشه ، یعنی هر وقت چهار تا صفر توی ورودی دیدی ، خروجی رو فعال کن ، در این صورت ما همون لحظه ریست گفته بودیم ظرف من 0000 باشه ، پس همون لحظه خروجی فعال میشه و فکر میکنه چهار تا صفر از ورودی گرفته ، در صورتی که ما اصلا از ورودی چیزی نگرفتیم که !! اصلا هنوز شروع نکردیم چیزی بگیریم ، بنابراین برای حل این مشکل ما یه متغییر i میذاریم که هر بار یه بیت ورودی وارد ظرف شد یدونه بهش اضافه بشه و هروقت به 4 رسید ، یعنی ما 4 بیت وارد ظرف کردیم بنابراین حالا هرچی توی ظرف هست واقعا بیت های ورودی هست و مربوط به صفر های حالت ریست نیست ، پس وقتی چهار بیت وارد ظرف شد من یه سیگنال Led که اسمش رو دلبخواهی انتخاب کردم ، مقدارش رو یک میکنم و توی خط 32 میگم فقط وقتی حق داری خروجی رو 1 کنی که اولا Led فعال باشه یعنی حداقل ما 4 رقم وارد ظرف مون شده باشه ، ثانیا اون 4 رقمی که توی ظرف وارد شده برابر با 1100 یا الگوی من باشه . این جلسه تقریبا راحت ترین و ساده ترین جلسه بین کل جلسات بود منتها توضیحش با متن خیلی سخته ، ویدئو این جلسه رو که ببینید متوجه میشید چقد آسونه . دانلود فیلم جلسه
رفتن به جلسه بعد ...m
سلام ممنون بابت آموزش های خوبتون یک سوال داشتم برای مدل ظرف حالتی که ظرف یک الگوی صحیح رو تشخیص میده و بعد یک شیفت انجام میشه و دوباره با همون داده قبلی الگو شکل میگیره تو درتو رو در نظر نگرفتید. یعنی مثلا الگوی مد نظر 1111 هست و ورودی ما هم 111111، اینجا با هر شیفت دوباره الگو ایجاد شده در حالیکه باید ظرف کامل خالی بشه بعد با یک های جدید دنبال الگو بگرده
سید محسن
سلام ، اینطور سوالات رو میشه دوجور حل کرد . یکی با رعایت همپوشانی و یکی هم با عدم رعایت همپوشانی . مثالی که ما حل کردیم باتوجه به رعایت همپوشانی بوده . یعنی اگر الگویی ظاهر شد و یک بیت جدید وارد شد با بیت های قبلی همپوشانی یا اشتراک داشته باشن . برای عدم رعایت همپوشانی از طریق راه حل ظرف ، باید شمارنده رو بعد از هر بار کشف رشته ، صفر کنید .