fork the master
Dependencies: TextLCD mbed-rtos mbed
Fork of Pacemaker by
main.cpp@18:e0bc54c0dbeb, 2014-12-02 (annotated)
- Committer:
- Jing_Qiu
- Date:
- Tue Dec 02 22:12:44 2014 +0000
- Revision:
- 18:e0bc54c0dbeb
- Parent:
- 17:6c44d5317c49
updated with fixes from mbed testing
Who changed what in which revision?
User | Revision | Line number | New contents of line |
---|---|---|---|
mfrede | 0:6d04b1860ecf | 1 | /* |
mfrede | 0:6d04b1860ecf | 2 | * Pacemaker MBED code |
mfrede | 0:6d04b1860ecf | 3 | * |
mfrede | 0:6d04b1860ecf | 4 | * CIS541 Embedded Systems for Life Critical Applications |
amlittle042 | 15:4cd550c14f97 | 5 | * Authors: Jing Qiu |
amlittle042 | 15:4cd550c14f97 | 6 | * Michael Frederick |
amlittle042 | 15:4cd550c14f97 | 7 | * Tim Hu |
amlittle042 | 15:4cd550c14f97 | 8 | * Alex Little |
mfrede | 0:6d04b1860ecf | 9 | * |
mfrede | 1:e37d0cad77e2 | 10 | */ |
Jing_Qiu | 3:34e9766539fe | 11 | |
mfrede | 1:e37d0cad77e2 | 12 | #include "mbed.h" |
mfrede | 1:e37d0cad77e2 | 13 | #include "LPC17xx.h" |
mfrede | 1:e37d0cad77e2 | 14 | #include "TextLCD.h" |
mfrede | 1:e37d0cad77e2 | 15 | #include "rtos.h" |
mfrede | 11:dd278ffcb31f | 16 | #include <ctype.h> |
mfrede | 1:e37d0cad77e2 | 17 | |
Jing_Qiu | 3:34e9766539fe | 18 | #define AVI_h 100 |
Jing_Qiu | 3:34e9766539fe | 19 | #define AVI_l 30 |
Jing_Qiu | 3:34e9766539fe | 20 | #define PVARP_h 500 |
Jing_Qiu | 3:34e9766539fe | 21 | #define PVARP_l 150 |
Jing_Qiu | 3:34e9766539fe | 22 | |
Jing_Qiu | 3:34e9766539fe | 23 | #define VRP_h 500 |
Jing_Qiu | 3:34e9766539fe | 24 | #define VRP_l 150 |
Jing_Qiu | 3:34e9766539fe | 25 | #define BM(x) (1<<(x)) |
Jing_Qiu | 18:e0bc54c0dbeb | 26 | #define PULSE_WIDTH_V 10 |
Jing_Qiu | 18:e0bc54c0dbeb | 27 | #define PULSE_WIDTH_A 10 |
Jing_Qiu | 3:34e9766539fe | 28 | |
amlittle042 | 15:4cd550c14f97 | 29 | TextLCD lcd(p15, p16, p17, p18, p19, p20, TextLCD::LCD16x2); |
Jing_Qiu | 5:376358077dc8 | 30 | |
Jing_Qiu | 3:34e9766539fe | 31 | int LRI_h = 1666; |
Jing_Qiu | 3:34e9766539fe | 32 | int LRI_l = 666; |
Jing_Qiu | 5:376358077dc8 | 33 | int observation_interval=10000; //ms |
mfrede | 8:ce2565cfe709 | 34 | bool setObservation = false; |
Jing_Qiu | 3:34e9766539fe | 35 | |
mfrede | 1:e37d0cad77e2 | 36 | Serial pc(USBTX, USBRX); |
amlittle042 | 15:4cd550c14f97 | 37 | |
mfrede | 1:e37d0cad77e2 | 38 | char mode = 'N'; |
Jing_Qiu | 3:34e9766539fe | 39 | |
mfrede | 1:e37d0cad77e2 | 40 | int a_clock; |
mfrede | 1:e37d0cad77e2 | 41 | int v_clock; |
mfrede | 6:6bc5e65ada4e | 42 | bool setobservation = false; |
mfrede | 1:e37d0cad77e2 | 43 | |
Jing_Qiu | 5:376358077dc8 | 44 | int beat; |
Jing_Qiu | 5:376358077dc8 | 45 | |
amlittle042 | 15:4cd550c14f97 | 46 | InterruptIn atrial_int(p21); // double check me |
amlittle042 | 15:4cd550c14f97 | 47 | InterruptIn vent_int(p22); // me too |
Jing_Qiu | 3:34e9766539fe | 48 | |
Jing_Qiu | 18:e0bc54c0dbeb | 49 | DigitalOut aPace(p23); |
Jing_Qiu | 18:e0bc54c0dbeb | 50 | DigitalOut vPace(p24); |
Jing_Qiu | 3:34e9766539fe | 51 | |
Jing_Qiu | 3:34e9766539fe | 52 | bool aSensed = 0; // 0 means that we are expecting Apace or Asense next |
Jing_Qiu | 5:376358077dc8 | 53 | DigitalOut led1(LED1); //apace |
Jing_Qiu | 5:376358077dc8 | 54 | DigitalOut led2(LED2); //vpace |
Jing_Qiu | 5:376358077dc8 | 55 | DigitalOut led3(LED3); //asense |
Jing_Qiu | 5:376358077dc8 | 56 | DigitalOut led4(LED4); //vsense |
Jing_Qiu | 3:34e9766539fe | 57 | |
Jing_Qiu | 3:34e9766539fe | 58 | void initTimer(); |
Jing_Qiu | 3:34e9766539fe | 59 | void startTimer(); |
Jing_Qiu | 3:34e9766539fe | 60 | |
Jing_Qiu | 3:34e9766539fe | 61 | void asense(); |
Jing_Qiu | 3:34e9766539fe | 62 | void vsense(); |
Jing_Qiu | 3:34e9766539fe | 63 | |
Jing_Qiu | 3:34e9766539fe | 64 | void apace(); |
Jing_Qiu | 3:34e9766539fe | 65 | void vpace(); |
Jing_Qiu | 3:34e9766539fe | 66 | |
Jing_Qiu | 3:34e9766539fe | 67 | |
Jing_Qiu | 3:34e9766539fe | 68 | void apace() |
Jing_Qiu | 3:34e9766539fe | 69 | { |
Jing_Qiu | 5:376358077dc8 | 70 | led1 = 1; |
Jing_Qiu | 18:e0bc54c0dbeb | 71 | aPace = 1; |
Jing_Qiu | 18:e0bc54c0dbeb | 72 | wait_ms(PULSE_WIDTH_A); |
Jing_Qiu | 18:e0bc54c0dbeb | 73 | aPace = 0; |
mfrede | 8:ce2565cfe709 | 74 | led1 = 0; |
mfrede | 13:0a430559b488 | 75 | beat++; |
Jing_Qiu | 5:376358077dc8 | 76 | |
Jing_Qiu | 3:34e9766539fe | 77 | } |
Jing_Qiu | 3:34e9766539fe | 78 | |
Jing_Qiu | 3:34e9766539fe | 79 | void vpace() |
Jing_Qiu | 3:34e9766539fe | 80 | { |
Jing_Qiu | 5:376358077dc8 | 81 | led2= 1; |
Jing_Qiu | 18:e0bc54c0dbeb | 82 | vPace = 1; |
Jing_Qiu | 18:e0bc54c0dbeb | 83 | wait_ms(PULSE_WIDTH_V); |
Jing_Qiu | 18:e0bc54c0dbeb | 84 | vPace = 0; |
Jing_Qiu | 5:376358077dc8 | 85 | led2 = 0; |
Jing_Qiu | 3:34e9766539fe | 86 | } |
Jing_Qiu | 3:34e9766539fe | 87 | |
Jing_Qiu | 3:34e9766539fe | 88 | void initTimer() |
Jing_Qiu | 3:34e9766539fe | 89 | { |
Jing_Qiu | 3:34e9766539fe | 90 | // set up OS timer (timer0) |
Jing_Qiu | 3:34e9766539fe | 91 | LPC_SC->PCONP |= BM(1); //power up timer0 |
Jing_Qiu | 3:34e9766539fe | 92 | LPC_SC->PCLKSEL0 |= BM(2); // clock = CCLK (96 MHz) |
Jing_Qiu | 3:34e9766539fe | 93 | LPC_TIM0->PR = 48000; // set prescale to 48000 (2048 Hz timer) |
Jing_Qiu | 3:34e9766539fe | 94 | LPC_TIM0->MR0 = 1; // match0 compare value (32-bit) |
Jing_Qiu | 3:34e9766539fe | 95 | LPC_TIM0->MCR |= BM(0)|BM(1); // interrupt and reset on match0 compare |
Jing_Qiu | 3:34e9766539fe | 96 | NVIC_EnableIRQ(TIMER0_IRQn); // enable timer interrupt |
Jing_Qiu | 3:34e9766539fe | 97 | } |
Jing_Qiu | 3:34e9766539fe | 98 | |
Jing_Qiu | 3:34e9766539fe | 99 | void startTimer() |
Jing_Qiu | 3:34e9766539fe | 100 | { |
Jing_Qiu | 3:34e9766539fe | 101 | LPC_TIM0->TCR |= BM(1); // reset timer1 |
Jing_Qiu | 3:34e9766539fe | 102 | LPC_TIM0->TCR &= ~BM(1); // release reset |
Jing_Qiu | 3:34e9766539fe | 103 | LPC_TIM0->TCR |= BM(0); // start timer |
Jing_Qiu | 3:34e9766539fe | 104 | } |
Jing_Qiu | 3:34e9766539fe | 105 | |
Jing_Qiu | 3:34e9766539fe | 106 | void resetTimer() |
Jing_Qiu | 3:34e9766539fe | 107 | { |
Jing_Qiu | 3:34e9766539fe | 108 | LPC_TIM0->TCR |= BM(1); // reset timer0 |
Jing_Qiu | 3:34e9766539fe | 109 | LPC_TIM0->TCR &= ~BM(1); // release reset |
Jing_Qiu | 3:34e9766539fe | 110 | } |
Jing_Qiu | 3:34e9766539fe | 111 | |
Jing_Qiu | 3:34e9766539fe | 112 | |
Jing_Qiu | 3:34e9766539fe | 113 | |
mfrede | 1:e37d0cad77e2 | 114 | void display_thread_handler(void const *args) |
mfrede | 1:e37d0cad77e2 | 115 | { |
mfrede | 1:e37d0cad77e2 | 116 | while(1) |
mfrede | 1:e37d0cad77e2 | 117 | { |
Jing_Qiu | 5:376358077dc8 | 118 | wait_ms(observation_interval); |
amlittle042 | 15:4cd550c14f97 | 119 | pc.printf("BPM: %d\r\n",beat*60000/observation_interval); |
amlittle042 | 15:4cd550c14f97 | 120 | lcd.cls(); |
amlittle042 | 15:4cd550c14f97 | 121 | lcd.printf("BPM: %d\r\n", beat*60000/observation_interval); |
Jing_Qiu | 5:376358077dc8 | 122 | beat=0; |
mfrede | 1:e37d0cad77e2 | 123 | } |
mfrede | 1:e37d0cad77e2 | 124 | } |
mfrede | 1:e37d0cad77e2 | 125 | |
mfrede | 1:e37d0cad77e2 | 126 | |
mfrede | 1:e37d0cad77e2 | 127 | void asense() { |
Jing_Qiu | 3:34e9766539fe | 128 | if (v_clock >= VRP_l) { //Ignore vSense outside this time interval |
Jing_Qiu | 3:34e9766539fe | 129 | v_clock = 0; |
Jing_Qiu | 3:34e9766539fe | 130 | aSensed = 0; |
Jing_Qiu | 3:34e9766539fe | 131 | } |
Jing_Qiu | 5:376358077dc8 | 132 | led3 = 1; |
Jing_Qiu | 18:e0bc54c0dbeb | 133 | wait_ms(PULSE_WIDTH_A); |
Jing_Qiu | 18:e0bc54c0dbeb | 134 | led3 = 0; |
Jing_Qiu | 5:376358077dc8 | 135 | |
mfrede | 1:e37d0cad77e2 | 136 | } |
mfrede | 1:e37d0cad77e2 | 137 | |
mfrede | 1:e37d0cad77e2 | 138 | void vsense() { |
mfrede | 16:a1c97cd207eb | 139 | if ((a_clock >= PVARP_l) && aSensed == 0){ |
Jing_Qiu | 3:34e9766539fe | 140 | a_clock = 0; |
Jing_Qiu | 3:34e9766539fe | 141 | aSensed = 1; |
Jing_Qiu | 5:376358077dc8 | 142 | beat++; |
Jing_Qiu | 3:34e9766539fe | 143 | } |
Jing_Qiu | 5:376358077dc8 | 144 | led4 = 1; |
Jing_Qiu | 18:e0bc54c0dbeb | 145 | wait_ms(PULSE_WIDTH_V); |
Jing_Qiu | 18:e0bc54c0dbeb | 146 | led4 = 0; |
mfrede | 1:e37d0cad77e2 | 147 | } |
mfrede | 1:e37d0cad77e2 | 148 | |
mfrede | 1:e37d0cad77e2 | 149 | void button_handler(void const *args) |
mfrede | 1:e37d0cad77e2 | 150 | { |
mfrede | 8:ce2565cfe709 | 151 | int observation_temp=0; |
mfrede | 1:e37d0cad77e2 | 152 | while(1) |
mfrede | 1:e37d0cad77e2 | 153 | { |
mfrede | 1:e37d0cad77e2 | 154 | char buffer; |
mfrede | 1:e37d0cad77e2 | 155 | if(pc.readable()) { |
mfrede | 11:dd278ffcb31f | 156 | buffer = toupper(pc.getc()); |
mfrede | 1:e37d0cad77e2 | 157 | if (buffer == 'N') |
mfrede | 10:19a2ce5660ea | 158 | { |
mfrede | 1:e37d0cad77e2 | 159 | mode = buffer; |
mfrede | 10:19a2ce5660ea | 160 | LRI_h = 1500; |
mfrede | 10:19a2ce5660ea | 161 | LRI_l = 600; |
mfrede | 10:19a2ce5660ea | 162 | } |
mfrede | 1:e37d0cad77e2 | 163 | else if (buffer == 'S') |
mfrede | 10:19a2ce5660ea | 164 | { |
mfrede | 1:e37d0cad77e2 | 165 | mode = buffer; |
mfrede | 10:19a2ce5660ea | 166 | LRI_h = 2000; |
mfrede | 10:19a2ce5660ea | 167 | LRI_l = 1000; |
mfrede | 10:19a2ce5660ea | 168 | } |
mfrede | 1:e37d0cad77e2 | 169 | else if (buffer == 'E') |
mfrede | 10:19a2ce5660ea | 170 | { |
mfrede | 1:e37d0cad77e2 | 171 | mode = buffer; |
mfrede | 10:19a2ce5660ea | 172 | LRI_h = 600; |
mfrede | 10:19a2ce5660ea | 173 | LRI_l = 342; |
mfrede | 10:19a2ce5660ea | 174 | } |
mfrede | 1:e37d0cad77e2 | 175 | else if (buffer == 'M') |
mfrede | 10:19a2ce5660ea | 176 | { |
mfrede | 1:e37d0cad77e2 | 177 | mode = buffer; |
mfrede | 10:19a2ce5660ea | 178 | LRI_h = 2000; |
mfrede | 10:19a2ce5660ea | 179 | LRI_l = 342; |
mfrede | 10:19a2ce5660ea | 180 | } |
mfrede | 1:e37d0cad77e2 | 181 | else if (buffer == 'A' && mode == 'M') |
mfrede | 1:e37d0cad77e2 | 182 | apace(); |
mfrede | 1:e37d0cad77e2 | 183 | else if (buffer == 'V' && mode == 'M') |
mfrede | 1:e37d0cad77e2 | 184 | vpace(); |
mfrede | 8:ce2565cfe709 | 185 | else if (buffer == 'O') { |
mfrede | 8:ce2565cfe709 | 186 | setObservation = true; |
mfrede | 8:ce2565cfe709 | 187 | observation_temp = 0; |
mfrede | 8:ce2565cfe709 | 188 | } |
mfrede | 14:94f1b9e3eb43 | 189 | else if (buffer == 13 && setObservation) //newline |
mfrede | 6:6bc5e65ada4e | 190 | { |
mfrede | 8:ce2565cfe709 | 191 | observation_interval = observation_temp*1000; |
mfrede | 8:ce2565cfe709 | 192 | setObservation = false; |
mfrede | 14:94f1b9e3eb43 | 193 | // printf("observation interval now: %d\r\n",observation_interval); |
mfrede | 6:6bc5e65ada4e | 194 | } |
mfrede | 8:ce2565cfe709 | 195 | else if (setObservation) |
mfrede | 6:6bc5e65ada4e | 196 | { |
mfrede | 8:ce2565cfe709 | 197 | observation_temp *= 10; |
mfrede | 14:94f1b9e3eb43 | 198 | observation_temp += buffer-48; |
mfrede | 1:e37d0cad77e2 | 199 | |
mfrede | 6:6bc5e65ada4e | 200 | } |
mfrede | 1:e37d0cad77e2 | 201 | } |
mfrede | 1:e37d0cad77e2 | 202 | } |
mfrede | 1:e37d0cad77e2 | 203 | } |
mfrede | 1:e37d0cad77e2 | 204 | |
Jing_Qiu | 3:34e9766539fe | 205 | void pacemaker_thread_handler(void const *args) |
Jing_Qiu | 3:34e9766539fe | 206 | { |
Jing_Qiu | 3:34e9766539fe | 207 | |
Jing_Qiu | 3:34e9766539fe | 208 | /********************************************************** |
Jing_Qiu | 3:34e9766539fe | 209 | ************Initialize timer to interrupt every 1 ms********* |
Jing_Qiu | 3:34e9766539fe | 210 | ***********************************************************/ |
Jing_Qiu | 3:34e9766539fe | 211 | |
Jing_Qiu | 3:34e9766539fe | 212 | initTimer(); |
Jing_Qiu | 3:34e9766539fe | 213 | startTimer(); |
Jing_Qiu | 3:34e9766539fe | 214 | |
Jing_Qiu | 3:34e9766539fe | 215 | while(1){} |
Jing_Qiu | 3:34e9766539fe | 216 | |
Jing_Qiu | 3:34e9766539fe | 217 | } |
Jing_Qiu | 3:34e9766539fe | 218 | |
Jing_Qiu | 3:34e9766539fe | 219 | |
Jing_Qiu | 3:34e9766539fe | 220 | /********************************************************** |
Jing_Qiu | 3:34e9766539fe | 221 | ************ timer interrupt every 1 ms********* |
Jing_Qiu | 3:34e9766539fe | 222 | ***********************************************************/ |
Jing_Qiu | 3:34e9766539fe | 223 | |
Jing_Qiu | 3:34e9766539fe | 224 | extern "C" void TIMER0_IRQHandler (void) { |
Jing_Qiu | 3:34e9766539fe | 225 | if((LPC_TIM0->IR & 0x01) == 0x01) // if MR0 interrupt |
Jing_Qiu | 3:34e9766539fe | 226 | { |
Jing_Qiu | 3:34e9766539fe | 227 | LPC_TIM0->IR |= (1 << 0); // Clear MR0 interrupt flag |
Jing_Qiu | 3:34e9766539fe | 228 | if (v_clock >= (LRI_h-AVI_l) && aSensed == 0) { |
Jing_Qiu | 3:34e9766539fe | 229 | a_clock = 0; |
Jing_Qiu | 3:34e9766539fe | 230 | aSensed = 1; |
Jing_Qiu | 3:34e9766539fe | 231 | //printf("Apace %d\r\n",v_clk); |
Jing_Qiu | 3:34e9766539fe | 232 | apace(); |
Jing_Qiu | 3:34e9766539fe | 233 | /* |
Jing_Qiu | 3:34e9766539fe | 234 | setGPIO(a_pace); |
Jing_Qiu | 3:34e9766539fe | 235 | wait_us(PULSE_WIDTH_A); |
Jing_Qiu | 3:34e9766539fe | 236 | clearGPIO(a_pace); |
Jing_Qiu | 3:34e9766539fe | 237 | */ |
Jing_Qiu | 3:34e9766539fe | 238 | } |
Jing_Qiu | 3:34e9766539fe | 239 | if ((a_clock >= AVI_h) && aSensed == 1) { |
Jing_Qiu | 3:34e9766539fe | 240 | v_clock = 0; |
Jing_Qiu | 3:34e9766539fe | 241 | aSensed = 0; |
Jing_Qiu | 5:376358077dc8 | 242 | //led3 = 0; |
Jing_Qiu | 3:34e9766539fe | 243 | //printf("Vpace %d\r\n",a_clk); |
Jing_Qiu | 3:34e9766539fe | 244 | /* |
Jing_Qiu | 3:34e9766539fe | 245 | setGPIO(v_pace); |
Jing_Qiu | 3:34e9766539fe | 246 | wait_us(PULSE_WIDTH_V); |
Jing_Qiu | 3:34e9766539fe | 247 | clearGPIO(v_pace); |
Jing_Qiu | 3:34e9766539fe | 248 | */ |
Jing_Qiu | 3:34e9766539fe | 249 | vpace(); |
Jing_Qiu | 3:34e9766539fe | 250 | } |
Jing_Qiu | 3:34e9766539fe | 251 | v_clock++; |
Jing_Qiu | 3:34e9766539fe | 252 | a_clock++; |
Jing_Qiu | 5:376358077dc8 | 253 | |
Jing_Qiu | 5:376358077dc8 | 254 | if(v_clock>500) led3 = 0; |
Jing_Qiu | 5:376358077dc8 | 255 | if(a_clock>500) led4 = 0; |
Jing_Qiu | 3:34e9766539fe | 256 | } |
Jing_Qiu | 3:34e9766539fe | 257 | } |
mfrede | 1:e37d0cad77e2 | 258 | |
mfrede | 1:e37d0cad77e2 | 259 | |
Jing_Qiu | 3:34e9766539fe | 260 | int main (void) { |
Jing_Qiu | 3:34e9766539fe | 261 | //TODO set parameters |
Jing_Qiu | 18:e0bc54c0dbeb | 262 | atrial_int.rise(&asense); |
Jing_Qiu | 18:e0bc54c0dbeb | 263 | vent_int.rise(&vsense); |
Jing_Qiu | 3:34e9766539fe | 264 | |
Jing_Qiu | 3:34e9766539fe | 265 | Thread display(display_thread_handler); |
Jing_Qiu | 3:34e9766539fe | 266 | Thread keyboard(button_handler); |
Jing_Qiu | 3:34e9766539fe | 267 | Thread pacemaker(pacemaker_thread_handler); |
Jing_Qiu | 3:34e9766539fe | 268 | |
Jing_Qiu | 3:34e9766539fe | 269 | while(1){} |
Jing_Qiu | 3:34e9766539fe | 270 | |
Jing_Qiu | 3:34e9766539fe | 271 | |
mfrede | 1:e37d0cad77e2 | 272 | } |