Abend. Ich habe ein recht komplexes (für mich) System auf vielen modulen. Im System gibt es insgesamt 3 Clockdomains: 27Mhz,143Mhz und 49.5Mhz. An sich geht es um das Lesen von TV_eingang , speichern der Daten in SDRAM, und schließlich das Anzeigen des Bildes auf dem VGA-Monitor. Hier ist eine kurze Beschreibung: ADV7180 (video dacoder) liefert Daten @ 27Mhz-->die Daten werden mit diesem Clock verarbeitet und über dual Clock FiFO in den sdram geschoben. Der dual Clock FIFO sowie alle andere weitere Module funktionieren zu 100%. Das habe ich getestet. Auch der 27Mhz Block funktioniert alleine. Nun wenn ich alles zusammen verknüpfe, funktioniert mein System nicht wie es sein soll, anstatt von Bilddaten sehe ich irgendwelche Glitches. Wobei auch dann alles außer 27Mhz Domain funktioniert. Mich macht jetzt folgende Tabelle Sorgen(s.Bild) Aßerdem ist es so, dass der 27Mhz Clock (TDCLK_27)direkt vom VideoDecoder kommt, und ich habe jetzt das Bauchgefühl, dass es keine gute Idee war, diesen Clock für viele Prozesse in FPGA, die auch synchron laufen müssen, zu verwenden.Vllt. zieht das FPGA zu viel strom von diesem ADV7180 Ausgang? Bevor ich anfange, meine Design zu ändern, würde ich gerne ihre Meinung hören.
Ok, ich denke die Idee mit dem Clock und viel Strom ist hier nicht relevant. Ich habe mir noch Time Quest Analyser(kenne damit noch nicht aus) angeschaut. Es gibt viele rote Fehlermeldungen. Im Summary steht folgendes: 1 Short Setup Relationship CONSTRAINTS Paths Affected 20 2 Long Combinational Path HDL Paths Affected 20 Als Lösungsvorschlag steht : 1:Ensure launch and latch clock periods are exact multiples of each other, or force the correct setup relationship with set_max_delay for the path from "Signal in Clockdomain 27Mhz" und "SIgnal in Clockdomain 143Mhz" 2:Reduce the levels of combinational logic for the path from "Signal in Clockdomain 27Mhz" und "SIgnal in Clockdomain 143Mhz" Tja, die Lösung für 1: wäre entweder den Clock für SDRAM so ändern, damit es ein vielfaches von 27Mhz ist.Aber hilft es wirklich? Ich denke die Beste Lösung wäre die Anzahl der kombinatorische Logik zu verkleinern, nur habe ich keine Ahnung wie ich das mache... Ich denke, ich gehe jetzt lieber ist Bett. Hoffentlich erscheint hier ein Vorschlag, wenn ich aufwache:D
Böser Kommunist schrieb: > Im Summary steht folgendes: > > 1 Short Setup Relationship CONSTRAINTS Paths Affected 20 > 2 Long Combinational Path HDL Paths Affected 20 > > Als Lösungsvorschlag steht : > > 1:Ensure launch and latch clock periods are exact multiples of each > other, or force the correct setup relationship with > set_max_delay for the path from "Signal in Clockdomain 27Mhz" und > "SIgnal in Clockdomain 143Mhz" > > 2:Reduce the levels of combinational logic for the path from "Signal in > Clockdomain 27Mhz" und "SIgnal in Clockdomain 143Mhz" > Ich denke, ich gehe jetzt lieber ist Bett. Hoffentlich erscheint hier > ein Vorschlag, wenn ich aufwache:D Mir ist noch nicht völlig klar wo deine probleme sind. Die Meldungen von der Statischen Timining Analyse (STA) sind klar, das passt aber nur bedingt zu dem Fehlerbild: Böser Kommunist schrieb: > Nun wenn ich alles zusammen verknüpfe, funktioniert mein System nicht > wie es sein soll, anstatt von Bilddaten sehe ich irgendwelche Glitches. Meint auf den Datenleitungen (? welche: VGA-RGB, Videosecoder ein/ausgang?) siehst du womit (Scope, Monitor, Logicanalyzer, Simu?) was (?kurze Pulse, Farbige Streifen) und erwartest allerdings (?Pulse definierte Länge, periodische Signale,...) verletzte timings äußeren sich eher mit temperaturabhängigen Aussetzern. Stell erst mal sicher ob der FPGA überhaupt alle 3 Takte intern verteilen kann. Manchmal ist das arg eingeschrankt, manchmal geht das nur quadrantenweise und der Takt wird dann entweder überhaupt nicht oder auf nicht extra clockleitungen geführt was dann wg. Laufzeitunterschieden (skew) kein phasengleiches system mehr ist. Ich bau in meine designs für jede clockdomain ein heartbeat ein, also teiler auf Sekundentakt und lass damit leds blinken oder schau am scope an. Damit erwischt man totalausfallende Takt-domains schnell. Falls du FPGA-interne PLL/DCM oder so an den Takten hast, die haben statussignale (bspw. locked) die man sich auch anschauen kann. Dann können unsaubere taktübergänge Probleme bereiten, insbesonders steuersignale die an statemachines/Zähler führen. Bei statemachines dazu die Zustande überwachen, bspw ein errorpin das aktiv wird wenn ein illagler Zustand (der im others-Zweig) erreicht wird. Oder ein puls aus einer schnellen taktdomain soll was in einer langsamen steuern und wird natürlich nur bei passenden Phasenlagen gesehen. Solche signale zwischen den Taktdomainen kann die STA auflisten wenn ein passendes constraint gesetzt ist. Ich hab schopn länger nicht mehr mit Altera timequest gearbeitet und kann dir das nicht aus dem Ärmel schütteln. Als letzten Schritt dürfen natürlich die Signalpfade in den clockdomains nicht länger sein als der Takt es dort zu läßt (außer bei multicycle). Dazu mal die längsten genau anschauen. Eine pauschale Lösung gibt es dazu nicht. Manchmal hilft es die FSM codierung von binary auf one-hot umzustellen, manchmal muss die Logic verinfacht werden, oder spart sich synchrone resets die man dort nicht wirklich braucht, oder baut FF als Pipilenstages ein, oder man dupliziert FF um die Verdrahtung deren Ausgänge zu vereinfachen, oder platziert per Hand, oder stellt die Optimierung von area auf timing, oder oder oder .... Aber ich bin noch nicht überzeugt das dort das eigentliche Problem liegt, erst mal schauen ob die 3 domains überhaupt laufen und alle Taktübergänge sauber gemacht worden. Manchmal verrät sich mal ein auszählen von Übergänge die ich lt. Blockbild erwarte und Übergänge die wirklich vorhanden sind welche man nicht eingeplant hat - zu 99% sind es diese stellen die die Fehlerursache sind. MfG
Moin, die meisten Tools sollten eigentlich im schematic viewer (z.B. Synopsys) eine Timing-Analyse bereitstellen und dir kritische Pfade anzeigen. Manchmal ist das aber nicht so präzise und man muss im Dunkeln stochern. Manchmal muss man sich auch das Place and Route-Ergebnis ansehen und "raten", woher der ineffiziente Pfad kommt. Generell gewinnt man mit einem Pipeline-Konzept, also kombinatorische Verknüpfungen wie auch mögliche "data enable"-Signale einfach nochmal abtakten. Bei einigen FPGA-Architekturen muss man am RAM z.B. eine weitere Register-Stage einbauen, damit man den vollen Durchsatz hat. Das System muss dann mit einer Latenz auch klarkommen. Falls Du irgendwo Cross-Clockdomain-Logik hast, können die Tools auch manchmal Stress machen, obwohl alle Partitionen für sich keine Skewing-Probleme aufweisen. Das habe ich bei handgestrickten FIFOs des öfteren festgestellt. In dem Fall einfach die FIFOs aus den Core-Generatoren erstellen. Hoffe es hilft dir weiter, von aussen halt immer schwer zu sagen. Viel Glück!
Vielen Dank für ihre Vorschläge. Ich denke ich habe tatsächlich viele Operationen in 27Mhz Domain für gleichzeitige Bearbeitung gelassen. Jetzt will ich einzelne Prozesse als Pilepeline beschreiben. So hab ich es gemacht:
1 | PROCESS(TD_CLK27) |
2 | begin
|
3 | for i in 0 to 3 loop |
4 | case i is |
5 | when 0=> |
6 | Datain<=TD_DATA; |
7 | when 1=> |
8 | BT656_Converter_IN<=Datain; |
9 | when 2=> |
10 | Raw_DATA<=BT656_Converter_OUT; |
11 | when 3=> |
12 | YCrCb_TO_RGB_IN<=Raw_Data; |
13 | when 4=> |
14 | RED_COMPONENT<=YCrCb_to_RGB_OUT_RED; |
15 | end case; |
16 | |
17 | end loop; |
18 | end process; |
LEider hat es nichts gebracht, außerdem sehe ich in Technology Map Viewer sehe ich die zusätzliche Register(Datain,Raw_DATA,RED_COMPONENT) nicht. Ich habe eine ähnliche Pipelinekonstruktion für einen Multiplier gebaut, und dort sieht man jeweils ein FF zwischen jede Stufe, außerdem werden auch Zwischensignale sichtbar. Hier sieht es so aus, als ob der Compiler meine Bemühungen weg optimiert hat. Woran kann es liegen?
Böser Kommunist schrieb: > Hier sieht es so aus, als ob der Compiler meine Bemühungen weg > optimiert hat. > Woran kann es liegen? am fehlenden if rising_edge(TD_CLK27) then ... MfG,
Verdammt, rising edge habe ich übersehen... Mit rising_endge sieht es so wie es sein soll. Leider bringt diese Pipeline Änderung nichts, das Problem besteht immer noch. Außerdem habe ich den Clock in 27 MHZ Domain überwacht(mit der LED methode), der funktioniert problemlos. Ich weiss, mein Code sieht einwenig groß aus, aber man muss nur den 27 MHZ domain anschauen, vllt fällt jemandem auf was ich falsch mache, manchmal fokussiert man sich auf einen ganz falschen Weg und sieht das offensichtliche nicht. CCD.vhd ist die Top-Entity.Oben stehen zwei kleine TD_CLK27 Prozesse die offensichtlich das Problem machen -------weitere Kompoenente, die im 27MHZ Domain arbeiten--------- YCrCr_to_RGB<= ein einfaches Komponent, konvertiert YCrCb ins RGB. BT656<= decodiert den BT656 Video Protokol. Detektiert Bildanfang, Bildende, AktivVideo etc. Nichts besonderes: getestet, funktioniert. Gray<=Dient für Dual Clock FIFO,ein Binary_to_Gray Konverter. Falls jemand den Blick drauf wirft, wäre ich äußerst dankbar:)
Eine passende Testbench hast Du nicht gerade zur Hand, oder? Duke
Leider nicht. Bin ein Fpga Anfänger...
Böser Kommunist schrieb: > Jetzt will ich einzelne Prozesse als Pilepeline beschreiben. > So hab ich es gemacht: ... Böser Kommunist schrieb: > Leider bringt diese Pipeline Änderung nichts, das Problem besteht > immer noch. Das ist ja auch keine Pipeline im eigentliche Sinne, denn die bringt nur Latency. Die ganze Schleife wird einfach so abgerollt, dass hinterher genau das hier rauskommt:
1 | Datain<=TD_DATA; |
2 | BT656_Converter_IN<=Datain; |
3 | Raw_DATA<=BT656_Converter_OUT; |
4 | YCrCb_TO_RGB_IN<=Raw_Data; |
5 | RED_COMPONENT<=YCrCb_to_RGB_OUT_RED; |
Und diese ganze Schleifen im Prozess in YCrCb_to_RGB.vhd sind ebenso nutzlos und werden exakt so umgesetzt:
1 | PROCESS(YCLK) |
2 | BEGIN
|
3 | IF rising_edge(YCLK)THEN |
4 | Temp_CrR1<=to_integer(unsigned(Cr)-128)*11; |
5 | EN0<=ENABLEIN; |
6 | Temp_CrR2<=Temp_CrR1/8; |
7 | EN1<=EN0; |
8 | Rv<=to_integer(unsigned(Y))+Temp_CrR2; |
9 | EN2<=EN1; |
10 | IF(Rv<255)THEN |
11 | R<=STD_LOGIC_VECTOR(to_unsigned(Rv,8)); |
12 | ELSE
|
13 | R<=(others=>'1'); |
14 | END IF; |
15 | ENABLEOUT<=EN2; |
16 | |
17 | Temp_CbG1<=to_integer(unsigned(Cb)-128)*11; |
18 | Temp_CrG1<=to_integer(unsigned(Cr)-128)*23; |
19 | Temp_CbG2<=Temp_CbG1/32; |
20 | Temp_CrG2<=Temp_CrG1/32; |
21 | Gv<=to_integer(unsigned(Y))-Temp_CbG2-Temp_CrG2; |
22 | IF(Gv<255)THEN |
23 | G<=STD_LOGIC_VECTOR(to_unsigned(Gv,8)); |
24 | ELSE
|
25 | G<=(others=>'1'); |
26 | END IF; |
27 | |
28 | Temp_CbB1<=to_integer(unsigned(Cb)-128)*27; |
29 | Temp_CbB2<=Temp_CbB1/16; |
30 | Bv<=to_integer(unsigned(Y))+Temp_CbB2; |
31 | IF(Bv<255)THEN |
32 | B<=STD_LOGIC_VECTOR(to_unsigned(Bv,8)); |
33 | ELSE
|
34 | B<=(others=>'1'); |
35 | END IF; |
36 | END IF; |
37 | END PROCESS; |
Deine Beschreibung und meine "reduzierte" Beschreibung sind funktionell und vom ergebnis her gleichwertig. Mach dich einfach mal zum Verhalten von Signalen in Prozessen schlau. Und infor miere dich, wie Schleifen in VHEL umgesetz werden. Das ist unbedingt nötig...
Hallo Lothar, Ja ich weiss das die For-Schleife hier (in YCrCb Koverter) keinen Zweck erfüllt, ich habe einfach die Pipeline Beispiele mit "for" und ohne gesehen. Die For-Schleife lasse ich bloss für Übersichtlichkeit. Ich dachte es wird helfen, wenn im 27Mhz-Domain ich die Zwischenergebnisse abspeichere. ursprunglich hatte ich es so stehen:
1 | |
2 | |
3 | |
4 | u4: component YCrCb_to_RGB |
5 | port map ( |
6 | YCLK=>TD_CLK27, |
7 | Y=>Comp_Y, |
8 | Cr=>Comp_Cr, |
9 | Cb=>Comp_Cb, |
10 | R=>Comp_R, |
11 | G=>Comp_G, |
12 | B=>Comp_B, |
13 | enablein=>validin, |
14 | enableout=>validout |
15 | );
|
16 | u3 : component BT656 |
17 | port map ( |
18 | clkin=>TD_CLK27, |
19 | datain=>TD_DATA, |
20 | dataout=>BT656_DATA, |
21 | endfrm=>ENDFRAME, |
22 | capen=>BT656_ENABLE, |
23 | venable=>VID_ENABLE, |
24 | beginfrm=>BEGINFRAME |
25 | );
|
26 | |
27 | |
28 | PROCESS(TD_CLK27) |
29 | BEGIN
|
30 | |
31 | |
32 | IF (RST2_2='1') then |
33 | BT656_ENABLE<='0'; |
34 | |
35 | INIT<='0'; |
36 | validin<='0'; |
37 | STATE_FLAG<='1'; |
38 | STATE<=GETCB; |
39 | ELSIF rising_edge(TD_CLK27)then |
40 | BT656_ENABLE<='1'; |
41 | if(VID_ENABLE='1')then |
42 | CASE STATE IS |
43 | WHEN GETCB=> |
44 | validin<='0'; |
45 | Comp_Cb<=BT656_DATA; |
46 | STATE<=GETY; |
47 | STATE_FLAG<='1'; |
48 | WHEN GETCR=> |
49 | |
50 | IF(INIT='0')THEN |
51 | validin<='1'; |
52 | INIT<='1'; |
53 | else
|
54 | validin<='0'; |
55 | END IF; |
56 | STATE<=GETY; |
57 | Comp_Cr<=BT656_DATA; |
58 | STATE_FLAG<='0'; |
59 | WHEN GETY=> |
60 | IF(INIT='1')then |
61 | validin<='1'; |
62 | |
63 | end if; |
64 | Comp_Y<=BT656_DATA; |
65 | IF(STATE_FLAG='1')THEN |
66 | STATE<=GETCR; |
67 | ELSE
|
68 | STATE<=GETCB; |
69 | END IF; |
70 | END CASE; |
71 | ELSE
|
72 | validin<='0'; |
73 | STATE_FLAG<='1'; |
74 | STATE<=GETCB; |
75 | end if; |
D.h. der Ausgang aus einem Komponent war diirekt der Eingang von dem Nächsten, es war praktisch schon eine Pipeline Konstruktion, so wie ich es verstehe. Leider hat es auch so nicht funktioniert
:
Bearbeitet durch User
Ok, es wird noch schlimmer... Zum Testen habe ich ein TV-Demo-Design (geliefert von terasic, ich benutze DE1-SoC) auf das Board geladen, um zu sehen ob alles funktioniert. Tatsächlich funktioniert alles. Auf dem Monitor erscheint das Bild von meiner CCD Kamera, alle sind glücklich. Nun habe ich das von terasic geliefertes Demo auf meiner Maschine neu kompiliert und wieder hochgeladen: Das Design funktioniert nicht mehr, das Bild ist nicht synchronisiert (fliegt von oben nach unten), die Farben werden verzerrt wiedergegebenen, der Bildschirm blinkt manchmal... Ok, dachte ich, vllt sind meine Kompiler-Einstellungen anders, deswegen geht es nicht. Default design(frisch aus dem zip. File,ohne Änderungen)wieder hochgeladen: das Problem bleibt bestehen. Das Board ausgeschaltet, Strom getrennt, wieder eingeschaltet, default Design drauf: Das Problem ist immer noch da. Wie kann es denn sein? Vorher hat das Demo funktioniert, jetzt nicht mehr? Vllt ein Hardwaredefekt auf dem Board..?
Gibt es da irgendwelche Konfigurations-Proms auf dem board? Oder Chips, die selber konfiguriert werden muss und nun "verstellt" sein könnten?
Bitte melde dich an um einen Beitrag zu schreiben. Anmeldung ist kostenlos und dauert nur eine Minute.
Bestehender Account
Schon ein Account bei Google/GoogleMail? Keine Anmeldung erforderlich!
Mit Google-Account einloggen
Mit Google-Account einloggen
Noch kein Account? Hier anmelden.