Hallo Zusammen,
ich versuche für die HS einen VierBitZähler mit Lattice Diamond zu
programmieren und bin noch recht neu in der Materie.
1
libraryieee;
2
useieee.std_logic_1164.all;
3
4
entitycount4is
5
port(
6
CLK,RD:instd_logic;
7
Q:outstd_logic_vector(3downto0)
8
);
9
endentitycount4;
10
11
architecturebehaviorofcount4is
12
begin
13
count:process(CLK,RD)is
14
typeint15isrange0to15;
15
variablecount_value:int15;
16
variablesum:int15;
17
variablei:int15;
18
variablerest:int15;
19
variabley:std_logic_vector(3downto0);
20
21
begin
22
-- Reset
23
24
ifRD='1'
25
count_value:=0;
26
else
27
28
-- Zaehler
29
ifCLK'eventandCLK='1'then
30
ifcount_value<15then
31
count_value:=count_value+1;
32
else
33
count_value:=0;
34
endif;
35
endif;
36
endif;
37
38
-- Umsetzung Integer in Bit Vektor
39
sum:=count_value;
40
foriin0to3loop
41
rest:=summod2;
42
sum:=sum/2;
43
ifrest=1then
44
y(i):='1';
45
else
46
y(i):='0';
47
endif;
48
endloop;
49
Q<=y;
50
51
endprocesscount;
52
53
endarchitecturebehavior;
Das hab ich bis jetzt zustande gebracht, aber das Programm schreit in
Zeile 25,26,36 immer Syntaxfehler. Aber ich seh einfach nicht was falsch
ist.
Kann mir jemand sagen was genau ich verändern muss?
Vielen Dank schon mal im Voraus.
MfG April
April206 schrieb:> Aber ich seh einfach nicht was falsch> ist.
Da hast Du wohl nicht richtig hingeguckt: jedes 'if' braucht ein 'then'.
Sonst gibt's halt einen Syntaxfehler.
April206 schrieb:> Das hab ich bis jetzt zustande gebracht, aber das Programm schreit in> Zeile 25,26,36 immer Syntaxfehler.
Und sonst gar nichts?
> Kann mir jemand sagen was genau ich verändern muss?
Du solltest weniger Variablen verwenden. Und wenn, dann nur dort, wo sie
gebraucht werden. Für einen 4 Bit Zähler braucht man nicht mal eine
einzige.
Oder andersrum: an der völlig unnötigen Verwendung von Variablen erkennt
man den Softwareentwickler, der jetzt auch noch Hardware beschreiben
will/soll/muss... ;-)
Das sieht man dann auch an der beliebigen Struktur des Prozesses und
seiner unvollständigen Sensitivliste. Sieh mal in dein VHDL Buch:
entweder ist ein Prozess synchron oder kombinatorisch. Aber nicht
irgendeine vogelwilde Kombination von beiden.
BTW: bitte künftig die [ vhdl ] Tags verwenden.
Zur exzessiven und unnoetigen Verwendung von Variablen sowie einem
verschrobenen Prozess mit asynchronem Reset, Clock, und dem
Variablengedoens hat Lothar ja schon was geschrieben... So beschreibt
man keine HW...
Diamond hat auch einen Template Editor, weis jetzt nicht genau wo, aber
muesste man im Menue aufrufen koennen.
Da sind Code gerueste fuer die meissten Standardsachen drin. Auch
Zaehler. Waere in Deinem Fall ein guter Startpunkt.
berndl schrieb:> Zeile 25,26 duerfte das hier sein:> rest := sum mod 2;> sum := sum/2;> Ist auch klar, wenn oben nur steht:use ieee.std_logic_1164.all;
Nö.
Zum Rechnen mit integern braucht's nur die std Library, und die steckt
schon im Compiler.
Zeile 25 ist das da:
April206 schrieb:> if RD = '1'> count_value := 0;> else
Und da muss man nicht lange suchen, wo der Fehler steckt.
berndl schrieb:> Zur exzessiven und unnoetigen Verwendung von Variablen sowie einem> verschrobenen Prozess mit asynchronem Reset, Clock, und dem> Variablengedoens hat Lothar ja schon was geschrieben... So beschreibt> man keine HW...
Es gibt keine Regel (ausser der Lothar'schen ;) ), die die Verwendung
von Variablen untersagt. Variablen sind ein reguläres Sprachelement von
VHDL. Wenn der TO es in der Vorlesung schon behandelt hätte, hätte er
dort, wo "exzessiv" Variablen verwendet werden, wahrscheinlich
1
q<=std_logic_vector(unsigned(sum,q'length));
geschrieben.
Schaut man in die entsprechenden Funktionen in ieee.std_logic_1164 und
numeric_std, sehen die im Inneren höchstwahrscheinlich sehr ähnlich oder
genauso aus. Und benutzen - unerhörterweise - genauso "exzessiv"
Variablen.
Markus F. schrieb:> Es gibt keine Regel (ausser der Lothar'schen ;) ), die die Verwendung> von Variablen untersagt. Variablen sind ein reguläres Sprachelement von> VHDL. Wenn der TO es in der Vorlesung schon behandelt hätte, hätte er> dort, wo "exzessiv" Variablen verwendet werden, wahrscheinlich> q <= std_logic_vector(unsigned(sum, q'length));>> geschrieben.
Es sind ja nicht die Regeln, sondern die Erfahrung, die lehrt, das
variables von VHDL-Anfängern sehr oft falsch verstanden benutzt werden,
was zu einer vermeidbar unnötig langen Lernphase führt.
Ist vielleicht wie mit 'goto', - das ist auch ein reguläres Sprachmittel
in C, trotzdem wird tunlichst davon abgeraten es zu benutzen, weil es zu
schwer wartbaren Code führt, man sich sozusagen selbst ins Knie
schiesst.
Markus F. schrieb:> Variablen sind ein reguläres Sprachelement von VHDL.
Aber eben nicht so, wie sie von C Programmierern dann in ihrem VHDL
Programm eingesetzt werden.
Wer dann das kapiert hat, was im
Beitrag "Variable vs Signal" abgehandelt ist, der
braucht schon gleich gar nicht so viele Variablen.
Lothar M. schrieb:> Aber eben nicht so, wie sie von C Programmierern dann in ihrem VHDL> Programm eingesetzt werden.
Doch, genauso.
Es sind die Signale, die sich "anders" verhalten.
Was der C-Programmierer lernen muß, ist
1. dass sich Signale eben anders verhalten als Variablen (die er kennt)
2. dass er auf Signale nicht verzichten kann, weil VHDL-Variablen
ausserhalb von Prozeduren und Funktionen nur sehr eingeschränkt
(als "Zwischenergebnis") verwendbar sind
3. dass er sich deswegen ganz schnell damit beschäftigen (und
verinnerlichen) sollte, was bei Signalen anders ist
Markus F. schrieb:> Was der C-Programmierer lernen muß, ist>> 1. dass sich Signale eben anders verhalten als Variablen (die er kennt)> 2. dass er auf Signale nicht verzichten kann, weil VHDL-Variablen> ausserhalb von Prozeduren und Funktionen nur sehr eingeschränkt> (als "Zwischenergebnis") verwendbar sind> 3. dass er sich deswegen ganz schnell damit beschäftigen (und> verinnerlichen) sollte, was bei Signalen anders ist
Nein, der C-Programmierer muß, wenn er synthesefähigen Code schreiben
will, lernen:
* Was die Grundelemente digitaler Logic sind (Kombinatorik und Speicher
(sequentiell))
* Wie die Templates für diese aussehen (FF, Muxer, shiftreg, encoder,
FSM, embedded ROM, RAM,..) und benutzt werden
* Wie man RTL und structural code schreibt
und weil zur synthese die simulation gehört, muss er/sie ebenfalls
lernen
* wie man eine Testbench aufsetzt, schreibt und den simulator bedient
Das ist IMHO der schnellere Weg als mit "Try und error" herauszufinden
was das Synthesetool jetzt eigentlich erwartet und das es mit anderen
syntaktisch korrekten strukturen nicht tut.
Also einfach mal den "Synthesis code style guide durcharbeiten", bevor
man mit dem Schreiben der erste Codezeile anfängt.
https://www.xilinx.com/support/documentation/sw_manuals/xilinx14_7/sim.pdfhttps://www.google.com/url?sa=t&rct=j&q=&esrc=s&source=web&cd=1&ved=2ahUKEwjcw66t59fnAhVMQEEAHQ2SDNIQFjAAegQIBBAB&url=http%3A%2F%2Fwww.latticesemi.com%2F~%2Fmedia%2FLatticeSemi%2FDocuments%2FUserManuals%2FEI%2FHDLcodingguidelines.pdf%3Fdocument_id%3D48203&usg=AOvVaw2GxKAE8jNOXddev6DF_06K
Markus F. schrieb:> Lothar M. schrieb:>> Aber eben nicht so, wie sie von C Programmierern dann in ihrem VHDL>> Programm eingesetzt werden.> Doch, genauso.> Es sind die Signale, die sich "anders" verhalten.
Es ist die gesamte "Programmiersprache" samt Variablen und Schleifen und
wasweißichauchimmer, die sich völlig anders verhält... ;-)
Denn schon allein der überaus eingeschränkte Einsatzbereich von
Variablen und das kuriose Verhalten einer for-Schleife sollte dem
C-Programmierer zeigen: das, was sich da Variable oder Schleife nennt,
ist offenbar ganz was anderes, als das, was ich bisher so kenne.
Beim Englisch-Lernen nennt man sowas "false friends": man meint, die
Bedeutung eines Wortes schon zu kennen. Lass einfach mal jemand
"silicon" ins Deutsche übersetzen. Oder "Silikon" ins Englische.
Und genauso geht es mit "variable" in VHDL und in C.
> Was der C-Programmierer lernen muß, ist> 2. dass er auf Signale nicht verzichten kann, weil VHDL-Variablen> ausserhalb von Prozeduren und Funktionen nur sehr eingeschränkt> (als "Zwischenergebnis") verwendbar sind
Dass besagter C-Programmierer im Fall einer Variablen dann auf die Idee
kommt, eine auch ausserhalb von Prozessen global gültige "shared
variable" einzusetzen, ist nur der nächste "logische" Irrschritt.
Markus F. schrieb:> berndl schrieb:>> Zeile 25,26 duerfte das hier sein:>> rest := sum mod 2;>> sum := sum/2;>> Ist auch klar, wenn oben nur steht:use ieee.std_logic_1164.all;>> Nö.>> Zum Rechnen mit integern braucht's nur die std Library, und die steckt> schon im Compiler.
hmmmm, wo hat er da Integer? Er hat einen neuen Typ definiert:
1
typeint15isrange0to15;
2
variablecount_value:int15;
3
variablesum:int15;
4
variablei:int15;
5
variablerest:int15;
Gilt dann dafuer Division und Modulo?
>> Zeile 25 ist das da:>> April206 schrieb:>> if RD = '1'>> count_value := 0;>> else
das ist nochmal ein Syntaxfehler. Ich vermute mal, der oben gepostete
Teil passt nicht ganz zur Fehlermeldung.
Die Zeilennummern 25, 26 und 36 wuerden gut zu meiner Vermutung passen
wenn Zeile 36 die letzte waere...
berndl schrieb:>> das ist nochmal ein Syntaxfehler. Ich vermute mal, der oben gepostete> Teil passt nicht ganz zur Fehlermeldung.>> Die Zeilennummern 25, 26 und 36 wuerden gut zu meiner Vermutung passen> wenn Zeile 36 die letzte waere...
Uebrigens: In Diamond ist es auch so, dass immer nur einige Fehler
angezeigt werden, wenn es zu viele gibt.
Die muss man dann erst beheben, dann kommen neue Fehlermeldungen. :-)
hey April206
hinter einem if fehlt einfach nur ein then
um genau zu sein hier
>> if RD = '1' "then">> count_value := 0;>> else
dann läuft dein Zähler.
LG