Verilog-syntaxis beheersen: Essentiële regels & best practices
Lexicale conventies in Verilog lijken op C: het bevat een stroom tokens. Een lexicaal token kan uit één of meer tekens bestaan en tokens kunnen commentaren, sleutelwoorden, getallen, strings of witruimte zijn. Alle regels moeten eindigen met een puntkomma ;.
Verilog is hoofdlettergevoelig, dus var_a en var_A zijn verschillend.
Commentaren
Er zijn twee manieren om commentaren te schrijven in Verilog.
- Een enkelvoudige regel commentaar begint met
//en vertelt de Verilog-compiler om alles na dit punt tot het einde van de regel als commentaar te behandelen. - Een meerdere-regels commentaar begint met
/*en eindigt met*/en kan niet genest worden.
Enkelvoudige regelcommentaren kunnen wel genest worden in een meervoudig-regelcommentaar.
// Dit is een enkelvoudig regelcommentaar
integer a; // Maakt een int-variabele a, en behandelt alles rechts van // als commentaar
/* Dit is een meervoudig-regel of blokcommentaar */
/* Dit is /* een ongeldig genest blokcommentaar */ */
/* Echter, // deze is oké */
// Dit is ook oké
///////////// Nog steeds okéWitruimte
Witruimte is een term voor spaties, tabs, nieuwe regels en formfeeds, en wordt meestal genegeerd door Verilog, behalve wanneer het tokens scheidt. Dit helpt bij indentatie voor leesbaarheid.
module dut; // 'module' is een sleutelwoord, 'dut' is een identifier reg [8*6:1] name = "Hello!"; // De 2 spaties aan het begin worden genegeerd
Spaties en tabs worden wel bewaard in strings. In het onderstaande voorbeeld krijgt de string-variabele addr de waarde "Earth " vanwege behoud van spaties.
// Er is geen spatie aan het begin van deze regel, // maar er is een spatie in de string reg [8*6:1] addr = "Earth "; endmodule
Operatoren
Er zijn drie typen operatoren: unaire, binaire, en ternaire of conditionele.
- Unaire operatoren staan links van hun operand
- Binaire operatoren staan tussen hun operanden
- Conditionele operatoren hebben twee gescheiden operatoren die drie operanden scheiden
x = ~y; // ~ is een unaire operator, y is de operand
x = y | z; // | is een binaire operator, y en z zijn operanden
x = (y > 5) ? w : z; // ?: is een ternaire operator, expressie (y>5), w en z zijn operandenAls expressie (y > 5) waar is, krijgt variabele x de waarde van w, anders de waarde van z.
Getalformaten
We zijn gewend getallen als decimalen. Maar getallen kunnen ook in binair, octaal en hexadecimaal worden voorgesteld. Standaard behandelen Verilog-simulators getallen als decimalen. Om ze in een andere radix weer te geven, moeten regels worden gevolgd.
16 // Getal 16 in decimaal 0x10 // Getal 16 in hexadecimaal 10000 // Getal 16 in binair 20 // Getal 16 in octaal
Gespecificeerde grootte (Sized)
Gespecificeerde getallen worden weergegeven als [size]'[base_format][number], waar size alleen in decimaal wordt geschreven om het aantal bits aan te geven.
- base_format kan decimaal ('d of 'D), hexadecimaal ('h of 'H), octaal ('o of 'O) zijn en specificeert welke basis het number deel vertegenwoordigt.
- number wordt gespecificeerd als opeenvolgende cijfers 0-9 voor decimaal, en 0-9, A-F voor hexadecimaal.
3'b010; // grootte 3, binair ('b), nummer 010 (waarde 2 in binair)
3'd2; // grootte 3, decimaal ('d), nummer 2
8'h70; // grootte 8, hexadecimaal ('h), nummer 0x70 (decimaal 112)
9'h1FA; // grootte 9, hexadecimaal ('h), nummer 0x1FA (decimaal 506)
4'hA = 4'd10 = 4'b1010 = 4'o12 // Decimaal 10 in vier formaten
8'd234 = 8'D234 // Hoofdletters of kleine letters voor base_format mag
32'hFACE_47B2; // Underscore (_) kan 16-bit getallen scheiden voor leesbaarheidHoofdletters zijn legaal voor getalspecificatie wanneer base_formaat hexadecimaal is.
16'hcafe; // kleine letters Geldig 16'hCAFE; // hoofdletters Geldig 32'h1D40_CAFE; // underscore als scheider tussen 4 letters Geldig
Ongespecificeerde grootte (Unsized)
Getallen zonder base_format specificatie zijn standaard decimale getallen. Getallen zonder size specificatie hebben een standaardaantal bits afhankelijk van simulator en machine.
integer a = 5423; // base_format niet gespecificeerd, a krijgt decimaal 5423
integer a = 'h1AD7; // size niet gespecificeerd, omdat a int is (32 bits), waarde = 32'h0000_1AD7Negatief
Negatieve getallen worden gespecificeerd door een minteken - voor de grootte van een getal. Het is illegaal om een minteken tussen base_format en number te plaatsen.
-6'd3; // 8-bit negatief getal opgeslagen als two's complement van 3 -6'sd9; // Voor signed wiskunde 8'd-4; // Illegaal
Strings
Een tekenreeks tussen dubbele aanhalingstekens " " heet een string. Het kan niet over meerdere regels gesplitst worden en elk teken kost 1 byte.
"Hello World!" // String met 12 tekens -> vereist 12 bytes "x + z" // String met 5 tekens "How are you feeling today ?" // Illegaal: string mag niet over meerdere regels
Identifiers
Identifiers zijn namen van variabelen voor referentie. Ze bestaan uit alfanumerieke tekens [a-z][A-Z][0-9], underscores _ of dollarteken $ en zijn hoofdlettergevoelig. Ze mogen niet beginnen met een cijfer of dollarteken.
integer var_a; // Bevat letters en underscore -> Geldig integer $var_a; // Begint met $ -> Ongeldig integer v$ar_a; // Bevat letters en $ -> Geldig integer 2var; // Begint met cijfer -> Ongeldig integer var23_g; // Bevat alfanumeriek en underscore -> Geldig integer 23; // Alleen cijfers -> Ongeldig
Sleutelwoorden
Sleutelwoorden zijn gereserveerde identifiers voor taalconstructies en zijn in kleine letters. Een lijst met belangrijke sleutelwoorden:
Verilog-revisies
Verilog heeft een paar revisies ondergaan, met toevoegingen van 1995 tot 2001:
Verilog
- Verilog beheersen: Complete tutorial voor digitale schakelingontwerp
- Verilog concatenatie beheersen: Een praktische gids
- Verilog-toewijzingen begrijpen: types, syntax en best practices
- Verilog Blocking vs. Non-Blocking: belangrijkste verschillen uitgelegd
- Verilog-functies beheersen voor efficiënt RTL-ontwerp
- Verilog Tasks begrijpen: Functions vs Tasks, Syntax en Gebruik
- Verilog Clock Generator: Ontwerp & Implementatie Gids
- Verilog Math Functions beheersen voor efficiënt Hardware-ontwerp
- Verilog $timeformat beheersen: Precisie en Weergave-controle
- Verilog Timescales begrijpen en printen in elke Scope
- Verilog File I/O onder de knie: Openen, Lezen, Schrijven en Sluiten