Oldschoolowy projekt

Kącik dla elektroniki retro - układy, urządzenia, podzespoły, literatura itp.
Awatar użytkownika
gaweł
Expert
Expert
Posty: 859
Rejestracja: wtorek 24 sty 2017, 22:05
Lokalizacja: Białystok

Oldschoolowy projekt

Postautor: gaweł » piątek 08 lis 2019, 02:24

Tajemniczy projekt na Z80

Oldschoolowe projekty wymagają olschoolowych rozwiązań. Taki powrót do przeszłości,
to może być zabawą wartą wszystkiego. Nabyty w międzyczasie bagaż doświadczeń
i wiedzy może stanowić pomocną dłoń i w sumie wracając do remake dawnych konstrukcji,
nie warto się oglądać, bo wyjdzie kopia tego co było. A przecież chodzi o co innego,
ma być fajna zabawa i nowe rozkosze łamania głowy. Nowe spojrzenie to również nowe
problemy, więc nie wszystko da się wymyślić „tak na żywca”. Niezbędna jest faza
„research & development”, bo jeszcze się nie urodził taki, co by wiedział wszystko
na dzień dobry. Przykładowo jakiś systemik na Z80 dzisiaj to bym zrobił na pamięciach
statycznych, bo są łatwo dostępne, dużej pojemności i łatwo się je obsługuje. Kiedyś
tak nie było, więc... skoro wszystko ma być klimatyczne, to należy zabrać się do
roboty: research.


Wszystko jest do uzyskania bazując na TTL'ach, jednak chcąc zrobić coś fajnego, może się okazać, że PCB zajmie 2500m2 powierzchni. No cóż, pewne rzeczy warto skrócić. Takim skrótem jest zastosowanie układów PLD, ale... również takich oldschoolowych. Będzie klimatycznie. W mojej szufladzie wala się kilka układów CPLD chyba z ubiegłego wieku, obecnie już nieprodukowanych (więc się nadają ;) ).
latl01_ilu01.jpg
Tak prawdę mówiąc to moje pierwsze doświadczenia z tego rodzajem układów właśnie zaczęły się od takich. Poza tym są na +5V, ważny argument. No więc trzeba odświeżyć technologię, tamta trochę odbiega od obecnej.
Do obróbki tych układów stosuje się oprogramowanie od LATTICE, o czym pisałem już TU. Z szuflady wyciągam, lekko przykurzone układy do eksperymentów
latl01_ilu02.jpg
i odpowiedni osprzęt (programator, choć to zbyt szumna nazwa, więc prosty interfejs do programowania).
latl01_ilu03.jpg
Rzeczywiście jest prosty, zawiera w sobie 74HC244 i jest przyłączany do portu CENTRONIX.
latl01_ilu04.jpg
latl01_ilu05.jpg
Na stronie LATTICE można odnaleźć dokument o takim interfejsie. Lattice'owe układy CPLD można programować w docelowym środowisku, tylko ichni JTAG jest lekko śmieszny, bo złączka do interfejsu programującego jest 8-pinowa (choć w gruncie rzeczy jest 7-pinowa).
latl01_ilu06.jpg
Pierwszy eksperyment to następujące środowisko:
latl01_ilu07.png
Jest generator fali prostokątnej zbudowany na bazie NE555, którego impulsy wchodzą na licznik binarny (CD4040). Wyjście licznika (wystarczy 8 bitów) wchodzą na układ CPLD a ten retransmituje je do wyświetlenia na LED'ach. Najprostsze użycie z możliwych, by nie walczyć z jakimiś duchami.
Rzeczywiste środowisko:
latl01_ilu08.jpg
latl01_ilu09.jpg
latl01_ilu10.jpg
Wklepanie opisu w VHDL'u to chwila nieuwagi:

Kod: Zaznacz cały

library ieee;
use ieee.std_logic_1164.all;
use ieee.std_logic_arith.all;
use ieee.std_logic_unsigned.all;

entity ispLSI1016Demo is port ( InCnt  : in std_logic_vector ( 7 downto 0 ) ;
                                OutCnt : out std_logic_vector ( 7 downto 0 ) ) ;
end ispLSI1016Demo ;

architecture behavioral of ispLSI1016Demo is

begin

  OutCnt <= InCnt ;

end behavioral ;
Posługiwanie się narzędziem opisałem przy okazji GAL'i. Tu dodam jedynie kwestię przyporządkowania pinów do określonych sygnałów. Więc należy wybrać:
latl01_ilu11.png
To uruchomi soft do przydziału zasobów:
latl01_ilu12.png
Klikając na plusiki, rozwinie się lista sygnałów wejściowych i wyjściowych użyta w opisie w VHDL'u. Po kliknięciu na nazwę sygnału, powstaje możliwość przypisania numeru pinu (w kolumnie Pin).
latl01_ilu13.png
I tak dla każdego i zgodnie z wyżej pokazanym schematem. Można sobie nawet obejrzeć jak to wygląda.
latl01_ilu14.png
Syntezę odpala się klikając na:
latl01_ilu15.png
No i nadeszła chwila prawdy i coś... nie poszło tak jak powinno. Soft do programowania zastosowanego układu nie chciał się skumać z interfejsem programującym, twierdzi, że nie ma portu LPT1. Ktoś tu oszukuje, w kompie jest port LPT1, w końcu używam programatora od Elnec, który właśnie takiego używa. Lattice nie chciał, a Elnec stanął na wysokości zadania i potrafił zaprogramować układ (co prawda wymagał przełożenia do odpowiedniej podstawi w programatorze). Trzeba będzie zrobić jakieś badania i ustalić przyczynę problemów i podejść jeszcze raz, w najbliższym czasie. Na razie zaprogramowany układ „mruga diodami LED”.
W sumie sukces połowiczny, coś wyszło, ale nie wszystko odbyło się zgodnie z planem. Ach te rozkosze łamania głowy...
Nie masz wymaganych uprawnień, aby zobaczyć pliki załączone do tego posta.

Prawdziwe słowa nie są przyjemne. Przyjemne słowa nie są prawdziwe.
Lao Tse

Awatar użytkownika
gaweł
Expert
Expert
Posty: 859
Rejestracja: wtorek 24 sty 2017, 22:05
Lokalizacja: Białystok

Re: Oldschoolowy projekt

Postautor: gaweł » środa 12 lut 2020, 20:46

Każdy człowiek ma jakieś zainteresowania lub pasje, takie zajęcia, które są dla niego najważniejsze,
najcenniejsze. Jedni zbierają znaczki pocztowe inni oddają się eksperymentowaniu w zakresie elektroniki. W ostatnich
czasach „starożytne” pojęcie elektroniki, które kojarzy się z zapachem unoszącej się kalafonii i łączeniem tranzystorów,
oporników i kondensatorów, coraz bardziej oddala się od obecnego spojrzenia na tematykę. Rewolucja, jaką
wniosło zastosowanie mikroprocesora spowodowało wręcz rewolucję w możliwościach. Coś, co kiedyś było z pogranicza
wręcz magii, staje się obecnie wręcz codziennością. Spróbujmy się rozejrzeć wokół i dostrzec jakieś urządzenie
elektroniczne realizujące funkcję bardziej złożoną niż ładowarka do telefonu by nie miało ono
wewnątrz mikrokontrolera.
Nowoczesne mikrokontrolery mają takie możliwości, że „papcie zrywa”, jednak może zamiast gonić za
nieuchwytnym, zatrzymać się i z zainteresowaniem spojrzeć wstecz i pochylić się nad czymś, co odcisnęło swój
ślad na dalsze dzieje niektórych wynalazków. To one między innymi zasiewały w umysłach szalone koncepcje,
popychały świat do przodu. Wręcz kultowe procki z rodziny Z80 nawet po wielu latach nadal absorbują
wiele umysłów. To od nich zaczęła się moja przygoda z prockami i po iluś latach zataczam wielkie koło,
by do nich wrócić. Co to będzie … nie wiem, koncepcje ulegają ewolucji, jednak stanowią jakąś ciągłość. To co było
kiedyś stało się inspiracją dla dnia dzisiejszego, natomiast dzień dzisiejszy jest „źródłem” dla dnia jutrzejszego.
Z tego wszystkiego nasuwa się jeden wniosek: nie ma ograniczeń i wszystko jest możliwe (choć niektórzy
twierdzą, że nie da się wywrócić wojskowego hełmu na drugą stronę).
Dotychczasowy efekt badawczy trochę nie wypalił, więc zostaje odłożony trochę na późniejsze
czasy, a obecnie, by nie tracić czasu poświęciłem swój czas drugiej połowie. Soft jest nieodłącznym
elementem składowym każdego diwajsa zawierającego procki.


z80s-i01.jpg


KONCEPCJA

Czasami „specjalne” tematy wymagają specjalnego potraktowania i specjalnych narzędzi. A jak wiadomo, narzędzia, to rzecz ważna, bo bez nich to tylko można urobić się po łokcie i później zostanie tylko pozżymać się. Tylko na kogo? No więc by nie mieć powodów do narzekania, warto wcześniej trochę pomyśleć. No i tak urodziła się koncepcja specjalizowanego narzędzia do tworzenia oprogramowania – kompilatora asm dla kultowego proca. Niby takich w sieci internetowej jest … dużo, to może jednak warto pomyśleć nad własnymi rozwiązaniami, nad własną wizją rozwiązania określonych potrzeb.
Tu występują ściśle określone wymagania. Takim nadrzędnym i istotnym jest to, by istniała możliwość wygenerowania kodu programu, który jest umieszczony w określonej lokacji adresowej, ale jest „wylinkowany” na inny adres. Chodzi o to, by powstał kawałek binarnego kodu, który ma zostać przepisany w inny region i tam ma być sprawnie działający. Niby można zrobić jakąś „plombę” na tą okoliczność, typu napisać program zaadresowany na docelowy obszar i później zrobić z jego kodu wstawkę do innego programu. No trochę złożona operacja...
Skoro jednak wybrałem sobie taką ścieżkę, w której planuję wykorzystanie odpowiednich narzędzi, może warto zadbać, by było ono maksymalnie użyteczne. Taka drobna „eskalacja wymagań” zaowocowała kolejnymi zachciankami i możliwościami. Oprócz możliwości jakie daje kompilacja warunkowa (coś, co w języku C jest standardem), jedną z takich zachcianek jest możliwość używania nawet złożonych wyrażeń jako operandy instrukcji oraz danych wbijanych w kod za pomocą odpowiednich dyrektyw. Mając za sobą napisanych tysiące wierszy w języku asm, można dostrzec kilka typowych problemów, których rozwiązanie można niejako zautomatyzować. Trochę przemyśleń, trochę pracy... i powstała jakaś wstępna wersja, którą podzieliłem się z naszą koleżanką taszą. Ona dodała swoich 5 groszy do całości, nawet spowodowała drobną rewolucję w koncepcji. Uwzględniając jej sugestie, postał w „lazarus” program realizujący założoną funkcjonalność, jednak jego podstawowym elementem jest „niemy” komponent realizujący funkcję kompilatora. W oparciu o ten komponent można utworzyć program w wersji „okienkowej”, jak i w wersji „konsolowej”. Łącząc wszystkie koncepcje, można zaryzykować stwierdzenie, że poniższy program jest naszym wspólnym dzieckiem.

PODSTAWOWA SKŁADNIA

Podstawowa składnia zapisów instrukcji jest wzorowana na ogólnie przyjętej, niemniej jest kilka „prywatnych” myków. Wzorem wielu języków programowania, tu nie występuje rozróżnienie pisowni małymi i wielkimi literami. Wszystkie dyrektywy zaczynają się od znaku kropki. W operandach instrukcji mogą wystąpić odwołania do etykiet w programie lub do stałych. Sama etykieta jest nazwą (słowem) innym niż słowo kluczowe (lub słowo stanowiące rozszerzenie na potrzeby rozszerzenia możliwości nie będące słowem kluczowym w dotychczasowym ujęciu – słowa kluczowe będą opisywane w przy okazji opisu nowych możliwości). Etykieta może być zakończona znakiem dwukropka („:”) będącym separatorem pomiędzy etykietą a instrukcją (dyrektywą). Znak dwukropka nie jest obowiązkowy (jak jest, to jest, jak nie ma, to również żadna tragedia). Podobnie ma się sprawa akumulatora w instrukcjach arytmetycznych i logicznych. W asm procka Z80 są instrukcje dotyczące operacji 8-bitowych (gdzie występuje rejestr akumulatora A) lub 16-bitowych (gdzie rolę akumulatora pełni para rejestrów HL), które mają ten sam mnemonik (przykładem jest instrukcja ADD). Z tego powodu w instrukcjach tych konieczne jest jawne określenie rejestru pełniącego rolę akumulatora (rejestr A lub rejestr HL). W każdym innym przypadku (operacji 8-bitowych) domyślnym rejestrem występującym w operacji jest rejestr A, co ma swoje odbicie w zapisie instrukcji, gdzie rejestr ten może zostać pominięty w zapisie (bo jest domyślny). W zaproponowanej wersji, istnieje możliwość zapisu rejestru A jako operandu operacji (pomimo, że jest domyślnym) lub go pominięciu. Kompilator nie jest wrażliwy na zapis (jak jest zapisany, to OK, jak nie ma, to również jest OK). Stałe tekstowe mogą być ujęte w apostrofy lub znaki cudzysłowu, jednak na obu końcach stałej tekstowej mają być identyczne. Stałe liczbowe mogą mieć zapis binarny, dziesiętny, ósemkowy lub szesnastkowy. System zapisu jest zdeterminowany znakiem kończącym liczbę (zapisanym na styk z cyframi). Brak jawnego wskazania oznacza, że dana stała jest zapisana w systemie dziesiętnym. Akceptowane przez kompilator znaki determinujące system zapisu są następujące:
  • B (b) – oznacza zapis binarny,
  • O (o) lub Q (q) – oznacza zapis ósemkowy,
  • D (d) – oznacza zapis dziesiętny,
  • H (h) – oznacza zapis szesnastkowy.

Każda stała liczbowa zaczyna się od znaku cyfry. Na oznaczenie cyfr w systemie szesnastkowym używane są litery A .. F (a..f).

WYRAŻENIA

Jako operandy instrukcji lub dyrektyw mogą występować wyrażenia. Jako wyrażenie rozumiane jest dowolne wyrażenie (z użyciem operatorów arytmetycznych lub logicznych), w którym występują odwołania do innych stałych lub etykiet. Można wyróżnić dwa typy wyrażeń: policzalne w danej chwili (chwili użycia) lub niepoliczalne w danej chwili. Policzalność jest związana ze znajomością wartości stałych (wartość stałej jest znana) lub etykiet (wartością etykiety jest jej adres w przestrzeni adresowej → etykieta może wystąpić dalej w programie źródłowym, toteż w danej chwili jej adres nie jest znany, co implikuje, że wyrażenie, w którym jest użyta etykieta jest niepoliczalne). Poprawnie napisany program ma wszystkie operandy policzalne na zamknięciu programu. Typowo, w języku asm nie dopuszcza się, by w wyrażeniach występowało kilka etykiet. Właściwie, to nie widzę powodu, by takie coś było niedopuszczalne. Jeżeli kompilator będzie dysponował analizą ogólnie pojętego wyrażenia, to nie ma powodu, by „ograniczać jego wolność”. W końcu każda etykieta to jakaś liczba (adres w przestrzeni jest liczbą), więc możliwe jest wykonanie obliczenia dowolnego wyrażenia logiczno-arytmetycznego. Można dyskutować nad sensem przykładowo instrukcji (pobrać do rejestru HL iloczyn adresów dwóch etykiet):

Kod: Zaznacz cały

LD HL,<etykieta1> * <etykieta2>

Czy taki zapis ma sens? Może ma, może nie ma, to jest wyłącznie kwestia interpretacji i intencji piszącego.
Przyglądając się instrukcjom, można zauważyć, że niektóre z nich mają operandy jako stałe liczbowe, przykładowo numer bitu w operacjach bitowych (SET <numer bitu> , A). Jeżeli kompilator jest wyposażony w analizator wyrażeń, to dlaczego ma istnieć ograniczenie, gdzie <numer bitu> musi być jawnie wpisaną liczbą. Z punktu widzenia kompilatora, jest to policzalne wyrażenie o wartości od 0 do 7 włącznie. Toteż zapisy:

Kod: Zaznacz cały

NBIT   .EQU      3

SET   NBIT+2,A
SET   1+2+3,A

są całkiem legalnymi instrukcjami, gdyż w momencie ich analizy wszystkie szczegóły są znane, a to pozwala wygenerować właściwy kod instrukcji. Można się zastanawiać po co jest taka możliwość? Czasem odpowiedź jest bardziej zaskakująca niż można się spodziewać: bo to jest ograniczanie możliwości, bo to jest wyjścia poza ogólnie przyjęte schematy, bo to pozwala pomyśleć inaczej niż każdy by się tego spodziewał, bo inne rozwiązanie tematu w kompilatorze stanowi wyjątek, a wyjątki to... zawsze wyjątki. Reasumując niektóre operandy instrukcji muszą być wyrażeniami policzalnymi w danej chwili, większość zaś musi być policzalna na zakończenie programu.
Będąc w temacie wyrażeń, to w wyrażeniu mogą być zastosowane jawne stałe (liczbowe lub tekstowe jedno lub dwuznakowe co odpowiada stałej 8-bitowej lub stałej 16-bitowej), stałe jako identyfikatory stałych. Obok stałych mogą wystąpić „zmienne”, identyfikatory etykiet, których wartością jest adres w przestrzeni adresowej. Naturalnym jest, że etykieta może być już znana (mieć określony adres) lub nieznana (jeszcze nie występująca). W zilogowych instrukcjach operand może być 8-bitowy lub 16-bitowy i to wynika w kontekstu użycia. Jeżeli wyrażenie jest policzalne, jego wartość jest wstawiona do generowanego kodu. W przeciwnym wypadku w kod wchodzi stała 0FFH lub 0FFFFH (tworzy miejsce na docelową wartość, która zostanie uzupełniona w chwili, gdy wyrażenie stanie się policzalne, jeżeli będzie niepoliczalne, to wygeneruje błąd a w kodzie zostaną same FF'y). Rzecz jasna, kontrolowany jest zakres, w jakim ma się zmieścić wartość wyrażenia.
Przykład:

Kod: Zaznacz cały

Label   NOP
   LD  A, Label

nie ma powodu by kompilator awanturował się w przypadku powyższej instrukcji, jeżeli wartość etykiety Label (jej adres) jest mniejsza niż 256 pomimo że w ogólnym przypadku adres etykiety jest 16-bitowy.
Inny przykład, gdzie etykieta Label może mieć dowolną wartość, to zapis jak poniżej:

Kod: Zaznacz cały

   LD  A, hi(Label)
   LD  I, A

Label   NOP

pozwala na wsparcie przy obsłudze przerwań (część adresu należy wpisać do rejestru I).
Oprócz identyfikatorów stałych i etykiet w wyrażeniu mogą wystąpić operatory arytmetyczne oraz logiczne. Kompilator rozpoznaje następujące operatory:
  • „+” – operator dodawania arytmetycznego, standardowo operator dwuargumentowy (a+b); analizator rozpozna zastosowanie operatora jako jednoargumentowego (+a) i w tym przypadku nie wygeneruje żadnych operacji, jest to tożsamość,
  • „-” – operator odejmowania arytmetycznego, standardowo operator dwuargumentowy (a-b) jednak analizator rozpozna zastosowanie jako operatora jednoargumentowego (-a) i w tym przypadku zrealizuje negację arytmetyczną,
  • „*” – operator mnożenia arytmetycznego, występuje jako operator dwuargumentowy (a*b)
  • „/” – operator dzielenia arytmetycznego (jako dzielenie całkowitoliczbowe), występuje jako operator dwuargumentowy,
  • „&” alternatywnie AND – operator iloczynu logicznego, występuje jako operator dwuargumentowy (a & b, a and b),
  • „|” alternatywnie OR – operator sumy logicznej, występuje jako operator dwuargumentowy (a | b, a or b),
  • „^” alternatywnie XOR – operator logiczny EXOR, występuje jako operator dwuargumentowy (a ^ b, a xor b),
  • „~” alternatywnie NOT – operator negacji, występuje jako operator jednoargumentowy (~ a, not a),
  • „<” alternatywnie SHL – operator przesunięcia logicznego w lewo, występuje jako operator dwuargumentowy (a < b, a shl b),
  • „>” alternatywnie SHR – operator przesunięcia logicznego w prawo, występuje jako operator dwuargumentowy (a > b, a shr b).
Dodatkowo w wyrażeniach mogą występować wywołania określonych funkcji. Analizator rozpoznaje następujące funkcje (jest ich więcej i będą sukcesywnie później wyjaśnione):
  • hi ( a ) – jednoargumentowa funkcja dająca jako wynik wartość starszego bajtu w wartościach dwubajtowych,
  • lo ( a ) – jednoargumentowa funkcja dająca jako wynik wartość młodszego bajtu w wartościach dwubajtowych,
  • mod ( a , b ) – dwuargumentowa funkcja obliczenia arytmetycznego typu modulo: reszta z dzielenia wyrażenia a przez wyrażenie b,
  • same ( a ) – „sztuczna” funkcja tożsamościowa (o czym za chwilę).
W wyrażeniach może wystąpić dowolne zagłębienie nawiasów (oczywiście każdy nawias otwierający musi mieć nawias zamykający). Takie podejście czasami może doprowadzić do niejednoznaczności. Przykładowo:
LD HL , ( A + B ) * ( C + D )
skoro za przecinkiem występuje nawias, to kompilator potraktuje to jako instrukcję typu LD HL,(nnnn) i powyższy zapis wygeneruje błąd kompilacji (część A+B jest wyrażeniem, dalej nawias zamykający a pozostała część *(C+D) jest syntaktycznie niepoprawna. Pomimo, że wygląda to jak wygląda, intencją autora jest zapis typu: LD HL,nnnn, a wyrażenie nnnn jest zapisane w postaci ( A + B ) * ( C + D ), gdzie nawias wchodzi jako część wyrażenia. Na tą okoliczność została wprowadzona do kompilatora jednoargumentowa funkcja SAME(x). Wyrażenie SAME((A+B)*(C+D)) nie zaczyna się od znaku nawiasu, więc kompilator nie będzie miał problemów z rozpoznaniem wariantu instrukcji, a sama funkcja nie wpływa na wartość wyrażenia.
Zapisy:
LD HL , same ( ( A + B ) * ( C + D ) )
LD HL , ( same ( ( A + B ) * ( C + D ) ) )
zostaną poprawnie zinterpretowane: jako LD HL,nnnn oraz jako LD HL,(nnnn).
Nie masz wymaganych uprawnień, aby zobaczyć pliki załączone do tego posta.

Prawdziwe słowa nie są przyjemne. Przyjemne słowa nie są prawdziwe.
Lao Tse

Awatar użytkownika
gaweł
Expert
Expert
Posty: 859
Rejestracja: wtorek 24 sty 2017, 22:05
Lokalizacja: Białystok

Re: Oldschoolowy projekt

Postautor: gaweł » czwartek 13 lut 2020, 02:36

KOMPILACJE WARUNKOWE

Kompilator ZILO pozwala na kompilacje warunkowe (filozofia podobna do stosowanej w języku C). W kodzie źródłowym można zawrzeć zapisy, które nie podlegają analizie (w sensie nie są instrukcjami podlegającymi kompilacji) a są jedynie przetwarzane przez coś, co można nazwać preprocesorem. Zadaniem preprocesora jest „wyłapanie ważnych dla niego elementów” oraz włączanie lub nie do kompilowanego tekstu odpowiednich zapisów. Podobnie jak wszystkie dyrektywy, zapisy do kompilacji warunkowych zaczynają się od znaku kropki. W ogólnym zapisie wygląda to następująco:

Kod: Zaznacz cały

.IF <warunek>
<ciąg instrukcji 1>
.ELSE
<ciąg instrukcji 2>
.ENDIF

w zależności od wartości wyrażenia <warunek> (traktowanego w kategoriach logicznych) do tekstu źródłowego będzie włączony <ciąg instrukcji 1> lub <ciąg instrukcji 2>. Zapis warunkowy nie musi mieć wariantu .ELSE, czyli może przyjąć postać:

Kod: Zaznacz cały

.IF <warunek>
<ciąg instrukcji 1>
.ENDIF

w zapisie warunku może wystąpić dowolne wyrażenia logiczne, w którym mogą zostać użyte operatory logiczne AND, OR, NOT i XOR (podobnie jak w wyrażeniach arytmetycznych). Również można stosować nawiasy.
Elementy występujące w wyrażeniu muszą być policzalne w chwili jego użycia, czyli wcześniej muszą wystąpić przypisania wprowadzanym identyfikatorom ich wartości logicznej. Zapis jest następujący:

Kod: Zaznacz cały

.DEF <identyfikator parametru> = <wartość>

gdzie <identyfikator parametru> to po prostu nazwa, natomiast <wartość> to jest słowo kluczowe TRUE lub FALSE.
W wyrażeniu logicznym mogą również występować stałe logiczne. W najprostszym przypadku wyrażenie logiczne może sprowadzić się do stałej logicznej TRUE lub FALSE.
Innym wariantem zapisu na użytek kompilacji warunkowych jest:

Kod: Zaznacz cały

.IFDEF <identyfikator parametru>

lub

Kod: Zaznacz cały

.IFNDEF <identyfikator parametru>

i powyższe warunki są rozpatrywane w kategorii: czy jest zdefiniowany (czy nie jest zdefiniowany) wskazany parametr (nie rozpatruje się wartości parametru a jedynie fakt jego definicji).
Każdy zdefiniowany parametr ma swoje odzwierciedlenie w raporcie kompilacji, jak pokazuje to rysunek:
zilo_kon01.png
Zapisy kompilacji warunkowych mogą być zagnieżdżane.
zilo_kon02.png
Tu może warto zauważyć, że zapis:

Kod: Zaznacz cały

.if not ( def1 and ( def2 or def3 ) xor def4 )

można interpretować jako:

Kod: Zaznacz cały

if (def1 and ( def2 or def3 )) =  def4

gdyż operator XOR w logice spełnia funkcję komparatora (dokładniej zanegowanego komparatora), toteż wyrażenie NOT ( cos1 xor cos2) jest równoważne: czy cos1 = cos2.
Nie masz wymaganych uprawnień, aby zobaczyć pliki załączone do tego posta.

Prawdziwe słowa nie są przyjemne. Przyjemne słowa nie są prawdziwe.
Lao Tse


Wróć do „Retro”

Kto jest online

Użytkownicy przeglądający to forum: Obecnie na forum nie ma żadnego zarejestrowanego użytkownika i 1 gość