Read up to 8 debounced switches from serial port

Dependencies:   mbed

Committer:
jm
Date:
Sat Feb 12 16:46:49 2011 +0000
Revision:
0:f3a5f6fe1c03
jmSwitch Command Line Interface Module

Who changed what in which revision?

UserRevisionLine numberNew contents of line
jm 0:f3a5f6fe1c03 1 /*************************************************************************
jm 0:f3a5f6fe1c03 2 * @file jmRingBuffer.c
jm 0:f3a5f6fe1c03 3 * @brief Command Line Rx Ring Buffer
jm 0:f3a5f6fe1c03 4 *
jm 0:f3a5f6fe1c03 5 * @date Feb 12, 2011
jm 0:f3a5f6fe1c03 6 */
jm 0:f3a5f6fe1c03 7
jm 0:f3a5f6fe1c03 8
jm 0:f3a5f6fe1c03 9 #include "jmRingBuffer.h"
jm 0:f3a5f6fe1c03 10 #include "stdio.h"
jm 0:f3a5f6fe1c03 11
jm 0:f3a5f6fe1c03 12 // static creation of Command Line Buffer
jm 0:f3a5f6fe1c03 13 struct RingBuffer Line, *pLine;
jm 0:f3a5f6fe1c03 14
jm 0:f3a5f6fe1c03 15 /** @brief Command line ring buffer initialization.
jm 0:f3a5f6fe1c03 16 * @param none
jm 0:f3a5f6fe1c03 17 * @returns none
jm 0:f3a5f6fe1c03 18 */
jm 0:f3a5f6fe1c03 19 void InitCommandLineRingBuffer(void){
jm 0:f3a5f6fe1c03 20 pLine = &Line;
jm 0:f3a5f6fe1c03 21 FlushRingBuffer(pLine);
jm 0:f3a5f6fe1c03 22 }
jm 0:f3a5f6fe1c03 23
jm 0:f3a5f6fe1c03 24 /** @brief Move ring head pointer foward.
jm 0:f3a5f6fe1c03 25 * @param *p pointer to ring buffer
jm 0:f3a5f6fe1c03 26 * @returns none
jm 0:f3a5f6fe1c03 27 */
jm 0:f3a5f6fe1c03 28 void NextHead(struct RingBuffer *p)
jm 0:f3a5f6fe1c03 29 { p->head++;
jm 0:f3a5f6fe1c03 30 if(p->head >= DimRingBuffer)
jm 0:f3a5f6fe1c03 31 p->head=0;
jm 0:f3a5f6fe1c03 32 }
jm 0:f3a5f6fe1c03 33
jm 0:f3a5f6fe1c03 34 /** @brief Move ring tail pointer foward.
jm 0:f3a5f6fe1c03 35 * @param pointer to ring buffer
jm 0:f3a5f6fe1c03 36 * @returns none
jm 0:f3a5f6fe1c03 37 */
jm 0:f3a5f6fe1c03 38 void NextTail(struct RingBuffer *p)
jm 0:f3a5f6fe1c03 39 { p->tail++;
jm 0:f3a5f6fe1c03 40 if(p->tail >= DimRingBuffer)
jm 0:f3a5f6fe1c03 41 p->tail=0;
jm 0:f3a5f6fe1c03 42 }
jm 0:f3a5f6fe1c03 43
jm 0:f3a5f6fe1c03 44 /** @brief Check if buffer full.
jm 0:f3a5f6fe1c03 45 * @param *p pointer to ring buffer
jm 0:f3a5f6fe1c03 46 * @returns true if full, false otherwise
jm 0:f3a5f6fe1c03 47 */
jm 0:f3a5f6fe1c03 48 bool Full(struct RingBuffer *p)
jm 0:f3a5f6fe1c03 49 { if(p->qty >= DimRingBuffer)
jm 0:f3a5f6fe1c03 50 return true;
jm 0:f3a5f6fe1c03 51 else
jm 0:f3a5f6fe1c03 52 return false;
jm 0:f3a5f6fe1c03 53 }
jm 0:f3a5f6fe1c03 54
jm 0:f3a5f6fe1c03 55 /** @brief Insert a char in buffer.
jm 0:f3a5f6fe1c03 56 * @param c unsigned char to be inserted
jm 0:f3a5f6fe1c03 57 * @param *p pointer to ring buffer
jm 0:f3a5f6fe1c03 58 * @returns none
jm 0:f3a5f6fe1c03 59 */
jm 0:f3a5f6fe1c03 60 void Insert(unsigned char c, struct RingBuffer *p)
jm 0:f3a5f6fe1c03 61 { if(Full(p))
jm 0:f3a5f6fe1c03 62 NextHead(p);
jm 0:f3a5f6fe1c03 63 else
jm 0:f3a5f6fe1c03 64 p->qty++;
jm 0:f3a5f6fe1c03 65
jm 0:f3a5f6fe1c03 66 p->Buffer[p->tail]=c;
jm 0:f3a5f6fe1c03 67 NextTail(p);
jm 0:f3a5f6fe1c03 68 }
jm 0:f3a5f6fe1c03 69
jm 0:f3a5f6fe1c03 70 /** @brief Check if ring buffer not empty.
jm 0:f3a5f6fe1c03 71 * @param *p pointer to ring buffer
jm 0:f3a5f6fe1c03 72 * @returns true if full, false otherwise
jm 0:f3a5f6fe1c03 73 */
jm 0:f3a5f6fe1c03 74 bool NotEmpty(struct RingBuffer *p)
jm 0:f3a5f6fe1c03 75 { if(p->qty == 0)
jm 0:f3a5f6fe1c03 76 return false ;
jm 0:f3a5f6fe1c03 77 else
jm 0:f3a5f6fe1c03 78 return true;
jm 0:f3a5f6fe1c03 79 }
jm 0:f3a5f6fe1c03 80
jm 0:f3a5f6fe1c03 81 /** @brief Extract a char from ring buffer.
jm 0:f3a5f6fe1c03 82 * @param *p pointer to ring buffer
jm 0:f3a5f6fe1c03 83 * @returns unsigned char
jm 0:f3a5f6fe1c03 84 */
jm 0:f3a5f6fe1c03 85 unsigned char Extract(struct RingBuffer *p)
jm 0:f3a5f6fe1c03 86 { unsigned char c;
jm 0:f3a5f6fe1c03 87 c = p->Buffer[p->head];
jm 0:f3a5f6fe1c03 88 if(NotEmpty(p))
jm 0:f3a5f6fe1c03 89 { NextHead(p);
jm 0:f3a5f6fe1c03 90 p->qty--;
jm 0:f3a5f6fe1c03 91 }
jm 0:f3a5f6fe1c03 92 return c;
jm 0:f3a5f6fe1c03 93 }
jm 0:f3a5f6fe1c03 94
jm 0:f3a5f6fe1c03 95 /** @brief Flush ring buffer.
jm 0:f3a5f6fe1c03 96 * @param *p pointer to ring buffer
jm 0:f3a5f6fe1c03 97 * @returns none
jm 0:f3a5f6fe1c03 98 */
jm 0:f3a5f6fe1c03 99 void FlushRingBuffer(struct RingBuffer *p)
jm 0:f3a5f6fe1c03 100 { int i;
jm 0:f3a5f6fe1c03 101 p->head = 0;
jm 0:f3a5f6fe1c03 102 p->tail = 0;
jm 0:f3a5f6fe1c03 103 p->qty = 0;
jm 0:f3a5f6fe1c03 104 for(i=0;i<DimRingBuffer;i++)p->Buffer[i]=0;
jm 0:f3a5f6fe1c03 105 }
jm 0:f3a5f6fe1c03 106
jm 0:f3a5f6fe1c03 107 /** @brief Delete last char from ring buffer.
jm 0:f3a5f6fe1c03 108 * @param *p pointer to ring buffer
jm 0:f3a5f6fe1c03 109 * @returns none
jm 0:f3a5f6fe1c03 110 */
jm 0:f3a5f6fe1c03 111 void DelChar(struct RingBuffer *p)
jm 0:f3a5f6fe1c03 112 { if(p->qty != 0){
jm 0:f3a5f6fe1c03 113 if(p->tail==0)p->tail=DimRingBuffer;
jm 0:f3a5f6fe1c03 114 else p->tail--;
jm 0:f3a5f6fe1c03 115 p->qty--;
jm 0:f3a5f6fe1c03 116 }
jm 0:f3a5f6fe1c03 117 }
jm 0:f3a5f6fe1c03 118
jm 0:f3a5f6fe1c03 119 /** @brief Remove a command line from ring buffer.
jm 0:f3a5f6fe1c03 120 * @param c end command identifier unsigned char
jm 0:f3a5f6fe1c03 121 * @param *p pointer to ring buffer
jm 0:f3a5f6fe1c03 122 * @returns none
jm 0:f3a5f6fe1c03 123 */
jm 0:f3a5f6fe1c03 124 void NextCommand(unsigned char c, struct RingBuffer *p){
jm 0:f3a5f6fe1c03 125 // remove all char till end identifier is found
jm 0:f3a5f6fe1c03 126 while(NotEmpty(p) && p->Buffer[p->head] != c)
jm 0:f3a5f6fe1c03 127 { NextHead(p);
jm 0:f3a5f6fe1c03 128 p->qty--;
jm 0:f3a5f6fe1c03 129 }
jm 0:f3a5f6fe1c03 130
jm 0:f3a5f6fe1c03 131 // remove end identifier
jm 0:f3a5f6fe1c03 132 if(NotEmpty(p)&& p->Buffer[p->head] == c)
jm 0:f3a5f6fe1c03 133 { NextHead(p);
jm 0:f3a5f6fe1c03 134 p->qty--;
jm 0:f3a5f6fe1c03 135 }
jm 0:f3a5f6fe1c03 136 }
jm 0:f3a5f6fe1c03 137
jm 0:f3a5f6fe1c03 138 /** @brief View ring buffer content.
jm 0:f3a5f6fe1c03 139 * Print ring buffer content
jm 0:f3a5f6fe1c03 140 * @param *p pointer to ring buffer
jm 0:f3a5f6fe1c03 141 * @returns none
jm 0:f3a5f6fe1c03 142 */
jm 0:f3a5f6fe1c03 143 void ViewRingBuffer(struct RingBuffer *p){
jm 0:f3a5f6fe1c03 144 int i,j;
jm 0:f3a5f6fe1c03 145
jm 0:f3a5f6fe1c03 146 printf("\nRingBuffer Qty: %d \nContent: ",p->qty);
jm 0:f3a5f6fe1c03 147
jm 0:f3a5f6fe1c03 148 for(j=0,i=p->head;j<p->qty;j++){
jm 0:f3a5f6fe1c03 149 printf("%c",p->Buffer[i]);
jm 0:f3a5f6fe1c03 150 if(i++>DimRingBuffer)i=0;
jm 0:f3a5f6fe1c03 151 }
jm 0:f3a5f6fe1c03 152 printf("\n");
jm 0:f3a5f6fe1c03 153 }
jm 0:f3a5f6fe1c03 154
jm 0:f3a5f6fe1c03 155 /** @brief Extract a word from ring buffer.
jm 0:f3a5f6fe1c03 156 * The extracted word is put in the array pointed by word
jm 0:f3a5f6fe1c03 157 * @param p pointer to a ring buffer
jm 0:f3a5f6fe1c03 158 * @param word pointer to array of char
jm 0:f3a5f6fe1c03 159 * @returns true if a word is extracted otherwise returns false
jm 0:f3a5f6fe1c03 160 */
jm 0:f3a5f6fe1c03 161 bool ExtractWord(struct RingBuffer *p, char * word){
jm 0:f3a5f6fe1c03 162 unsigned char c;
jm 0:f3a5f6fe1c03 163 int i,j;
jm 0:f3a5f6fe1c03 164 j=0;
jm 0:f3a5f6fe1c03 165
jm 0:f3a5f6fe1c03 166 if(NotEmpty(p)){
jm 0:f3a5f6fe1c03 167 for(i=0;i<WordMaxSize-1;i++){
jm 0:f3a5f6fe1c03 168 // extract a char from Rx ring buffer
jm 0:f3a5f6fe1c03 169 c=Extract(p);
jm 0:f3a5f6fe1c03 170
jm 0:f3a5f6fe1c03 171 // remove leading blanks
jm 0:f3a5f6fe1c03 172 if(c==' ' && j==0)continue;
jm 0:f3a5f6fe1c03 173
jm 0:f3a5f6fe1c03 174 // end of word or end of command line
jm 0:f3a5f6fe1c03 175 if(c==' ' || c==nl)break;
jm 0:f3a5f6fe1c03 176
jm 0:f3a5f6fe1c03 177 // build the Word
jm 0:f3a5f6fe1c03 178 word[j++]=c;
jm 0:f3a5f6fe1c03 179 }
jm 0:f3a5f6fe1c03 180 // 0 string termination
jm 0:f3a5f6fe1c03 181 word[j]=0;
jm 0:f3a5f6fe1c03 182 if(j>0)return true;
jm 0:f3a5f6fe1c03 183 }
jm 0:f3a5f6fe1c03 184 return false;
jm 0:f3a5f6fe1c03 185 }
jm 0:f3a5f6fe1c03 186
jm 0:f3a5f6fe1c03 187 /** @brief Extract an unsigned int from ring buffer.
jm 0:f3a5f6fe1c03 188 * Convert a word from buffer into an integer between min and max values
jm 0:f3a5f6fe1c03 189 * Value converted should be between min and max values.
jm 0:f3a5f6fe1c03 190 * Value should be decimal or hexadecimal (beginning by 0x or 0X)
jm 0:f3a5f6fe1c03 191 * @param p pointer to ring buffer
jm 0:f3a5f6fe1c03 192 * @param result pointer to unsigned int
jm 0:f3a5f6fe1c03 193 * @param min minimum limit
jm 0:f3a5f6fe1c03 194 * @param max maximum limit
jm 0:f3a5f6fe1c03 195 * @returns true if value is converted beetween limits, including limits.
jm 0:f3a5f6fe1c03 196 */
jm 0:f3a5f6fe1c03 197 bool ExtractUInteger(struct RingBuffer *p, unsigned int *result, unsigned int min, unsigned int max){
jm 0:f3a5f6fe1c03 198 unsigned int i ;
jm 0:f3a5f6fe1c03 199 char word[WordMaxSize-1];
jm 0:f3a5f6fe1c03 200
jm 0:f3a5f6fe1c03 201 if(ExtractWord(p,word)){ // Extract string value
jm 0:f3a5f6fe1c03 202 if(word[0]=='0' && (word[1]=='x' || word[1]=='X')) {
jm 0:f3a5f6fe1c03 203 sscanf(word,"%x",&i); // convert hexadecimal input
jm 0:f3a5f6fe1c03 204 }
jm 0:f3a5f6fe1c03 205 else
jm 0:f3a5f6fe1c03 206 sscanf(word,"%d",&i); // convert decimal input
jm 0:f3a5f6fe1c03 207
jm 0:f3a5f6fe1c03 208 if(i>=min && i<=max){
jm 0:f3a5f6fe1c03 209 *result = i;
jm 0:f3a5f6fe1c03 210 return true;
jm 0:f3a5f6fe1c03 211 }
jm 0:f3a5f6fe1c03 212 }
jm 0:f3a5f6fe1c03 213 *result = 0;
jm 0:f3a5f6fe1c03 214 return false;
jm 0:f3a5f6fe1c03 215 }