logo elektroda
logo elektroda
X
logo elektroda
REKLAMA
REKLAMA
Adblock/uBlockOrigin/AdGuard mogą powodować znikanie niektórych postów z powodu nowej reguły.

[FPGA][ALTERA/INTEL] Simulation Waveform - nieoczekiwane stany Unknown Forcing

matti0010 23 Kwi 2019 20:59 543 11
REKLAMA
  • #1 17922629
    matti0010
    Poziom 11  
    Posty: 319
    Pomógł: 8
    Ocena: 25
    Witam,

    Mam problem z symulacją w Quartus pamięci RAM, która jest komponentem IP (megafunkcja). Wszystko jest dobrze jeżeli wykonuję symulację samej pamięci RAM. Problem pojawia się gdy symuluję większą część układu, w skład której wchodzi pamieć RAM. Próbowałem różnych ustawień megafunkcji i samego Quartusa. W efekcie widziałem różnego rodzaju zmiany ale nadal pojawiało się sporo Unknown Forcing (X). Można to zobaczyć na poniższej grafice (jest to wyjście pamięci RAM):
    [FPGA][ALTERA/INTEL] Simulation Waveform - nieoczekiwane stany Unknown Forcing

    Mam taki problem tylko z pamięciami RAM.
    Pamięć RAM jest zainicjalizowana, tak samo wszystkie "zmienne" w kodzie.
    Co więcej, układ ten po wgraniu na rzeczywisty układ FPGA (płytki DE0-Nano i DE10-Nano) działa bez zarzutu. Problemem jest tylko sama symulacja.

    Czy ktoś spotkał się z takim problemem i wie jak go rozwiązać?
    Nie znalazłem niczego użytecznego w google. Widziałem, że inni mieli podobny problemy ale nie znalazłem odpowiedzi, która w moim przypadku okazałaby się pomocna.
  • REKLAMA
  • Pomocny post
    #2 17923724
    yakuza_2000
    Poziom 21  
    Posty: 291
    Pomógł: 48
    Ocena: 10
    RAM wygenerowany w Quartusie jest inicjalizowany plikiem *.hex. Jeśli w folderze z symulacja nie ma tego pliku(albo nie pokazałeś narzędziu gdzie może szukać), w pamięci zostaną wartości X.
  • REKLAMA
  • #3 17924410
    matti0010
    Poziom 11  
    Posty: 319
    Pomógł: 8
    Ocena: 25
    RAM mam zainicjalizowany. Testowałem to zarówno plikiem *.mif jak i *.hex.
    Pliki wskazałem (raczej) dobrze. W pamięci ROM, którą podobno inicjalizuję mam takie wartości jakich oczekuję.

    Czy jest możliwe, że mam coś źle ustawione w samym Quartusie? Może trzeba przestawić jakieś parametry symulacji?
  • REKLAMA
  • Pomocny post
    #4 17924436
    yakuza_2000
    Poziom 21  
    Posty: 291
    Pomógł: 48
    Ocena: 10
    No to jest jeszcze opcja ze sam wpisujesz te X do pamięci :wink: . Pokaż co się dzieje na interfejsie do zapisu RAM. Najlepiej to pokaż przebiegi ze wszystkich wejść/wyjść ramu.
  • Pomocny post
    #5 17924485
    Konto nie istnieje
    Poziom 1  
  • Pomocny post
    #6 17924518
    yakuza_2000
    Poziom 21  
    Posty: 291
    Pomógł: 48
    Ocena: 10
    atari_robbo napisał:
    Niezainicjowana pamięć to zazwyczaj 'U'


    W Verilogu niezainicjowana pamięć będzie mieć X. Ale fakt, najbardziej prawdopodobne jest to że autor zrobił zwarcie ;p
  • REKLAMA
  • #7 17924585
    matti0010
    Poziom 11  
    Posty: 319
    Pomógł: 8
    Ocena: 25
    Jeżeli chodzi o sam kod, to wygląda on tak (przepraszam, za bałagan w kodzie ale ciągle go zmieniam szukając problemu więc nie jest posprzątany...):

    Plik MAIN:
    Kod: Verilog
    Zaloguj się, aby zobaczyć kod


    PLLR_RAM:
    Kod: Verilog
    Zaloguj się, aby zobaczyć kod


    PLLR_GENERATOR:
    Kod: Verilog
    Zaloguj się, aby zobaczyć kod


    Plik *.mif do inicjalizacji:
    Kod: Verilog
    Zaloguj się, aby zobaczyć kod


    I drugi alternatywny plik *.hex do inicjalizacji:
    Kod: Verilog
    Zaloguj się, aby zobaczyć kod


    Według mnie plik *.mif jest bardziej czytelny.

    Generator jest zwykłym licznikiem, który ma się "przekręcić" po osiągnięciu maksymalnej wartości (16 cykli) i tym samym jest on generatorem adresu dla pamięci RAM.
    Najpierw zapisuję dane do pamięci RAM (wejście "in_UKOM" w pliku MAIN) a później chcę odczytywać dane z tej pamięci.
    Wiem, że to fizycznie działa bo podpiąłem analizator stanów logicznych, wgrałem kod na płytki DE0-Nano i DE10-Nano a następnie widziałem, że mam na wejściu i wyjściu pamięci RAM to co chcę. Problem więc leży tylko w symulacji a nie działaniu.

    Mam kilka różnych pamięci RAM w całym układzie i każda w pewnym momencie zaczyna bez powodu wyrzucać stany "X"...

    Symulację pokazującą wejścia i wyjścia wrzucę jak ją ponownie wygeneruję. Niestety trochę to to trwa dla całego układu.

    Nie wiedziałem o opcji "Trace X". Spróbuję znaleźć o tym jakieś informacje i wskazówki jak można odpalić to śledzenie w Quartus. Chyba, że tutaj ktoś napisze mi krótki "idiotoodporny" poradnik :)
  • #8 17924709
    yakuza_2000
    Poziom 21  
    Posty: 291
    Pomógł: 48
    Ocena: 10
    Po pobieżnym przeglądnięciu kodu nie widzę żeby to w tym module powstały X, musiały raczej "przyjść" z zewnątrz. Robisz symulacje samego modułu PLLR_MAIN? Czy ten moduł jest gdzieś użyty?

    Plus parę uwag:
    1) Ogólnie ten kod nie jest napisany w stylu "FPGA" :wink:
    Na przykład:
    Kod: Verilog
    Zaloguj się, aby zobaczyć kod


    Ten licznik jest taktowny zegarem 'triger', który jest generowany przez bramkę XOR. Normalnie chcemy tak zaprojektować układ, żeby licznik był taktowany globalnym zegarem np clk, a jego inkrementacja następowała w odpowiednim warunku np:

    Kod: Verilog
    Zaloguj się, aby zobaczyć kod


    Oczywiście ten kod nie zastępuję twojego kodu, bo trzeba tak wygenerować sygnał 'triger', żeby pojawiał się tam stan niski na jeden cykl zegara, gdy (triger_UKOM xor triger_KPI) zmieni stan z 1 na 0.
    Przy okazji, poczytaj o blocking/non-blocking assignments.

    2) Dlaczego masz pamięć dual clock? I co robi moduł BUFOR_1BIT?
    3) Zamiast
    Kod: Verilog
    Zaloguj się, aby zobaczyć kod

    możesz napisać
    Kod: Verilog
    Zaloguj się, aby zobaczyć kod

    co jest bardziej czytelne. Analogicznie jest z nand.
    4)Tak z ciekawości, robisz ten projekt na uczelnie/do pracy/hobbystycznie?
  • #9 17924738
    matti0010
    Poziom 11  
    Posty: 319
    Pomógł: 8
    Ocena: 25
    Jest użyty w większym układzie (znacznie większym). Robiłem jednak symulacje tego układu od strony wejść PLLR_MAIN i tam nie było ani jednego "X". Postaram się jutro wieczorem wrzucić symulację, dziś już nie dam rady.

    Wszelkie uwagi mile widziane :) jestem głównie samoukiem więc pewnie robię sporo błędów.

    Specjalnie chciałem dać bramkę XOR bo próbuję odseparować się od globalnego CLK. Teraz jeszcze nie do końca mnie się to udało ale w kolejnej wersji tego układu planuję "wyrzucić" jak najwięcej linii globalnego CLK a te co zostaną chcę "bramkować". Niemniej jednak rozumie o co chodzi i dziękuję za uwagę :)

    BUFOR_1BIT opóźnia sygnał o jeden cykl zegara. Przedrostek 1BIT mówi mi, że to bufor 1-bitowy. Mam jeszcze kilka innych buforów. Dałem go teraz tylko na czas testów.
    Mam dual clock tylko z powodu testów i prób odpalenia tego ustrojstwa. Wcześniej miałem single clock bez rejestru na wyjściu pamięci (jest mi zbędne "bramkowanie czy raczej rejestrowanie :) " wyjścia).

    Jestem elektronikiem, dla mnie bardziej intuicyjne są opisy XOR, NAND, AND, OR, NOR itd. bo odzwierciedlają jak najbardziej architekturę, którą sobie zaprojektowałem przed rozpoczęciem pisania kodu. Gdybym pisał kod na mikrokontroler czy PC to na pewno używałbym "^".


    Pośrednio na uczelnie i hobbystycznie. Chcę się douczyć jak najwięcej i zrobić dekoder LDPC (kodowanie LDPC wykorzystywane jest w np. telewizji cyfrowej (WiMax, DVB-T2, DVB-S2, itd.) czy 5G więc temat jest całkiem ciekawy). Robię to w ramach projektu kilkuletniego na uczelnię, ale sam temat stał się moim hobby i w sumie najbardziej zależy mi na nauczeniu się jak najwięcej :) I na uruchomieniu tej wrednej symulacji... potrzebuję jej do uruchomienia analizy poboru energii (Power Analyzer).
  • #10 17926593
    matti0010
    Poziom 11  
    Posty: 319
    Pomógł: 8
    Ocena: 25
    Wrzucam grafiki z symulacji:
    [FPGA][ALTERA/INTEL] Simulation Waveform - nieoczekiwane stany Unknown Forcing [FPGA][ALTERA/INTEL] Simulation Waveform - nieoczekiwane stany Unknown Forcing

    Linie sygnałowe z przedrostkiem PLLR pokazują sygnały wejściowe i wyjściowe modułu PLLR_MAIN. Reszta to pozostałe sygnały całego układu, które obecnie nie są istotne.

    Jeżeli chodzi o nazewnictwo pomiędzy symulacją a modułem PLLR_MAIN to:
    Kod: Verilog
    Zaloguj się, aby zobaczyć kod


    Tak się zastanawiam, chyba to bramka NAND wszystko psuje w PLLR_MAIN.
    Muszę się nad tym zastanowić.
  • #11 17926726
    yakuza_2000
    Poziom 21  
    Posty: 291
    Pomógł: 48
    Ocena: 10
    Z tych przebiegów wynika że te X przychodzą z zewnątrz - widać je na wejściu in_UKOM[4:0]. Do tego wygląda że wszystko się popsuło gdy sygnał "in_sterowanie" zmienił stan na '0'.

    Dlaczego chcesz się odseparować od globalnego CLK? FPGA są tak zaprojektowane żeby używać kilku, kilkudziesięciu globalnych/regionalnych zegarów. Wtedy osiągniesz największą wydajność. Zegary które są generowane przez logikę kombinacyjną są złą praktyka - takie zegary mogą mieć hazardy (jeśli nie zrobisz odpowiedniego bramkowania), do tego trudniej jest spełnić wymagania czasowe.


    Ogólnie myślę że dekoder LDPC to trochę za gruba sprawa dla początkującego, lepiej zacząć od czegoś prostszego :wink:.
  • #12 17926776
    matti0010
    Poziom 11  
    Posty: 319
    Pomógł: 8
    Ocena: 25
    "in_sterowanie" informuje dekoder, że skończono transmitować dane z zewnątrz do układu.

    Chcę spróbować zrobić częściowo asynchroniczny dekoder. Poza tym chcę odciąć się od zegarów w pewnym stopniu aby osiągnąć tę asynchroniczność.

    Co do LDPC. Mam już kilka wersji tego dekodera i wszystkie działają ;) Oczywiście wszystkie sam zrobiłem od zera.
    Jasne, mają kilka bolączek ale to dopiero etap developerski. Czasem wychodzą małe "smaczki", które przeoczyłem. Niestety ale LDPC są dość wymagające pod kątem architektury i nie zawsze wszystko wyłapię od razu. Tym bardziej, że testuję różne podejścia w trakcie robienia tego.
    Mam nawet skrypt, w którym wpisuję sobie żądane parametry dekodera i całość jest generowana (skrypt mojego autorstwa).
    Ogólnie fajna zabawa jest z tym.

    Poprawiłem sygnał wren, dodałem parę drobnych rzeczy, kilka odjąłem i teraz działa:
    [FPGA][ALTERA/INTEL] Simulation Waveform - nieoczekiwane stany Unknown Forcing

    Od 2 tygodni sprawdzałem wszystko tylko nie sygnał wren... Ale jestem teraz zły sam na siebie :D

    Jeszcze sporo pracy mnie czeka ale problem jest rozwiązany. Muszę uważać na sygnał "wren".

    BARDZO DZIĘKUJĘ ZA POMOC. WSZYSTKIE UWAGI I PYTANIA DOPROWADZIŁY DO ZNALEZIENIA ROZWIĄZANIA :D

Podsumowanie tematu

✨ Użytkownik zgłasza problem z symulacją pamięci RAM w Quartus, gdzie podczas symulacji większego układu pojawiają się stany Unknown Forcing (X). Symulacja samej pamięci RAM działa poprawnie, a problem występuje tylko w kontekście większego systemu. Użytkownik potwierdza, że pamięć RAM jest zainicjalizowana, a wszystkie zmienne w kodzie są poprawne. W odpowiedziach sugerowane są różne przyczyny problemu, takie jak brak pliku inicjalizacyjnego, błędy w kodzie, czy możliwość konfliktu sygnałów. Użytkownik dostarcza fragmenty kodu oraz przebiegi sygnałów, co prowadzi do wniosku, że stany X mogą pochodzić z zewnętrznych sygnałów. Po poprawkach w sygnale wren, problem został rozwiązany.
Podsumowanie AI na podstawie dyskusji. Może zawierać błędy.
REKLAMA