This is an old revision of the document!
= Laboratorul 5 - Debugging skills =
In laboratoarele anterioare au fost prezentate elementele de limbaj Verilog si de descriere comportamentala a doua tipuri de circuite: secventiale si combinationale. Acest laborator se va concentra pe modul in care ne asiguram ca un circuit are functionalitatea dorita.
In acest laborator vom corecta erorile dintr-un adder8 caruia i-am oferit o functionalitate diferita decat a celorlalte module de tip adder implementate in laboratoarele anterioare.
Modulul adder8 va primi la intrare un pachet de date ce contine termenii adunarii pe 8 biti, si va returna la iesire suma tuturor termenilor. Modulul va avea un semnal de error, care va fi asertat in cazul in care se detecteaza vreo eroare (i.e. overflow).
<imgcaption interconnect | Adder8></imgcaption>
<tabcaption tabel-interfete_in center |Interfata de Intrare>
Port | Width (bits) | Directie | Valoare la reset | Descriere |
---|---|---|---|---|
data_in | 8 | in | 0 | Folosit pentru a trimite termenii operatiei de adunare |
valid_in | 1 | in | 0 | Valideaza un byte de date |
sot_in | 1 | in | 0 | Marcheaza inceputul unei tranzactii. Va fi activ un singur ciclu de ceas |
eot_in | 1 | in | 0 | Marcheaza sfarsitul unei tranzactii. Va fi activ un singur ciclu de ceas |
</tabcaption>
<tabcaption tabel-interfete_out center |Interfata de Iesire>
Port | Width (bits) | Directie | Valoare la reset | Descriere |
---|---|---|---|---|
data_out | 8 | out | 0 | Folosit pentru a trimite rezultatul operatiei de adunare. |
valid_out | 1 | out | 0 | Valideaza un byte de date |
sot_out | 1 | out | 0 | Marcheaza inceputul unei tranzactii. Va fi activ un singur ciclu de ceas |
eot_out | 1 | out | 0 | Marcheaza sfarsitul unei tranzactii. Va fi activ un singur ciclu de ceas |
</tabcaption>
<tabcaption tabel-interfete_stat center |Interfata de Status>
Port | Width (bits) | Directie | Valoare la reset | Descriere |
---|---|---|---|---|
error | 1 | out | 0 | Folosit pentru a marca o eroare ce s-a intamplat in timpul realizarii operatiei de adunare. |
</tabcaption>
Modulul va primi unul sau mai multi bytes de date, va realiza operatia de adunare intre toti termenii, si apoi va pune rezultatul pe interfata de iesire. Rezultatul va fi reprezentat pe maximum 10 biti. Deoarece latimea semnalului de iesire este de doar 8 biti, intreg rezultatul va fi pus pe interfata de iesire in doi cicli consecutivi (vezi exemplu de la capitolul Protocol de iesire). In cazul in care rezultatul nu poate fi reprezentat pe 10 biti, semnalul de eroare va fi asertat, iar toti bitii sumei vor fi pusi pe 1. Semnalul de eroare trebuie asertat pe intreaga lungime a pachetului de iesire.
Tranzitiile RTL-ului (RTL = register-transfer level sau modul) si citirea semnalelor de intrare se va face pe frontul pozitiv al ciclului de ceas. Resetul este activ pe 0, blocul va fi considerat in reset cand resetul este 0, si va functiona normal cand resetul este 1.
<imgcaption interconnect | O tranzactie de intrare></imgcaption>
Blocul nu poate accepta tranzactii consecutive. Acesta are nevoie de un delay de minim un ciclu de ceas intre 2 intrari consecutive
<imgcaption interconnect | Distanta intre tranzactii consecutive></imgcaption>
1) Pentru un rezultat pe maxim 8 biti
<imgcaption interconnect | Pentru un rezultat pe maxim 8 biti></imgcaption>
2) Pentru un rezultat pe maxim 10 biti
<imgcaption interconnect | Pentru un rezultat pe maxim 10 biti></imgcaption>
Rezultatul operatiei va fi obtinut prin concatenarea S1 si S2; Sum = {S1,S2}’
3) Pentru overflow
<imgcaption interconnect | Overflow></imgcaption>
<imgcaption interconnect | Exemplu de transfer></imgcaption>
<imgcaption interconnect | Diagrama de stari></imgcaption>
Cel mai rapid mod de a identifica o eroare este prin a verifica log-ul de simulare. Acesta e salvat in fisierul isim.txt sau poate fi urmarit direct in consola din simulator.
Codul trebuie sa contina mesaje de debug pentru ca log-urile sa fie utile. Aceste mesaje pot fi scrise folosind functiile de sistem:
* $display()
* $warning()
- nu e supportat de Xilinx ISE
* $error()
- nu e supportat de Xilinx ISE
Un mesaj simplu precum $display(“[ADDER_STATE_STATUS]: Entering state IDLE”), poate ajuta la debug-ul unei stari de DEADLOCK sau o tranzitie gresita.
Diagramele cu forme de unda (waveforms) sunt unealta principala de debug folosita, complementand log-ul. Acestea iti arata modul in care s-au modificat semnalele si variabilele locale in timp, pe tot parcursul simularii.
Un caz tipic de debug este urmatorul:
1) Testul pica cu urmatorul mesaj de eroare:
<imgcaption interconnect | Console error></imgcaption>
2) Datorita log-ului ne uitam pe semnalul de eroare din simulare (marcat cu visiniu in imaginea de mai jos)
<imgcaption interconnect | Waves></imgcaption>
3) Din diagrama formelor de unde ne dam seama ca semnalul nu este asertat in starea in care trebuie. Vom adauga variabila state in diagrama.
<imgcaption interconnect | Waves></imgcaption>
4) Observam ca in starea 4 (GENERATE_OUTPUT) semnalul error nu se aserteaza asa cum este de asteptat, de aici ne ducem in cod si observam ca lipseste linia: error_reg = overflow;
5) Corectam codul:
<imgcaption interconnect | Cod corectat></imgcaption>
6) Resimulam si obtinem comportamentul dorit
<imgcaption interconnect | Waves></imgcaption>
In cazul in care niciuna din metodele de mai sus nu merg, se vor pune breakpoint-uri direct in cod, pentru a verifica starea simularii intr-o anumita zona din cod. Aceasta solutie nu este una eficienta, si nu este viabila atunci cand codul devine mai mare. Pentru mai multe detalii urmariti tutorialul de debugging.
Niciuna din metodele de mai sus nu ar functiona daca nu ar exista teste care sa stimuleze modulul si sa monitorizeze activitea de pe interfata de iesire.
Pentru fiecare functionalitate a blocului ar trebui scris un test. In cazul adder8 vom avea nevoie minim de: * Un test care sa realizeze suma a N numere, iar rezultatul este pe 8 biti * Un test care sa realizeze suma a N numere, iar rezultatul este pe 10 biti * Un test care sa realizeze suma a N numere, iar rezultatul este pe mai mult de 10 biti * Un test in care sa trimitem mai multe tranzactii consecutive * Un test in care sa trimitem foarte multi termeni (N >= 40) * Un test in care sa trimitem un singur termen.
In cadrul scheletului de cod, in fisierul adder8_test vom avea un task numit drive care se ocupa de stimularea corespunzatoare a modulului. Task-ul monitor, interpreteaza semnalele de output si verifica corectitudinea acestora.
- (9p). Rulati scheletul de cod si corectati erorile care apar. (6×1.5p) * Hint: Testele se vor termina fie cu eroare, fie se vor bloca * Hint: Intreg exercitiul ruleaza timp de 2.2us.
- (1p). Pe modelul testelor din schelet, scrieti un nou test ce verifica o functionalitate a adder8 ce nu a fost explorata inca.
- (Bragging rights) 4p . Prin testul dezvoltat la exercitiul 2 se gaseste o eroare de functionare a adder8. * Conditii de acordare a bonusului: * Trimiteti un mail catre asistentul de laborator (cu sergiu.a.duda@gmail.com in CC) cu