More generic and scalable parser
Dependencies: SLCD mbed-rtos mbed
Fork of Serial_IO_test_v6 by
serialO_v6.cpp@3:2266158bf72f, 2015-03-18 (annotated)
- Committer:
- scohennm
- Date:
- Wed Mar 18 19:08:22 2015 +0000
- Revision:
- 3:2266158bf72f
- Parent:
- serialO_v5.cpp@2:8196b4cc681b
Example of checking for a valid note:
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
scohennm | 2:8196b4cc681b | 1 | #include "mbed.h" |
scohennm | 2:8196b4cc681b | 2 | #include <iostream> |
scohennm | 2:8196b4cc681b | 3 | #include <stdio.h> |
scohennm | 2:8196b4cc681b | 4 | #include <ctype.h> |
scohennm | 2:8196b4cc681b | 5 | #include <string.h> |
scohennm | 2:8196b4cc681b | 6 | #include <locale.h> |
scohennm | 2:8196b4cc681b | 7 | #include "rtos.h" |
scohennm | 2:8196b4cc681b | 8 | #include "SLCD.h" |
scohennm | 3:2266158bf72f | 9 | // Debug printout control |
scohennm | 3:2266158bf72f | 10 | #define PRINTDBUG |
scohennm | 3:2266158bf72f | 11 | #define PROGNAME "SerialIO v6\n\r" |
scohennm | 2:8196b4cc681b | 12 | |
scohennm | 2:8196b4cc681b | 13 | #define LCDLEN 10 |
scohennm | 2:8196b4cc681b | 14 | #define MAXCHAR 4 |
scohennm | 2:8196b4cc681b | 15 | #define ALL8 "8888" |
scohennm | 2:8196b4cc681b | 16 | #define LCDUPDATE 100 //ms |
scohennm | 2:8196b4cc681b | 17 | #define LEDBLINKTIME 300 // ms *** NOTE Change of units *** |
scohennm | 2:8196b4cc681b | 18 | #define SERIALREADTIME 50 //ms |
scohennm | 2:8196b4cc681b | 19 | // ASCII constants |
scohennm | 2:8196b4cc681b | 20 | #define CR '\r' |
scohennm | 3:2266158bf72f | 21 | #define ALLNOTES "CDEFGAB" // Note only 7 unique notes. |
scohennm | 3:2266158bf72f | 22 | #define NUMTONES 10 |
scohennm | 3:2266158bf72f | 23 | #define NONOTE 8 |
scohennm | 3:2266158bf72f | 24 | #define NOTEOFFSET 1 |
scohennm | 2:8196b4cc681b | 25 | |
scohennm | 2:8196b4cc681b | 26 | |
scohennm | 2:8196b4cc681b | 27 | |
scohennm | 3:2266158bf72f | 28 | float diatonicScale[NUMTONES] = {246.94, 261.63,293.66,329.63,349.23,392.00,440.00,493.88,523.25,587.33}; |
scohennm | 2:8196b4cc681b | 29 | |
scohennm | 2:8196b4cc681b | 30 | DigitalOut rLed(LED_RED); |
scohennm | 2:8196b4cc681b | 31 | |
scohennm | 2:8196b4cc681b | 32 | |
scohennm | 2:8196b4cc681b | 33 | Serial pc(USBTX, USBRX); // tx, rx |
scohennm | 2:8196b4cc681b | 34 | SLCD slcd; //define LCD display |
scohennm | 2:8196b4cc681b | 35 | char rxChar; |
scohennm | 2:8196b4cc681b | 36 | char rxString[LCDLEN]; |
scohennm | 2:8196b4cc681b | 37 | string rxRealString; |
scohennm | 2:8196b4cc681b | 38 | |
scohennm | 2:8196b4cc681b | 39 | void clearString (char * aString){ |
scohennm | 2:8196b4cc681b | 40 | int i; |
scohennm | 2:8196b4cc681b | 41 | int sSize = sizeof(aString); |
scohennm | 2:8196b4cc681b | 42 | |
scohennm | 2:8196b4cc681b | 43 | for (i=0; i< sSize; i++){ |
scohennm | 2:8196b4cc681b | 44 | aString[i] = NULL; |
scohennm | 2:8196b4cc681b | 45 | } |
scohennm | 2:8196b4cc681b | 46 | return; |
scohennm | 2:8196b4cc681b | 47 | } |
scohennm | 2:8196b4cc681b | 48 | |
scohennm | 2:8196b4cc681b | 49 | |
scohennm | 3:2266158bf72f | 50 | int isNote(char theNote){ //check for valid onte |
scohennm | 3:2266158bf72f | 51 | int noteListLen = sizeof(ALLNOTES); |
scohennm | 3:2266158bf72f | 52 | int pos = NONOTE; |
scohennm | 3:2266158bf72f | 53 | int i; |
scohennm | 3:2266158bf72f | 54 | for (i=0; i<noteListLen; i++){ |
scohennm | 3:2266158bf72f | 55 | if (ALLNOTES[i] == theNote){ |
scohennm | 3:2266158bf72f | 56 | pos = i; |
scohennm | 3:2266158bf72f | 57 | break; |
scohennm | 3:2266158bf72f | 58 | } |
scohennm | 3:2266158bf72f | 59 | } |
scohennm | 3:2266158bf72f | 60 | return (pos); |
scohennm | 3:2266158bf72f | 61 | } |
scohennm | 3:2266158bf72f | 62 | |
scohennm | 2:8196b4cc681b | 63 | |
scohennm | 2:8196b4cc681b | 64 | void LCDMessNoDwell(char *lMess){ |
scohennm | 2:8196b4cc681b | 65 | slcd.Home(); |
scohennm | 2:8196b4cc681b | 66 | slcd.clear(); |
scohennm | 2:8196b4cc681b | 67 | slcd.printf(lMess); |
scohennm | 2:8196b4cc681b | 68 | } |
scohennm | 2:8196b4cc681b | 69 | |
scohennm | 2:8196b4cc681b | 70 | // use "thread" in the name to keep things straight |
scohennm | 2:8196b4cc681b | 71 | // note the use of void constant * args - understand memory resources |
scohennm | 2:8196b4cc681b | 72 | // Thes are "forever loops" |
scohennm | 2:8196b4cc681b | 73 | void LCDdis_thread(void const *args){ |
scohennm | 2:8196b4cc681b | 74 | while(true) { |
scohennm | 2:8196b4cc681b | 75 | LCDMessNoDwell(rxString); |
scohennm | 2:8196b4cc681b | 76 | Thread::wait(LCDUPDATE); |
scohennm | 2:8196b4cc681b | 77 | } |
scohennm | 2:8196b4cc681b | 78 | } |
scohennm | 2:8196b4cc681b | 79 | |
scohennm | 2:8196b4cc681b | 80 | void serial_thread(void const *args){ |
scohennm | 2:8196b4cc681b | 81 | static int charIndex =0; |
scohennm | 2:8196b4cc681b | 82 | int rxStringLen; |
scohennm | 3:2266158bf72f | 83 | int noteOK; |
scohennm | 2:8196b4cc681b | 84 | while(true) { |
scohennm | 2:8196b4cc681b | 85 | if (pc.readable()) { // only read from the serial port if there is a character |
scohennm | 3:2266158bf72f | 86 | rxChar= toupper(pc.getc()); // reading clears the buffer |
scohennm | 3:2266158bf72f | 87 | noteOK = isNote(rxChar); |
scohennm | 2:8196b4cc681b | 88 | // construct a 4-digit string for the LCD |
scohennm | 2:8196b4cc681b | 89 | // check for carriage return |
scohennm | 2:8196b4cc681b | 90 | if (rxChar == CR) { |
scohennm | 2:8196b4cc681b | 91 | rxRealString.assign(rxString); |
scohennm | 3:2266158bf72f | 92 | rxStringLen = rxRealString.length(); |
scohennm | 3:2266158bf72f | 93 | #ifdef PRINTDBUG |
scohennm | 2:8196b4cc681b | 94 | pc.printf("%s - StringLen = %d OK \n\r", rxString, rxStringLen); |
scohennm | 3:2266158bf72f | 95 | #endif |
scohennm | 2:8196b4cc681b | 96 | charIndex = 0; // start building string from position zero next time around |
scohennm | 2:8196b4cc681b | 97 | } else { |
scohennm | 2:8196b4cc681b | 98 | if(charIndex == 0) clearString(rxString); |
scohennm | 2:8196b4cc681b | 99 | rxString[charIndex] = rxChar; |
scohennm | 2:8196b4cc681b | 100 | rxRealString.assign(rxString); |
scohennm | 3:2266158bf72f | 101 | #ifdef PRINTDBUG |
scohennm | 3:2266158bf72f | 102 | if(noteOK != NONOTE){ |
scohennm | 3:2266158bf72f | 103 | pc.printf("%s - IsNote - %4.2f\n\r", rxString, diatonicScale[noteOK + NOTEOFFSET]); |
scohennm | 3:2266158bf72f | 104 | } else { |
scohennm | 3:2266158bf72f | 105 | pc.printf("%s - Not a Note\n\r", rxString); |
scohennm | 3:2266158bf72f | 106 | } |
scohennm | 3:2266158bf72f | 107 | #endif |
scohennm | 2:8196b4cc681b | 108 | charIndex = (charIndex + 1)% (MAXCHAR); // Only allow 4 characters then roll over |
scohennm | 2:8196b4cc681b | 109 | |
scohennm | 2:8196b4cc681b | 110 | } |
scohennm | 2:8196b4cc681b | 111 | } |
scohennm | 2:8196b4cc681b | 112 | Thread::wait(SERIALREADTIME); |
scohennm | 2:8196b4cc681b | 113 | } |
scohennm | 2:8196b4cc681b | 114 | } |
scohennm | 2:8196b4cc681b | 115 | |
scohennm | 2:8196b4cc681b | 116 | int main() |
scohennm | 2:8196b4cc681b | 117 | { |
scohennm | 2:8196b4cc681b | 118 | |
scohennm | 2:8196b4cc681b | 119 | Thread lthread(LCDdis_thread); |
scohennm | 2:8196b4cc681b | 120 | Thread serthread(serial_thread); |
scohennm | 2:8196b4cc681b | 121 | |
scohennm | 2:8196b4cc681b | 122 | sprintf(rxString,"%s",ALL8); // just put something on the LCD to show it's working |
scohennm | 3:2266158bf72f | 123 | |
scohennm | 3:2266158bf72f | 124 | #ifdef PRINTDBUG |
scohennm | 3:2266158bf72f | 125 | pc.printf(PROGNAME); |
scohennm | 3:2266158bf72f | 126 | #endif |
scohennm | 2:8196b4cc681b | 127 | |
scohennm | 2:8196b4cc681b | 128 | while (true) { |
scohennm | 2:8196b4cc681b | 129 | rLed = !rLed; // toggle led |
scohennm | 2:8196b4cc681b | 130 | Thread::wait(LEDBLINKTIME); |
scohennm | 2:8196b4cc681b | 131 | } |
scohennm | 2:8196b4cc681b | 132 | } |