background image

24

r

ELEKTRON

IKA w RÓ¯NYCH ZASTOSOWANIACH

EMULATOR 

ZEGARA

DCF 77

(2)

Program steruj¹cy

Drug¹, bardzo istotn¹ czêœci¹ emulatora jest pro-

g

ram steruj¹cy. Program jest napisany w jêzyku C.

Na pocz¹tku jest zdefiniowany adres bazowy u¿y-

wanego przez emulator portu równoleg³ego. Zwy-

kle port LPT1 ma przypisany adres 0x378, nato-

miast LPT2 ma adres 0x278. Adres bazowy, przy-

dzielony dla portu równoleg³ego, mo¿na znaleŸæ

w ustawieniach BIOS

,

u lub Mój komputer/Panel

sterowania/System/Mened¿er urz¹dzeñ/Porty

(COM & LPT)/Port drukarki (LPT x)/Zasoby. Dla

opcji 1 (po³¹czenie bezpoœrednie) etykiecie 

wy-

soki

mo¿na przypisaæ wartoœæ 

0x001

. Wów-

czas dane bêd¹ generowane tylko na linii D0 po-

rtu równoleg³ego. Mo¿na te¿ zamieniæ wartoœci

przypisane etykietom 

wysoki

niski

co spo-

woduje zanegowanie generowanego przebiegu.

Dalej s¹ zdefiniowane podstawowe informacje

dotycz¹ce rodzaju anteny i zmiany czasu. Mo¿na

je modyfikowaæ w zale¿noœci od potrzeb. 

Zadaniem funkcji 

aktualizacja()

jest zape³-

nienie tablicy 

dane[]

ci¹giem informacji, które

póŸniej bêd¹ wysy³ane  przez port równoleg³y.

Tablica 

dane[]

jest u¿ywana w kontekœcie bito-

wym – ka¿dy bit danego pola tablicy stanowi jeden

bit danych wyjœciowych. W funkcji 

aktualiza-

cja()

s¹ równie¿ generowane bity parzystoœci

dla odpowiednich grup danych. 

Funkcja

jeden()

generuje d³ugi impuls (dla bitu

danych równego 1). Po ustawieniu stanu wysokie-

go na zdefiniowanych wczeœniej liniach portu rów-

noleg³ego funkcja oczekuje na zmianê stanu linii

PAP portu – do³¹czonej do wyjœcia  uk³adu scalo-

nego U2B. Czas oczekiwania wynosi 200 ms, po

czym liniom portu przypisuje siê stan niski. 

Funkcja 

zero()

odpowiada za generowanie krót-

kiego impulsu (bit danych równy 0). W tym przy-

padku po ustawieniu linii wyjœciowych portu funk-

cja oczekuje na narastaj¹ce zbocze na linii wejœcio-

wej ON/OF – do³¹czonej do wyjœcia uk³adu U2A,

a nastêpnie zeruje linie wyjœciowe. Teraz czas

oczekiwania wynosi 100  ms. 

Na pocz¹tku programu g³ównego informacje o da-

cie i czasie systemowym s¹ kopiowane do odpo-

wiednich zmiennych. Oczywiœcie u¿ytkownik nie

musi korzystaæ z informacji systemowych wstawia-

j¹c do zmiennych w³asne dane. Ze wzglêdów

praktycznych do zmiennej 

sek

okreœlaj¹cej aktu-

aln¹ liczbê sekund, jest podstawiona wartoœæ 58.

To powoduje, ¿e po uruchomieniu programu jest

generowany ostatni impuls ci¹gu danych, po czym

nastêpuje przerwa synchronizuj¹ca. W tym przy-

padku odbiornik rozpoczyna odbiór ci¹gu danych

ju¿ po up³ywie 2 s. Gdyby do zmiennej 

sek

zosta-

³a wstawiona rzeczywista liczba sekund (uzyska-

na z czasu systemowego), to w skrajnym przypad-

ku na synchronizacjê odbiornika danych DCF trze-

ba by czekaæ 1 minutê. Dalej program wypisuje

wartoœci przypisane poszczególnym zmiennym. Po

czym oczekuje na narastaj¹ce zbocze na linii wej-

œciowej PAP (do³¹czonej do wyjœcia uk³adu scalo-

nego U2B). Narastaj¹ce zbocza na tej linii pojawia-

background image

25

j¹ siê co 1 s. Je¿eli jest wykryta 59. sekunda ka¿dej mi-

nuty, to nastêpuje aktualizacja danych i ¿aden z impul-

sów nie jest wysy³any. Dla pozosta³ych sekund jest wy-

bierany z tablicy 

dane[]

kolejny _ odpowiadaj¹cy

danej sekundzie _ bit i zale¿nie od jego stanu, gene-

rowany na liniach wyjœciowych portu, krótki albo d³u-

gi impuls po czym program wypisuje na ekranie mo-

nitora aktualny czas. Nastêpnie oczekuje na pocz¹tek

kolejnej sekundy wyznaczony przez narastaj¹ce zbo-

cze na linii PAP i powtarza powy¿sze operacje.

Program zosta³ napisany i uruchomiony przy u¿yciu

popularnego kompilatora Turbo C. Do jego uruchomie-

nia mo¿na u¿yæ kompilatorów C++, choæ w tym przy-

padku, zale¿nie od wersji i producenta kompilatora mo-

g¹ byæ potrzebne pewne zmiany w tekœcie programu.

Niektóre kompilatory C++ nie pozwalaj¹ na dostêp do

portów komputera. W takiej sytuacji mo¿na skorzystaæ

z „wstawek asemblerowych”.  Przyk³adowo, cia³o

funkcji odpowiadaj¹cej za wys³anie do rejestru bazo-

wego portu 

port_wy

, wartoœci umieszczonej

w zmiennej 

w_wy

mo¿e mieæ tak¹ postaæ:

asm {

push dx
push ax
mov  dx,port_wy
mov  al,[w_wy]
out  dx,al
pop  ax
pop  dx

}

Natomiast cia³o funkcji odpowiadaj¹cej za odczytanie

z portu (rejestr bazowy + 1) 

port_wy+1

i umieszcze-

nie wyniku w zmiennej 

w_we

mo¿e wygl¹daæ tak:

asm {

push dx
push ax
mov  dx,port_wy+1
in   al,dx
mov  [w_we],al
pop  ax
pop  dx

}

Pe³ny program steruj¹cy prac¹ emulatora (Program

steruj¹cy.txt) znajduje siê na redakcyjnej stronie inter-

netowej pod adresem www.radioelektronik.pl

Opisany uk³ad emulatora by³ testowany na wielu

komputerach, wyposa¿onych w procesory o dra-

stycznie ró¿nych mo¿liwoœciach: pocz¹wszy od 80386

poprzez 80486, Pentium (MMX, II, III, IV), K6-2, Ath-

lon TB, i w ka¿dym przypadku dzia³a³ poprawnie.

n

Adam Mazurkiewicz

L I T E R A T U R A

[1] Gajewski P., Turczyñski J.: Cyfrowe uk³ady scalone CMOS. War-

szawa, WK£ 1990

[2]  Bielecki J.: Encyklopedia jêzyka C dla IBM PC. Warszawa, WK£

1989