1 | #include <htc.h>
|
2 | #include "hardware.h"
|
3 | #include "memorymap.h"
|
4 | #include "typedefs.h"
|
5 | #include "T39A.h"
|
6 | #include "i2c.h"
|
7 | #include "shtc1.h"
|
8 |
|
9 |
|
10 | // PIC12LF1840T39A Configuration Bit Settings
|
11 |
|
12 | #include <xc.h>
|
13 |
|
14 | // CONFIG1
|
15 | #pragma config FOSC = INTOSC // Oscillator Selection (INTOSC oscillator: I/O function on CLKIN pin)
|
16 | #pragma config WDTE = SWDTEN // WDT controlled by the SWDTEN bit in the WDTCON register
|
17 | #pragma config PWRTE = OFF // Power-up Timer Enable (PWRT enabled)
|
18 | #pragma config MCLRE = ON // MCLR Pin Function Select (MCLR/VPP pin function is digital input)
|
19 | #pragma config CP = OFF // Flash Program Memory Code Protection (Program memory code protection is disabled)
|
20 | #pragma config CPD = OFF // Data Memory Code Protection (Data memory code protection is disabled)
|
21 | #pragma config BOREN = OFF // Brown-out Reset Enable (Brown-out Reset disabled)
|
22 | #pragma config CLKOUTEN = OFF // Clock Out Enable (CLKOUT function is disabled. I/O or oscillator function on the CLKOUT pin)
|
23 | #pragma config IESO = OFF // Internal/External Switchover (Internal/External Switchover mode is disabled)
|
24 | #pragma config FCMEN = OFF // Fail-Safe Clock Monitor Enable (Fail-Safe Clock Monitor is disabled)
|
25 |
|
26 | // CONFIG2
|
27 | #pragma config WRT = OFF // Flash Memory Self-Write Protection (Write protection off)
|
28 | #pragma config PLLEN = OFF // PLL Enable (4x PLL disabled)
|
29 | #pragma config STVREN = ON // Stack Overflow/Underflow Reset Enable (Stack Overflow or Underflow will cause a Reset)
|
30 | #pragma config BORV = LO // Brown-out Reset Voltage Selection (Brown-out Reset Voltage (Vbor), low trip point selected.)
|
31 | #pragma config LVP = OFF // Low-Voltage Programming Enable (High-voltage on MCLR/VPP must be used for programming)
|
32 |
|
33 | /** enumeration for state maschine*/
|
34 | enum XMIT_STATE
|
35 | {
|
36 | OFF,
|
37 | PREAMBLE,
|
38 | DATA,
|
39 | CHECKSUM,
|
40 | SHDN,
|
41 | CMPL
|
42 | };
|
43 |
|
44 | /** Current state of transmitter state machine. */
|
45 | enum XMIT_STATE p_state = OFF;
|
46 |
|
47 | /**
|
48 | * Transmit buffer.
|
49 | */
|
50 | #define dataPacketSize 6
|
51 | volatile UINT8 dataPacket[6];// = {0xDE, 0xAD, 0xBE, 0xEF, 0xFF, 0xFF};
|
52 |
|
53 |
|
54 | /**
|
55 | * Debug Counter //replace DEV ID // Caution: I useses PR2 to get data over the SW reset.
|
56 | */
|
57 | #define DEBUG_COUNTER 0
|
58 | #if DEBUG_COUNTER
|
59 | volatile UINT8 ctr = 0;
|
60 | #endif
|
61 |
|
62 |
|
63 |
|
64 | /** Initialize microcontroller ports. */
|
65 | void initPorts()
|
66 | {
|
67 | // Transmitter control
|
68 | DATA_OUT = 0;
|
69 | DATA_DIR = output_pin;
|
70 | CTRL_OUT = 0;
|
71 | CTRL_DIR = output_pin;
|
72 |
|
73 | //All ports are digital
|
74 | ANSELA = 0;
|
75 |
|
76 | //Transmit Disable
|
77 | TXSTAbits.TXEN = 1;
|
78 | }
|
79 | void Init_WDT(void);
|
80 |
|
81 | /**Initialize Watchdog Timer */
|
82 | void Init_WDT ()
|
83 | {
|
84 | if (SEND_FREQUENCY == 1){
|
85 | WDTCONbits.WDTPS = 0b01010; //0b01010 = 1:32768; 1sec
|
86 | }
|
87 | else if (SEND_FREQUENCY == 2) {
|
88 | WDTCONbits.WDTPS = 0b01011; //0b01011 = 1:65536; 2sec
|
89 | }
|
90 | WDTCONbits.SWDTEN = 0b01; // WDT is turned on
|
91 | }
|
92 |
|
93 |
|
94 | #define I2C_WRITE 0
|
95 | #define I2C_READ 1
|
96 |
|
97 | /** Initialise MSSP port. (12F1822 - other devices may differ) */
|
98 | void i2c_Init(void){
|
99 |
|
100 | // Initialise I2C MSSP
|
101 | // Master
|
102 | TRISA1=1; // set SCL and SDA pins as inputs
|
103 | TRISA2=1;
|
104 |
|
105 | SSP1CON1 = 0b00101000; // I2C enabled, Master mode
|
106 | SSP1CON2 = 0x00;
|
107 | // I2C Master mode, clock = FOSC/(4 * (SSPADD + 1))
|
108 |
|
109 | #if (_XTAL_FREQ == 8000000)
|
110 | SSP1ADD = 4; // 400Khz @ 8Mhz Fosc
|
111 | #elif (_XTAL_FREQ == 16000000)
|
112 | SSP1ADD = 9; // 400Khz @ 16Mhz Fosc
|
113 | #elif (_XTAL_FREQ == 2000000)
|
114 | SSP1ADD = 12; // 400Khz @ 20Mhz Fosc
|
115 | #endif
|
116 |
|
117 |
|
118 | SSP1STATbits.SMP = 0; //Slew rate enabled for high speed mode
|
119 | SSP1STATbits.CKE = 1; //Enable SMBus compilant Input logic
|
120 | }
|
121 |
|
122 | /**
|
123 | * Reads the I2C SHTC T/H sensor
|
124 | */
|
125 | void sensor_read (volatile UINT8 dataPacket[]){
|
126 | //Start Measurement
|
127 | i2c_Start(); // send Start
|
128 | i2c_Address(I2C_SLAVE, I2C_WRITE); // Send slave address with write operation
|
129 | // Start Low Power H/T Measurement with Clock Stetching
|
130 | i2c_Write(0x44);
|
131 | i2c_Write(0xDE);
|
132 |
|
133 | //Start Read
|
134 | i2c_Restart(); // send Start
|
135 | i2c_Address(I2C_SLAVE, I2C_READ); // Send slave address with read operation
|
136 | for(char i=0; i<6;i++){
|
137 | dataPacket[i] = i2c_Read(1);
|
138 | }
|
139 | i2c_Stop(); // send Stop
|
140 | }
|
141 |
|
142 | /**
|
143 | * Initialize the EUSART interface for Clock out the plain bit stream for the transceiver
|
144 | */
|
145 | void init_eusart (void){
|
146 | //TRISA4 = 0;
|
147 | //TRISA5 = 0;
|
148 | //connect to Pin 4/5
|
149 | TXCKSEL = 1;
|
150 | RXDTSEL = 1;
|
151 |
|
152 | //Configuriere für Sync Serial
|
153 | #if (_XTAL_FREQ == 8000000)
|
154 | SPBRGL = 19;//100k baud @8mhz
|
155 | //SPBRGL = 128;//50k baud @8mhz
|
156 | #elif (_XTAL_FREQ == 16000000)
|
157 | SPBRGL = 39;//100k baud @8mhz
|
158 | #elif (_XTAL_FREQ == 2000000)
|
159 | SPBRGL = 4;//100k baud @8mhz
|
160 | #endif
|
161 |
|
162 | SYNC = 1; //Synchronous Mode
|
163 | SPEN = 1; //Serial Port Enable
|
164 | CSRC = 1; //Master Mode
|
165 | TXREG = 1; //EUSART Transmit Data Register
|
166 | SCKP = 1; //Transmit invertet data to the TC/CK pin
|
167 |
|
168 | //Transceiver aktivieren
|
169 | SREN = 0; //Disable Single Receive
|
170 | CREN = 0; //Disable Receiver
|
171 | //TXEN=1;
|
172 |
|
173 | //Enable Interrupt
|
174 | INTCONbits.GIE = 1;
|
175 | PIE1bits.TXIE = 1;
|
176 | PEIE = 1;
|
177 | ei();
|
178 | }
|
179 |
|
180 | void sendPacket()
|
181 | {
|
182 | #if (TRANSMITTMODE)
|
183 | __delay_ms(1);
|
184 | #else
|
185 | //Start-up time, 2mS
|
186 | DATA_OUT = 1;
|
187 | __delay_ms(2);
|
188 | DATA_OUT = 0;
|
189 | #endif
|
190 |
|
191 | PIE1bits.TXIE = 1;
|
192 | TXSTAbits.TXEN = 1;
|
193 | }
|
194 |
|
195 |
|
196 | /** Interrupt vector */
|
197 | static void interrupt int0()
|
198 | {
|
199 | GIE = 0;
|
200 | static UINT8 pc = 0;
|
201 | //RF PART
|
202 | if (PIR1bits.TXIF){
|
203 | switch (p_state) {
|
204 | case PREAMBLE:
|
205 | pc++;
|
206 | //Preamble Statemaschine
|
207 | switch (pc){
|
208 | //**Sync Word */
|
209 | case (PREAMBLE_BYTES+1):
|
210 | case (PREAMBLE_BYTES+3):
|
211 | TXREG = 0xCC;
|
212 | break;
|
213 | case (PREAMBLE_BYTES+2):
|
214 | case (PREAMBLE_BYTES+4):
|
215 | TXREG = 0xAA;
|
216 | break;
|
217 | //** Change to send data and send uniqe device ID
|
218 | case (PREAMBLE_BYTES+5):
|
219 | #if DEBUG_COUNTER
|
220 | TXREG = ctr;
|
221 | ctr = ctr + 1;
|
222 | #else
|
223 | TXREG = DEV_ID;
|
224 | #endif
|
225 | pc = 0;
|
226 | p_state = DATA;
|
227 | break;
|
228 | /**Send syncword*/
|
229 | default:
|
230 | TXREG = 0x55;
|
231 | break;
|
232 | }
|
233 | break;
|
234 |
|
235 | case DATA:
|
236 | TXREG = dataPacket[pc];
|
237 | pc++;
|
238 | //Check Packetcounter
|
239 | if (pc >= dataPacketSize){
|
240 | pc = 0;
|
241 | p_state = SHDN;
|
242 | PIE1bits.TXIE = 0; //Deactivate Interrupt because than it triggers always
|
243 | }
|
244 | break;
|
245 | default:
|
246 | break;
|
247 | }
|
248 |
|
249 | }
|
250 |
|
251 | GIE = 1;
|
252 | return;
|
253 | }
|
254 |
|
255 |
|
256 |
|
257 |
|
258 | void main ()
|
259 | {
|
260 |
|
261 | while (1)
|
262 | {
|
263 |
|
264 | __delay_ms(10);
|
265 |
|
266 | PCON = 0x03;
|
267 | OSCCONbits.SCS = 0b10;
|
268 | #if (_XTAL_FREQ == 8000000)
|
269 | OSCCONbits.IRCF = 0b1110;
|
270 | #elif (_XTAL_FREQ == 16000000)
|
271 | OSCCONbits.IRCF = 0b1111;
|
272 | #elif (_XTAL_FREQ == 2000000)
|
273 | OSCCONbits.IRCF = 0b1100;
|
274 | #else
|
275 | #error unsupported clock frequency
|
276 | #endif
|
277 | OSCCONbits.SPLLEN = 0;
|
278 |
|
279 |
|
280 |
|
281 | //Initialize MC
|
282 | initPorts();
|
283 |
|
284 | //Start H/T measurement
|
285 | i2c_Init();
|
286 | sensor_read(dataPacket);
|
287 |
|
288 |
|
289 | //Initialize RF
|
290 | TX_Init();
|
291 | init_eusart();
|
292 |
|
293 | //Send Datapacket
|
294 | p_state = PREAMBLE;
|
295 | sendPacket();
|
296 |
|
297 | //Enter Sleep Mode
|
298 | if (VOLTAGE_MODE == 1){
|
299 | Init_WDT(); //Low Power for 1 or 2 sec
|
300 | SLEEP();
|
301 | }
|
302 |
|
303 | else {
|
304 | while (1){
|
305 |
|
306 | //Shutdown transmitter if the transmission is complete
|
307 | if (p_state == SHDN)
|
308 | {
|
309 | TXSTAbits.TXEN=0; //Transmit Status and Control Register
|
310 | #if (TRANSMITTMODE) //Transmit Disable
|
311 | TX_MT_DIS();
|
312 | #endif
|
313 | p_state = CMPL;}
|
314 | }
|
315 |
|
316 | }
|
317 |
|
318 | }
|
319 | } // end of main
|