Sonoma (MAXREFDES14#) Code Documentation V01.00 Isolated EMP (Energy Measurement Processor)

- Main Page
- Data Structures
- Files

- File List
- Globals

All Data Structures Files Functions Variables Macros Pages
utilities.c
Go to the documentation of this file.
1
29 /*
30 * Copyright (C) 2012 Maxim Integrated Products, All Rights Reserved.
31 *
32 * Permission is hereby granted, free of charge, to any person obtaining a
33 * copy of this software and associated documentation files (the "Software"),
34 * to deal in the Software without restriction, including without limitation
35 * the rights to use, copy, modify, merge, publish, distribute, sublicense,
36 * and/or sell copies of the Software, and to permit persons to whom the
37 * Software is furnished to do so, subject to the following conditions:
38 *
39 * The above copyright notice and this permission notice shall be included
40 * in all copies or substantial portions of the Software.
41 *
42 * THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS
43 * OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
44 * MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT.
45 * IN NO EVENT SHALL MAXIM INTEGRATED PRODUCTS BE LIABLE FOR ANY CLAIM, DAMAGES
46 * OR OTHER LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE,
47 * ARISING FROM, OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR
48 * OTHER DEALINGS IN THE SOFTWARE.
49 *
50 * Except as contained in this notice, the name of Maxim Integrated Products
51 * shall not be used except as stated in the Maxim Integrated Products
52 * Branding Policy.
53 *
54 * The mere transfer of this software does not imply any licenses
55 * of trade secrets, proprietary technology, copyrights, patents,
56 * trademarks, maskwork rights, or any other form of intellectual
57 * property whatsoever. Maxim Integrated Products retains all ownership rights.
58 *
59 ***************************************************************************/
60
61 #include "xparameters.h" /* EDK generated parameters */
62 #include "stdio.h"
63 #include "utilities.h"
64 #include "MAXREFDES14.h"
65
66 #define UART_BASEADDR XPAR_XUARTPS_0_BASEADDR
67
68 #define OLED_VBAT 0x20
69 #define OLED_VDD 0x10;
70 #define OLED_RESET_B 0x08
71 #define OLED_DATA_COMMAND_B 0x04
72 #define OLED_SDIN 0x02
73 #define OLED_SCLK 0x01
74
75 void delay(int nStopValue)
86 {
87 int i=0;
88 int a=0;
89
90 for(i=0;i<nStopValue;i++)
91 {
92 a=i;
93 }
94 }
95
96 void led_knight_rider(XGpio *pLED_GPIO, int nNumberOfTimes)
107 {
108 int i=0;
109 int j=0;
110 u8 uchLedStatus=0;
111
112 // Blink the LEDs back and forth nNumberOfTimes
113 for(i=0;i<nNumberOfTimes;i++)
114 {
115 for(j=0;j<8;j++) // Scroll the LEDs up
116 {
117 uchLedStatus = 1 << j;
118 XGpio_DiscreteWrite(pLED_GPIO, 1, uchLedStatus);
119 delay(ABOUT_ONE_SECOND / 15);
120 }
121
122 for(j=0;j<8;j++) // Scroll the LEDs up
123 {
124 uchLedStatus = 8 >> j;
125 XGpio_DiscreteWrite(pLED_GPIO, 1, uchLedStatus);
126 delay(ABOUT_ONE_SECOND / 15);
127 }
128 }
129 }
130
131 int number_raised_to_power(int nBase, int nExponent)
144 {
145 int i=0;
146 int nValue=0;
147 if(nExponent==0)
148 nValue=1;
149 else
150 {
151 nValue = nBase;
152 for(i=1;i<nExponent;i++)
153 {
154 nValue = nValue * nBase;
155 }
156 }
157 return(nValue);
158 }
159
160 void print_asterisks(int nQuantity)
168 {
169 int i=0;
170 for(i=0;i<nQuantity;i++)
171 printf("*");
172 }
173
174 u8 getUartByte(u32 nUartAddress)
182 {
183 u8 uchInput;
184
185 // Check if the UART base address is the full UART located within the Zynq chip,
186 // if not, assume it is an HDL instantiated AXI-UartLite
187 if(nUartAddress==XPAR_PS7_UART_1_BASEADDR)
188 read(1, (char*)&uchInput, 1); // Get a byte from stdin
189 //MTS No XUartLite hardware or driver.
190 //MTS else
191 //MTS uchInput = XUartLite_RecvByte(nUartAddress);
192 return(uchInput);
193 }
194
195 void suchEndUartByte(u32 unUartAddress, u8 uchByte)
204 {
205 if(unUartAddress==DEFAULT_HYPERTERMINAL_UART_ADDRESS)
206 {
207 printf("%c",uchByte);
208 fflush(stdout);
209 }
210 //MTS No XUartLite hardware or driver.
211 //MTS else
212 //MTS XUartLite_SuchEndByte(unUartAddress, uchByte);
213 }
214
215 u8 checkUartEmpty(u32 unUartAddress)
223 {
224 u8 uchReturnVal=TRUE;
225 u32 unUartStatusRegisterAddress;
226 u32 unStatusRegisterValue;
227 if(unUartAddress==XPAR_PS7_UART_1_BASEADDR)
228 {
229 unUartStatusRegisterAddress = unUartAddress + 0x0000002C;
230 unStatusRegisterValue = Xil_In32(unUartStatusRegisterAddress);
231
232 // Register UART BASE ADDR + 0x2C. Bit 1 is a (1) when Rx FIFO is empty
233 if((unStatusRegisterValue & 0x00000002)==0x00000002)
234 uchReturnVal=TRUE;
235 else
236 uchReturnVal=FALSE;
237 }
238 else
239 {
240 //MTS No XUartLite hardware or driver.
241 //MTS if(XUartLite_IsReceiveEmpty(unUartAddress)==TRUE)
242 //MTS uchReturnVal=TRUE;
243 //MTS else
244 uchReturnVal=FALSE;
245 }
246
247 return(uchReturnVal);
248
249 }
250
251
252 void initializeOLED(u8 *pFont)
261 {
262 // First, initialize the global structure that represents the OLED device
263
264 //GPIO that manages the bit-banged SPI interface to the OLED
265 //XGpio_Initialize(&g_structureOLED.xgpioPort, XPAR_AXI_GPIO_OLED_DEVICE_ID);
266 XGpio_Initialize(&g_structureOLED.xgpioPort, XPAR_AXI_GPIO_OLED_DEVICE_ID);
267 XGpio_SetDataDirection(&g_structureOLED.xgpioPort, 1, 0x00); // Set the OLED peripheral to outputs
268 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, 0x00); // Set all values to zero
269 delay(100);
270
271 // Set the font in the OLED structure
272 g_structureOLED.font = pFont;
273
274 // Init the global variable that represents the OLED bit-bang pins
275 g_structureOLED.portStatus = 0x00;
276
277 // Init and clear the display buffer and the invertered/flipped buffer
278 clearOLEDBuffer(g_structureOLED.writeBuffer);
279 clearOLEDBuffer(g_structureOLED.flippedBuffer);
280
281 // Now, Initialize the OLED display (hardware)
282
283 // Disable VBAT power supply to the OLED integrated switcher
284 // Note: These bits control the Gate voltage on a P-Channel MOSFET
285 g_structureOLED.portStatus |= OLED_VBAT;
286 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, g_structureOLED.portStatus); // Set all values to zero
287 delay(ABOUT_ONE_SECOND/5);
288
289 //Enable VDD power supply to digital logic within OLED
290 g_structureOLED.portStatus |= OLED_VDD;
291 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, g_structureOLED.portStatus); // Set all values to zero
292 delay(ABOUT_ONE_SECOND/5);
293
294 // Disable reset
295 g_structureOLED.portStatus |= OLED_RESET_B;
296 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, g_structureOLED.portStatus); // Set all values to zero
297 delay(ABOUT_ONE_SECOND/5);
298
299 // Set Display Off
300 suchEndOLEDSPI(0xAE);
301 delay(100);
302
303 // Set Display Clock Divide Ratio. Oscillator Frequency
304 suchEndOLEDSPI(0xD5);
305 delay(100);
306 suchEndOLEDSPI(0x80);
307 delay(100);
308
309 // Set Multiplex Ratio
310 suchEndOLEDSPI(0xA8);
311 delay(100);
312 suchEndOLEDSPI(0x1F);
313 delay(100);
314
315 // Set Display Offset
316 suchEndOLEDSPI(0xD3);
317 delay(100);
318 suchEndOLEDSPI(0x00);
319 delay(100);
320
321 // Set Display Start Line
322 suchEndOLEDSPI(0x40);
323 delay(100);
324
325 // Set Charge Pump
326 suchEndOLEDSPI(0x8D);
327 delay(100);
328 suchEndOLEDSPI(0x14);
329 delay(100);
330
331 // Set Segment Re-Map
332 suchEndOLEDSPI(0xA1);
333 delay(100);
334
335 // Set COM Output Scan Direction
336 suchEndOLEDSPI(0xC8);
337 delay(100);
338
339 // Set Com Pins Hardware Configuration
340 suchEndOLEDSPI(0xDA);
341 delay(100);
342 suchEndOLEDSPI(0x02);
343 delay(100);
344
345 // Set Contrast Control
346 suchEndOLEDSPI(0x81);
347 delay(100);
348 suchEndOLEDSPI(0x8F);
349 delay(100);
350
351 // Set Pre-Charge Period
352 suchEndOLEDSPI(0xD9);
353 delay(100);
354 suchEndOLEDSPI(0xF1);
355 delay(100);
356
357 // Set VCOMH Deselect Level
358 suchEndOLEDSPI(0xDB);
359 delay(100);
360 suchEndOLEDSPI(0x40);
361 delay(100);
362
363 // Set Entire Display On
364 suchEndOLEDSPI(0xA4);
365 delay(100);
366
367 // Set Normal/Inverse Display
368 suchEndOLEDSPI(0xA6);
369 delay(100);
370
371 // Enable the VBAT power supply (which is used for the OLED)
372 g_structureOLED.portStatus &= ~OLED_VBAT;
373 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, g_structureOLED.portStatus); // Set all values to zero
374 delay(ABOUT_ONE_SECOND/2); // Long delay for internal OLED switcher to stabilize
375
376 // Set Display On
377 suchEndOLEDSPI(0xAF);
378 delay(100);
379 }
380
381
382 void suchEndOLEDSPI(u8 uchDataToWrite)
391 {
392 int i;
393
394 for(i=7;i>=0;i--)
395 {
396 // Set the OLED_SDIN bit
397 if(((uchDataToWrite >> i) & 0x01)==0x01)
398 g_structureOLED.portStatus |= OLED_SDIN;
399 else
400 g_structureOLED.portStatus &= ~OLED_SDIN;
401 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, g_structureOLED.portStatus);
402 delay(100);
403
404 // Clock in the data via a rising edge of SCLK
405 g_structureOLED.portStatus |= OLED_SCLK;
406 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, g_structureOLED.portStatus);
407 delay(100);
408 g_structureOLED.portStatus &= ~OLED_SCLK;
409 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, g_structureOLED.portStatus);
410 delay(100);
411 }
412 }
413
414
415 void clearOLEDBuffer(u8 *pauchBuffer)
424 {
425 int i;
426
427 for(i=0;i<512;i++)
428 pauchBuffer[i] = 0x00;
429
430 }
431
432 void displayOLEDBuffer(u8 *pauchBuffer)
442 {
443 int column=0;
444 int page=0;
445 u8 *p;
446 u8 uchPixelValue=0;
447
448 // Set the display mode to page based transfers
449 suchEndOLEDSPI(0x20);
450 delay(100);
451 suchEndOLEDSPI(0x02);
452 delay(100);
453
454 // Set the page pointer lower nibble to 0x0
455 suchEndOLEDSPI(0x00);
456 delay(100);
457
458 // Set the page pointer upper nibble to 0x0
459 suchEndOLEDSPI(0x10);
460 delay(100);
461
462 // Write 4 pages worth of data
463 // Note that the SSD1306 controller can handle 128x64 displays, but the OLED
464 // used on zedboard is only 128x32. Data is provided to the display as (4) pages of 128 bytes each.
465 p = pauchBuffer;
466 for(page=0;page<4;page++)
467 {
468 // Enable Command Mode (shut off data mode)
469 g_structureOLED.portStatus &= ~OLED_DATA_COMMAND_B;
470 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, g_structureOLED.portStatus); // Set all values to zero
471 delay(100); // Long delay for internal OLED switcher to stabilize
472
473 // Set the page command by issuing 0xB0 (page0), 0xB1 (page1) etc.
474 suchEndOLEDSPI((0xB0+page));
475
476 // Enable the Data mode (shut off command mode)
477 g_structureOLED.portStatus |= OLED_DATA_COMMAND_B;
478 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, g_structureOLED.portStatus); // Set all values to zero
479 delay(100); // Long delay for internal OLED switcher to stabilize
480
481 for(column=0;column<128;column++)
482 {
483 uchPixelValue = *p;
484 suchEndOLEDSPI(uchPixelValue); // change this to zero
485 p++;
486 }
487 }
488
489 // Enable Command Mode (shut off data mode)
490 g_structureOLED.portStatus &= ~OLED_DATA_COMMAND_B;
491 XGpio_DiscreteWrite(&g_structureOLED.xgpioPort, 1, g_structureOLED.portStatus); // Set all values to zero
492 delay(100); // Long delay for internal OLED switcher to stabilize
493 }
494
495 void putCharOLED(int x, int y, char chCharacter)
506 {
507 int i;
508 int nDisplayBufferIndex=0;
509 int nFontIndex=0;
510
511 // Create the index location for the character into the display memory
512 nDisplayBufferIndex = (x * 8) + (y * 16 * 8);
513
514 // Make sure the character has a valid value, else ignore
515 if(chCharacter >=0 && chCharacter<128)
516 {
517 nFontIndex = chCharacter * 8;
518
519 for(i=nDisplayBufferIndex;i<nDisplayBufferIndex+8;i++)
520 {
521 g_structureOLED.writeBuffer[i] = g_structureOLED.font[nFontIndex];
522 nFontIndex++;
523 }
524 }
525 }
526
527 void printfToBufferOLED(int x, int y,char *chString)
538 {
539 int nStringLength;
540 int nInitialDisplayLocation;
541 int nRemainingDisplayLength;
542 int i;
543 int xIndex=0;
544 int yIndex=0;
545 nStringLength = strlen(chString);
546
547 // Will the string fit on the display? If not, truncate the length
548 nInitialDisplayLocation = y*16 + x;
549 nRemainingDisplayLength = 64 - nInitialDisplayLocation;
550 if(nStringLength > nRemainingDisplayLength)
551 nStringLength = nRemainingDisplayLength;
552
553 xIndex = x;
554 yIndex = y;
555 for(i=0;i<nStringLength;i++)
556 {
557 putCharOLED(xIndex,yIndex,chString[i]);
558 xIndex++;
559 if(xIndex==16)
560 {
561 xIndex=0;
562 yIndex++;
563 }
564 }
565 }
566
567 void printfToOLED(int x, int y,char *chString)
579 {
580 printfToBufferOLED(x,y,chString);
581 flipAndCopyDisplayBuffer(g_structureOLED.writeBuffer, g_structureOLED.flippedBuffer);
582 displayOLEDBuffer(g_structureOLED.flippedBuffer);
583 }
584
585
586 void flipAndCopyDisplayBuffer(u8 *pauchSourceBuffer, u8 *pauchDestinationBuffer)
597 {
598 int i,x,y;
599 u8 uchTempWord1;
600 u8 uchTempWord2;
601 u8 uchTempWord3;
602
603 for(y=0;y<4;y++)
604 {
605 for(x=0;x<128;x++)
606 {
607 uchTempWord1 = pauchSourceBuffer[511-((y*128)+x)];
608 uchTempWord3 = 0;
609 for(i=0;i<8;i++)
610 {
611 uchTempWord2 = (uchTempWord1 >> (7-i)) & 0x01; // shift the bit to the bit0 location and mask off
612 uchTempWord2 = uchTempWord2 << i; // shift the bit back to the desired location.
613 uchTempWord3 += uchTempWord2;
614 }
615 pauchDestinationBuffer[((y*128)+x)] = uchTempWord3;
616 }
617 }
618 }
619
620 int htoi(char *sStr)
621 {
622 int nRet=0;
623 u8 uchEnd=0;
624 u8 uchCount;
625 for(uchCount=0;uchCount<100;uchCount++)
626 {
627 switch(sStr[uchCount])
628 {
629 case '0': nRet=nRet<<4; nRet=nRet+0; break;
630 case '1': nRet=nRet<<4; nRet=nRet+1; break;
631 case '2': nRet=nRet<<4; nRet=nRet+2; break;
632 case '3': nRet=nRet<<4; nRet=nRet+3; break;
633 case '4': nRet=nRet<<4; nRet=nRet+4; break;
634 case '5': nRet=nRet<<4; nRet=nRet+5; break;
635 case '6': nRet=nRet<<4; nRet=nRet+6; break;
636 case '7': nRet=nRet<<4; nRet=nRet+7; break;
637 case '8': nRet=nRet<<4; nRet=nRet+8; break;
638 case '9': nRet=nRet<<4; nRet=nRet+9; break;
639 case 'a': nRet=nRet<<4; nRet=nRet+10; break;
640 case 'b': nRet=nRet<<4; nRet=nRet+11; break;
641 case 'c': nRet=nRet<<4; nRet=nRet+12; break;
642 case 'd': nRet=nRet<<4; nRet=nRet+13; break;
643 case 'e': nRet=nRet<<4; nRet=nRet+14; break;
644 case 'f': nRet=nRet<<4; nRet=nRet+15; break;
645 case 'A': nRet=nRet<<4; nRet=nRet+10; break;
646 case 'B': nRet=nRet<<4; nRet=nRet+11; break;
647 case 'C': nRet=nRet<<4; nRet=nRet+12; break;
648 case 'D': nRet=nRet<<4; nRet=nRet+13; break;
649 case 'E': nRet=nRet<<4; nRet=nRet+14; break;
650 case 'F': nRet=nRet<<4; nRet=nRet+15; break;
651 default: uchEnd=1; break;
652 }
653 if(uchEnd)
654 {
655 break;
656 }
657 }
658 return nRet;
659 }