Hallo Leutz
Ich programmiere hier mit meinem Spartan 3AN Starter Kit und bin gerade
dabei eine 4 Stellige 7-Segmentanzeige an zu steuern. Hier erstmal mein
Programm:
--hier wird der Takt für das weiterschalten der Segment Stelle generiert
38
segclock:process
39
begin
40
waituntilrising_edge(clk);
41
if(segclkx<4999)then
42
segclkx<=segclkx+1;
43
segclk<='0';
44
else
45
segclkx<=0;
46
modi<=modi+1;
47
if(modi=3)then
48
modi<=0;
49
endif;
50
segclk<='1';
51
endif;
52
endprocesssegclock;
53
--der Schalter wählt zwei verschiedene Texte aus
54
schalt:process(schalter)
55
begin
56
if(schalter='1')then
57
-- abcdefgD
58
seg1<="10010001";-- H
59
seg2<="01001001";-- S
60
seg3<="11111101";-- -
61
seg4<="11100011";-- L
62
else
63
seg1<="00100100";-- 2
64
seg2<="00000011";-- 0
65
seg3<="10011111";-- 1
66
seg4<="00100101";-- 2
67
endif;
68
endprocessschalt;
69
--hier werden werden die einzelnen Stellen und Bitmuster geladen
70
segment:process
71
begin
72
waituntilrising_edge(segclk);
73
if(modi=0)then
74
segled<=seg1;
75
segstelle<="0111";
76
elsif(modi=1)then
77
segled<=seg2;
78
segstelle<="1011";
79
elsif(modi=2)then
80
segled<=seg3;
81
segstelle<="1101";
82
elsif(modi=3)then
83
segled<=seg4;
84
segstelle<="1110";
85
endif;
86
endprocesssegment;
87
-- übertrag des Anzeigewertes auf die LED
88
led<=x;
89
90
endBehavioral;
So und nun zu meinem Problem. Die Anzeigen auf der Segmentanzeige
stimmen nicht. Laut Test Bench läuft das Programm korrekt. Jedoch auf
dem Bord sind immer wieder einzelne Segmente falsch oder ganze Stellen
werden vertauscht. Um zu sehen ob es sich um falsches Bitmuster handelt
habe ich einfach mal ein einzelnes Segment Z.B. einen Punkt mit
eingefügt also aus:
1
seg4<="00100101";
einfach:
1
seg4<="00100100";
Jetzt sollte sich ja auf der Anzeige nur dieser Punkt ändern aber nein
es verändert sich die kommplette Anzeige. Wie schon gesagt in der Test
Bench läuft alles korrekt. Da muss doch irgend was beim übersetzen
schief laufen?
Was sagen deine LOC? Stimmen die? Oder hast Du welche vergessen?
Wo ist die PLL?
Oder Du hast ein Startproblem und einer der Counter arbeitet nicht mit
dem Startwert, den Du Dir denkst.
Was sagt ChipScope?
> ledclock: process> begin> wait until rising_edge(clk);
das funktioniert in der Simulation, aber in der Synthese nicht!
Verwende
if rising_edge(clk) then
> if (c<24999999) then> c <= c+1;> else> c <= 0;> x <= not x;> end if;
end if;
> end process ledclock;
In diesem Prozess ein ganz böses Faul indem du hier den clock "segclk"
verwendest. Dieser kommt von der Logic und ist einfach nur Pfui. Lass
diesen Prozess mit deinem "clk" laufen und verwende ein clock enable
signal von dem Prozess, wo du deinen Takt langsamer machst.
z.B.
if rising_edge(clk) then
if segclk_en = '1' then
-- hier code für langsame Takt
end if;
end if;
> --hier werden werden die einzelnen Stellen und Bitmuster geladen> segment: process> begin> wait until rising_edge(segclk);> if (modi = 0) then> segled <= seg1;> segstelle <= "0111";> elsif (modi = 1) then> segled <= seg2;> segstelle <= "1011";> elsif (modi = 2) then> segled <= seg3;> segstelle <= "1101";> elsif (modi = 3) then> segled <= seg4;> segstelle <= "1110";> end if;> end process segment;> -- übertrag des Anzeigewertes auf die LED> led <= x;>> end Behavioral;So und nun zu meinem Problem. Die Anzeigen auf der Segmentanzeige
L. schrieb:> das funktioniert in der Simulation, aber in der Synthese nicht!
wait until rising_edge funktioniert auch in der Synthese.
Die Sensitivity List sollte nur wie in dem Beispiel leer sein sowohl für
sim als auch syn.
ok, nehm ich zurück. Ist mir so noch nie untergekommen. Ist das die
feine Art das so zu machen?
Kann man damit in einem Prozess auch zweim "wait until rising_edge"
verwenden?
Danke L. jetzt funktioniert es auf anhieb.
Hm da sollte ich wohl mein Programmierstyl verbessern.
Weis jemand wo es ein gescheites freies Toturial für VHDL? Die Dinger
die ich hier auf der Seite gefunden habe sind irgend wie alle Mist ->
http://www.mikrocontroller.net/articles/VHDL
kannst du deinen Code nochmal posten?
auf anhieb habe ich leider keine Literatur zur Hand. Vielleicht finde
ich auf die schnelle was brauchbares. Ich mein mal eins von Xilinx
gesehen zu haben ...
Ben S. schrieb:> Ich programmiere hier mit meinem Spartan 3AN Starter Kit und> bin gerade dabei eine 4 Stellige 7-Segmentanzeige an zu steuern.
Nur interessehalber: Was ist das für ein Board? Auf dem
Spartan-3AN Starterkit (von Xilinx) ist ein LCD-Display,
keine 7-Segmentanzeige.
Ja die Segmentanzeige habe ich mir selber gebaut. Da hat wieder einer
Aufgepasst ;)
Ich suche eigentlich nen deutsch sprachiges Tutorial, ich hasse englisch
und das verlängert die Lernphase ungemein.
Hier nochmal der fertige Coode:
gerhard schrieb:> Die Initialisierungen in der Deklaration der signals haben für die> Synthese keinerlei Bedeutung.
Die Synthesizer können das heutzutage für alle SRAM-basierten FPGAs. Und
die müssen zum Power-Up sowieso erst mal geladen werden. Speziell für
Xilinx: siehe das WP272, in dem vorrangig der Reset abgehandelt wird,
und als Abhilfe für den "Entwickler-Reset-Knopf" eben diese Defaultwerte
empfohlen werden.
L. schrieb:>> wait until rising_edge(clk);> das funktioniert in der Simulation, aber in der Synthese nicht! Verwende> if rising_edge(clk) then
Natürlich funktioniert das tadellos:
http://www.lothar-miller.de/s9y/archives/16-Takt-im-Prozess.htmlz
Die Synthese kann sogar noch einiges mehr:
http://www.lothar-miller.de/s9y/archives/47-wait-im-Prozess.html> In diesem Prozess ein ganz böses Faul indem du hier den clock "segclk"> verwendest
Richtig! Denn damit werden hier zwei Taktdomänen aufgemacht, mit allen
resultierenden Seitenwirkungen. Und insbesondere die unkalkulierbare
Laufzeit des hier im Routign-Netzwerk verteilten Taktes ist
unkalkulierbar und bringt seltsame Effekte mit sich...
TittiKlopper schrieb:>>Kann man damit in einem Prozess auch zweim "wait until rising_edge">>verwenden?> Simulation: Ja> Synthese: Nein
Wie schon im Beitrag "Re: ISE übersetzt irgend wie nur Mist"
gepostet: wenn die Rahmenbedingungen passen (nur 1 Takt, nur 1 Flanke),
ist die Antwort beidesmal "Ja".
Der Ausgangspunkt war der Beitrag "Tesbench synthetisierbar machen".
hjk schrieb:> wait until rising_edge funktioniert auch in der Synthese.> Die Sensitivity List sollte nur wie in dem Beispiel leer sein sowohl für> sim als auch syn.
Sie muss leer sein, denn ein Prozess mit Sensitivliste ist nicht
anderes, als der einfachste vorstellbare Prozess mit nur einem einzigen
"wait until"...
Eine Sensitivliste ist also nur ein (einziges) "wait until" ganz am
Anfang eines Prozesses.
>Die Synthese kann sogar noch einiges mehr:>http://www.lothar-miller.de/s9y/archives/47-wait-i...
Man kann einem Anfänger doch nicht so ein Gerotze als Lern-Standard
vorsetzen! Nachher denkt man noch, dass man jede Zustandsmaschine so
beschreiben könne ...
Also bleibe ich dabei:
Simulation: Ja
Synthese: Nein
TittiKlopper schrieb:> Man kann einem Anfänger doch nicht so ein Gerotze als Lern-Standard> vorsetzen!
Das ist Deine persönliche Meinung.
Und das auch.
TittiKlopper schrieb:> Simulation: Ja> Synthese: Nein
Ich weiß Lothars Kompetenz und Engagement zu schätzen. Wenn Du das nicht
kannst, behalte Deine Meinung für Dich.
Dann kann ich in Ruhe meine Prozesse weitersynthetisieren:
Duke, dein Prozess ist völlig in Ordnung.
Wir sprachen jedoch von mehrerern "wait until rising_edge"-Abfragen in
einem Prozess.
Ich behalte meine Meinung nicht für mich, weil es einfach nur ein Unding
ist, Zustandsmaschinen wie von Lothar vorgeschlagen (für die Synthese)
so zu beschreiben.
Pro (Synthese-)Prozess darf es nur eine "wait until
rising_edge"-Anweisung geben. Alles andere ist Synthese-Tool-Luxus und
kein Standard.
TittiKlopper schrieb:> Man kann einem Anfänger doch nicht so ein Gerotze als Lern-Standard> vorsetzen! Nachher denkt man noch, dass man jede Zustandsmaschine so> beschreiben könne ...
Das wird der geneigte Anfänger dann schon merken, dass es so nicht geht.
Der dazu nötige Prozess heißt "Lernen". Was ist an "Lernen" so schlimm?
> Man kann einem Anfänger doch nicht so ein Gerotze als Lern-Standard> vorsetzen!Ich habe nicht behauptet, dass man das so machen solle. Ich selber war
sehr verwundert, dass das überhaupt geht. Und habe dann ausprobiert, wie
weit man da gehen kann.
> Pro (Synthese-)Prozess darf es nur eine "wait until rising_edge"> Anweisung geben. Alles andere ist Synthese-Tool-Luxus
Ein Blick über den Tellerrand kann nämlich nicht schaden. So sieht man
schnell mal, wieviel "Luft " man noch hat...
> und kein Standard.
Standard? Dann müssen wir uns auf den kleinsten gemeinsamen Nenner
beziehen und noch heute die Prozesse wie in den Lehrbüchern aus dem
letzten Jahrtausend schreiben:
1
process(reset,clk)begin...
Und dass das abhängig von der FPGA-Familie Murks (bei Xilinx) oder
überaus hilfreich (Lattice MachXO) ist, das kann man in den
entsprechenden AppNotes der Hersteller nachlesen.
Da findet man z.B. auch raus, dass beim Spartan 6 ein Initialwert
idealerweise gleich einem Reset-Wert sein sollte, weil dann Kombinatorik
gespart wird...
> und kein Standard.
Nehmen wir man den hier:
http://www.lothar-miller.de/s9y/archives/79-use_new_parser-YES.html
Was beim einen Parser "Standard" ist (Synplify) kann XST nicht. XST
kanns aber, wenn man den neuen Parser nimmt. Dazu auch die Beiträge:
https://www.mikrocontroller.net/search?query=use_new_parser
Und: was ist denn jetzt Standard?
VHDL selber kann das alles schon und noch viel mehr...
Duke Scarring schrieb:> Dann kann ich in Ruhe meine Prozesse weitersynthetisieren:
In locker 95% aller Fälle kommt man so komplett synchron und
beschwerdefrei mit korrekten Simulationen auch ohne VHDL 2008 durchs
Leben...
>Ein Blick über den Tellerrand kann nämlich nicht schaden.
Einen solchen Blick kann man wagen, wenn man den Weg vom Tellerboden zum
Tellerrand hinter sich hat.
>Sonst würden wir heute noch die Prozesse wie in den>Lehrbüchern aus dem letzten Jahrteusend schreiben:>process (reset, clk) begin ...
Habe hier Bücher aus diesem Jahrtausend herumliegen (201x), die allesamt
nach wie vor "process(reset, clk)" verwenden.
TittiKlopper schrieb:> Habe hier Bücher aus diesem Jahrtausend herumliegen (201x), die allesamt> nach wie vor "process(reset, clk)" verwenden.
Traurig, daß es die Bücher noch nicht bis zum Tellerand geschafft
haben...
TittiKlopper schrieb:> Alles andere ist Synthese-Tool-Luxus und> kein Standard.
Was Standard ist und was nicht findet sich in: IEEE Std 1076.6(tm)-2004
IEEE Standard for VHDL Register Transfer Level (RTL) Synthesis
Da findet man auch den folgenden Abschnitt: 6.1.3.4 Edge-sensitive
storage with multiple waits
Dort gibt es z.B. folgendes Beispiel:
TittiKlopper schrieb:> Habe hier Bücher aus diesem Jahrtausend herumliegen (201x), die allesamt> nach wie vor "process(reset, clk)" verwenden.
Erschütternd, nicht wahr?
Insbesondere, wenn dann noch eines davon in einer speziellen Spartan 3
Version (ISBN 0470185317) diese Konstrukte in sträflicher Weise
anpreist, völlig das Xilinx Whitepaper WP272 missachtend...
Duke Scarring schrieb:> IEEE Standard for VHDL Register Transfer Level (RTL) Synthesis> Da findet man auch den folgenden Abschnitt:> 6.1.3.4 Edge-sensitive storage with multiple waitsTittiKlopper schrieb:> Das Beispiel aus dem IEEE-Standard führt unter SynplifyPro (F-2011.09L)> zu folgender Fehlermeldung:>> All waits in a process must be identical
Also hat noch nicht mal Synplify einen gewissen "Standard" erreicht...
Die Synthesizerhersteller haben noch zu tun.
TittiKlopper schrieb:> Lothar, was macht das Synthese-Tool, wenn am Ende des Prozesses ein wait> steht?
Ich würde sagen, das Design kommt nicht weit über den Parser raus:
>> All waits in a process must be identical