Rev Author Line No. Line
193 miho 1 // Program STOPKY pro mereni casu prujezdu mezi cidlama pro souteze solarnich robotu
2 //
3 // (c) miho 2004
4 //
5 // Historie
6 //
7 // 1.00 Uvodni verze
8  
9 #define VER "1.00"
10  
11 // Definice zakladnich parametru
12 //
13 #include <16F84.h> // procesor
14 #use delay(clock=4000000) // krystal
15 #use rs232(baud=9600, xmit=PIN_B4) // seriovka a jeji parametry
16 #fuses XT,PUT,NOWDT,NOPROTECT // prepinace
17  
18  
19 // Definice pro pripojeni LCD displeje
20 //
21 #define LCD_RS PIN_A2 // Signal RS
22 #define LCD_E PIN_A3 // Signal E
23 #define LCD_D0 PIN_A4 // Data
24 #define LCD_D1 PIN_B1
25 #define LCD_D2 PIN_B2
26 #define LCD_D3 PIN_B3
27 #include <LCD.C>
28  
29  
30 // Definice pro pripojeni vstupu (cidel)
31 //
32 #define BUTTON_START PIN_B7 // Tlacitko START
33 #define BUTTON_STOP PIN_B6 // Tlacitko STOP
34 #define BUTTON_TEST PIN_B5 // Tlacitko TEST pro prechod do testovaciho rezimu
35  
36  
37 // Defince pro pripojeni vystupu pro pipak
38 //
39 #define BEEP_PORT_P PIN_A0 // Piezo pipak pozitivni
40 #define BEEP_PORT_N PIN_A1 // Piezo pipak negativni
41  
42  
43 // Definice globalnich promennych
44 //
45 unsigned int Beep; // citac pulperiod pro pipnuti
46 short int Beep_state; // stav pipaku (0 nebo 1)
47 unsigned int State_run; // 0 .. klid
48 // 1 .. bezi mereni casu
49 // 2 .. cas zmereny
50  
51  
52 // Obsluha vstupu cidel
53 //
54 // Cas se meri od signalu na tlacitku START po signal na tlacitku STOP
55 // Signaly na tlacitkach vyvolaji preruseni a dojde k preklopeni stavu v promenne State_run
56 //
57 #int_RB
58 RB_isr()
59 {
60 if(State_run)
61 {
62 if(~input(BUTTON_STOP))
63 {
64 State_run=2; // Domereno
65 Beep=100;
66 disable_interrupts(INT_RB); // Zakaz vstup tlacitek aby byl cas na zpracovani
67 }
68 }
69 else
70 {
71 if(~input(BUTTON_START))
72 {
73 State_run=1;
74 Beep=100;
75 }
76 }
77 }
78  
79  
80 // Obsluha preruseni od casovace
81 //
82 unsigned int32 Time; // citac casu (perioda 256us)
83  
84 #int_RTCC
85 RTCC_isr()
86 {
87 if(State_run==1) Time++; // zvetsi citac
88  
89 if(Time==(3600000000>>8)) Time=0; // Osetreni preteceni po 1 hodine
90  
91 if(Beep) // pokud se ma pipnout pipni
92 { // Beep je pocet pulperiod
93 Beep--;
94 output_bit(BEEP_PORT_P,Beep_state);
95 Beep_state=~Beep_state;
96 output_bit(BEEP_PORT_N,Beep_state);
97 }
98 }
99  
100  
101 // Obsluha vystupu a jeho presmerovani na LCD a RS232
102 //
103 int PutCharMode;
104 #define LCD 1
105 #define RS232 2
106 void PutChar(char c)
107 {
108 if(PutCharMode & LCD) LCD_Putc(c);
109 if(PutCHarMode & RS232) putc(c);
110 }
111  
112  
113 // Vypis casu - dlouhy program ale jen na jedinem miste
114 //
115 void DisplayCas()
116 {
117 int32 xTime;
118  
119 // Tisk vysledku v ms
120 // printf(PutChar,"Cas:%8lums\n\r",(Time<<8)/1000);
121  
122 // Tisk vysledku v s
123 xTime=(Time<<8)/1000;
124 printf(PutChar,"Cas:%4lu.%03lus\n\r",xTime/1000,xTime%1000);
125 }
126  
127  
128 // Testovaci rezim
129 //
130 void TestMode()
131 {
132  
133 int T;
134  
135 // Otestuj tlascitko TEST
136 if(input(BUTTON_TEST)) return;
137  
138 // Vypis na displej
139 printf(LCD_Putc,"\fTest Mode\n");
140  
141 for(;1;)
142 {
143 T=0;
144 if(~input(BUTTON_START)) T+=1;
145 if(~input(BUTTON_STOP)) T+=2;
146 printf(LCD_putc,"\n%d",T);
147 if(T)
148 {
149 if(T==3) T=4;
150 output_bit(BEEP_PORT_P,0);
151 output_bit(BEEP_PORT_N,1);
152 delay_ms(T);
153 output_bit(BEEP_PORT_P,1);
154 output_bit(BEEP_PORT_N,0);
155 delay_ms(T);
156 }
157 }
158 }
159  
160  
161 // Hlavni program
162 //
163 void main()
164 {
165 // Inicializace LCD displeje
166 lcd_init();
167 PutCharMode=LCD|RS232;
168 printf(PutChar,"\n\rStopky v."VER"\r\n(c) miho 2004\n\r");
169 delay_ms(100);
170  
171 // Inicializace stavovych promennych
172 State_run=0; // stopky stoji
173  
174 // Inicializace vstupu (preruseni od zmeny stavu)
175 input(BUTTON_START); // precti RB aby se inicializoval registr zmen RB
176 port_b_pullups(TRUE); // zapni pull up odpory
177  
178 // Testovaci mod
179 TestMode();
180  
181 // Inicializace casovace pod prerusenim
182 setup_counters(RTCC_INTERNAL,WDT_18MS); // Perioda je 256 instrukcnich taktu
183  
184 // Hlavni smycka porad dokola
185 for(;1;)
186 {
187  
188 // Nuluj citace
189 Time=0; // nulovy cas
190 Beep=0; // nepipej
191 State_run=0;
192  
193 // Povoleni preruseni
194 enable_interrupts(INT_RTCC); // povol preruseni od casovace
195 enable_interrupts(INT_RB); // povol preruseni od zmeny portu RB
196 enable_interrupts(global); // povol preruseni
197  
198 // Cekej az se zacne merit
199 for(;State_run==0;)
200 {
201 }
202  
203 // Prubezne vypisuj cas
204 PutCharMode=LCD; // vystup jen na LCD
205 for(;State_run==1;)
206 {
207 DisplayCas();
208 }
209  
210 // Vypis vysledny cas - na LCD hned
211 DisplayCas();
212  
213 // Vypis vysledny cas - na RS232 az po pipnuti
214 delay_ms(100); // ted se pod prerusenim pipa
215 PutCharMode=RS232;
216 disable_interrupts(global); // zakaz preruseni (aby fungovalo casovani seriovky)
217 DisplayCas();
218 enable_interrupts(global); // opet povol preruseni
219  
220 }
221 }