latest pacemaker

Dependencies:   TextLCD mbed-rtos mbed

Committer:
terryfan
Date:
Sun Dec 11 21:11:54 2016 +0000
Revision:
4:a9c37c60425c
Parent:
3:77efff091ef1
final pacemaker 12/11

Who changed what in which revision?

UserRevisionLine numberNew contents of line
terryfan 0:dac187b013e0 1 #include "mbed.h"
terryfan 0:dac187b013e0 2 #include "rtos.h"
terryfan 0:dac187b013e0 3 #include "TextLCD.h"
terryfan 0:dac187b013e0 4 #include <stdio.h>
terryfan 3:77efff091ef1 5
terryfan 0:dac187b013e0 6 InterruptIn vsignal(p7);
terryfan 0:dac187b013e0 7 InterruptIn asignal(p8);
terryfan 0:dac187b013e0 8 DigitalOut Vpace(p5);
terryfan 0:dac187b013e0 9 DigitalOut Apace(p6);
terryfan 3:77efff091ef1 10
terryfan 0:dac187b013e0 11 DigitalOut asense_led(LED1);
terryfan 0:dac187b013e0 12 DigitalOut vsense_led(LED2);
terryfan 0:dac187b013e0 13 DigitalOut apace_led(LED3);
terryfan 0:dac187b013e0 14 DigitalOut vpace_led(LED4);
terryfan 3:77efff091ef1 15
terryfan 0:dac187b013e0 16 Thread *pacemodeThread;
terryfan 3:77efff091ef1 17
terryfan 0:dac187b013e0 18 osThreadId signalTid;
terryfan 0:dac187b013e0 19 osThreadId senseTid;
terryfan 0:dac187b013e0 20 osThreadId displayTid;
terryfan 0:dac187b013e0 21 osThreadId pacemodeTid;
terryfan 1:e6f6471e2c00 22 osThreadId alarmTid;
terryfan 4:a9c37c60425c 23 osThreadId ledTid;
terryfan 0:dac187b013e0 24
terryfan 0:dac187b013e0 25 TextLCD lcd(p15, p16, p17, p18, p19, p20, TextLCD::LCD16x2);
terryfan 0:dac187b013e0 26 RawSerial pc(USBTX, USBRX);
terryfan 3:77efff091ef1 27
terryfan 0:dac187b013e0 28 Timer vClock;
terryfan 0:dac187b013e0 29 Timer aClock; //PaceSignal model
terryfan 3:77efff091ef1 30 Timer arpClock;
terryfan 3:77efff091ef1 31
terryfan 0:dac187b013e0 32 double LRI = 1000;
terryfan 0:dac187b013e0 33 double URI = 700;
terryfan 0:dac187b013e0 34 double VRP = 200; // V noise interval
terryfan 0:dac187b013e0 35 double ARP = 50; // A noise interval
terryfan 4:a9c37c60425c 36 double AVI = 150; // A-V max interval
terryfan 0:dac187b013e0 37 double PVARP = 300; // V-A max interval
terryfan 0:dac187b013e0 38 double ratio;
terryfan 0:dac187b013e0 39 int wait_period = 10; // 3a requirement
terryfan 3:77efff091ef1 40
terryfan 4:a9c37c60425c 41 double observation_interval = 10000; // In miliseconds
terryfan 0:dac187b013e0 42 int upperBound; //for mode changes
terryfan 0:dac187b013e0 43 int lowerBound; //for mode changes
terryfan 4:a9c37c60425c 44 double heart_beats = 0; // Heart-Beats (sensed or paced) since the last observation interval
terryfan 0:dac187b013e0 45 char mode = 'n';
terryfan 0:dac187b013e0 46 char key = 'n';
terryfan 0:dac187b013e0 47 char newObsInt[8];
terryfan 0:dac187b013e0 48 int manual_mode = 0;
terryfan 1:e6f6471e2c00 49 Mutex hr_mutex; //hr_mutex.lock()/unlock()
terryfan 3:77efff091ef1 50
terryfan 0:dac187b013e0 51 Queue<char,256> mode_q;
terryfan 0:dac187b013e0 52 Queue<char,256> signal_q;
terryfan 1:e6f6471e2c00 53 Queue<char,256> obsint_q;
terryfan 3:77efff091ef1 54
terryfan 0:dac187b013e0 55 volatile char c;
terryfan 0:dac187b013e0 56 volatile int mm = 0;
terryfan 3:77efff091ef1 57 volatile int om = 0;
terryfan 0:dac187b013e0 58 int mm_flag = 0;
terryfan 3:77efff091ef1 59
terryfan 0:dac187b013e0 60 void initialize_intervals()
terryfan 0:dac187b013e0 61 {
terryfan 0:dac187b013e0 62 LRI = 1000;
terryfan 0:dac187b013e0 63 URI = 700;
terryfan 0:dac187b013e0 64 }
terryfan 3:77efff091ef1 65
terryfan 0:dac187b013e0 66 void Rx_interrupt()
terryfan 0:dac187b013e0 67 {
terryfan 0:dac187b013e0 68 while(pc.readable()) {
terryfan 0:dac187b013e0 69 c = pc.getc();
terryfan 1:e6f6471e2c00 70 if(c == 'm' && om != 1) {
terryfan 0:dac187b013e0 71 mode_q.put((char*)c);
terryfan 0:dac187b013e0 72 mm = 1;
terryfan 1:e6f6471e2c00 73 } else if(c == 'n' || c == 'e' || c == 's' && om != 1) {
terryfan 0:dac187b013e0 74 mode_q.put((char*)c);
terryfan 0:dac187b013e0 75 mm = 0;
terryfan 0:dac187b013e0 76 } else if((c == 'a' || c == 'v') && mm) {
terryfan 0:dac187b013e0 77 signal_q.put((char*)c);
terryfan 1:e6f6471e2c00 78 } else if(c == 'o' && om != 1) {
terryfan 1:e6f6471e2c00 79 mode_q.put((char*)c);
terryfan 1:e6f6471e2c00 80 om = 1;
terryfan 1:e6f6471e2c00 81 } else if (c == '\r' && om) {
terryfan 1:e6f6471e2c00 82 obsint_q.put((char*)c);
terryfan 1:e6f6471e2c00 83 om = 0;
terryfan 1:e6f6471e2c00 84 } else if ((int)c > 47 && (int)c < 58 && om) {
terryfan 1:e6f6471e2c00 85 obsint_q.put((char*)c);
terryfan 0:dac187b013e0 86 }
terryfan 0:dac187b013e0 87 }
terryfan 0:dac187b013e0 88 }
terryfan 0:dac187b013e0 89
terryfan 3:77efff091ef1 90 // Function to toggle the LEDs 1,2,3,4
terryfan 4:a9c37c60425c 91 void ledThread(void const *args)
terryfan 4:a9c37c60425c 92
terryfan 3:77efff091ef1 93 {
terryfan 4:a9c37c60425c 94 while (1) {
terryfan 4:a9c37c60425c 95 osEvent ext_signal = osSignalWait(0, osWaitForever);
terryfan 4:a9c37c60425c 96 int evt = ext_signal.value.signals;
terryfan 4:a9c37c60425c 97
terryfan 4:a9c37c60425c 98 if (evt == 0xA) {
terryfan 3:77efff091ef1 99 asense_led = 1;
terryfan 3:77efff091ef1 100 Thread::wait(wait_period);
terryfan 3:77efff091ef1 101 asense_led = 0;
terryfan 4:a9c37c60425c 102 } else if (evt == 0xB) {
terryfan 3:77efff091ef1 103 vsense_led = 1;
terryfan 3:77efff091ef1 104 Thread::wait(wait_period);
terryfan 3:77efff091ef1 105 vsense_led = 0;
terryfan 4:a9c37c60425c 106 } else if (evt == 0xC) {
terryfan 3:77efff091ef1 107 apace_led = 1;
terryfan 3:77efff091ef1 108 Thread::wait(wait_period);
terryfan 3:77efff091ef1 109 apace_led = 0;
terryfan 4:a9c37c60425c 110 } else if (evt == 0xD) {
terryfan 3:77efff091ef1 111 vpace_led = 1;
terryfan 3:77efff091ef1 112 Thread::wait(wait_period);
terryfan 3:77efff091ef1 113 vpace_led = 0;
terryfan 4:a9c37c60425c 114 }
terryfan 3:77efff091ef1 115 }
terryfan 3:77efff091ef1 116 }
terryfan 3:77efff091ef1 117
terryfan 3:77efff091ef1 118 void alarmThread(void const *args)
terryfan 0:dac187b013e0 119 {
terryfan 2:682a3ac9d7a3 120 while (1) {
terryfan 2:682a3ac9d7a3 121 osEvent ext_signal = osSignalWait(0, osWaitForever);
terryfan 2:682a3ac9d7a3 122 int evt = ext_signal.value.signals;
terryfan 3:77efff091ef1 123
terryfan 3:77efff091ef1 124 if (evt == 0xb) {
terryfan 3:77efff091ef1 125 lcd.printf("%s", "\nALARM HIGH");
terryfan 3:77efff091ef1 126 } else if (evt == 0xc) {
terryfan 1:e6f6471e2c00 127 lcd.printf("%s", "\nALARM LOW");
terryfan 1:e6f6471e2c00 128 }
terryfan 1:e6f6471e2c00 129 }
terryfan 1:e6f6471e2c00 130 }
terryfan 3:77efff091ef1 131
terryfan 0:dac187b013e0 132 void displayThread(void const *args)
terryfan 0:dac187b013e0 133 {
terryfan 0:dac187b013e0 134 while (1) {
terryfan 0:dac187b013e0 135 Thread::wait(observation_interval);
terryfan 0:dac187b013e0 136 lcd.cls();
terryfan 3:77efff091ef1 137
terryfan 1:e6f6471e2c00 138 hr_mutex.lock();
terryfan 4:a9c37c60425c 139 double hr = (heart_beats*60) / (observation_interval / 1000);
terryfan 1:e6f6471e2c00 140 heart_beats = 0;
terryfan 1:e6f6471e2c00 141 hr_mutex.unlock();
terryfan 3:77efff091ef1 142
terryfan 4:a9c37c60425c 143 lcd.printf("%s%d%s","HR: ", (int)hr, " bpm");
terryfan 3:77efff091ef1 144
terryfan 3:77efff091ef1 145 if (hr > upperBound) {
terryfan 1:e6f6471e2c00 146 osSignalSet(alarmTid, 0xb);
terryfan 3:77efff091ef1 147 } else if (hr < lowerBound) {
terryfan 1:e6f6471e2c00 148 osSignalSet(alarmTid, 0xc);
terryfan 1:e6f6471e2c00 149 }
terryfan 0:dac187b013e0 150 }
terryfan 0:dac187b013e0 151 }
terryfan 3:77efff091ef1 152
terryfan 3:77efff091ef1 153
terryfan 3:77efff091ef1 154
terryfan 0:dac187b013e0 155 // Incoming signal from the heart
terryfan 0:dac187b013e0 156 void asignal_irq()
terryfan 0:dac187b013e0 157 {
terryfan 0:dac187b013e0 158 osSignalSet(signalTid, 0x1);
terryfan 0:dac187b013e0 159 }
terryfan 3:77efff091ef1 160
terryfan 0:dac187b013e0 161 // Incoming signal from the heart
terryfan 0:dac187b013e0 162 void vsignal_irq()
terryfan 0:dac187b013e0 163 {
terryfan 0:dac187b013e0 164 osSignalSet(signalTid, 0x2);
terryfan 0:dac187b013e0 165 }
terryfan 3:77efff091ef1 166
terryfan 3:77efff091ef1 167
terryfan 0:dac187b013e0 168 void PaceSignal(void const *args)
terryfan 0:dac187b013e0 169 {
terryfan 0:dac187b013e0 170 int pFlag1 = 0;
terryfan 0:dac187b013e0 171 int pFlag2 = 0;
terryfan 0:dac187b013e0 172 vClock.start();
terryfan 0:dac187b013e0 173 aClock.start();
terryfan 3:77efff091ef1 174 arpClock.start();
terryfan 4:a9c37c60425c 175
terryfan 0:dac187b013e0 176 while(1) {
terryfan 0:dac187b013e0 177 while (!pFlag1) {
terryfan 0:dac187b013e0 178 osEvent ext_signal = osSignalWait(0, osWaitForever);
terryfan 0:dac187b013e0 179 int evt = ext_signal.value.signals;
terryfan 3:77efff091ef1 180
terryfan 3:77efff091ef1 181 if (evt == 0x1 && vClock.read_ms() >= PVARP) { //aSense
terryfan 0:dac187b013e0 182 osSignalSet(senseTid, 0x1);
terryfan 0:dac187b013e0 183 aClock.reset();
terryfan 3:77efff091ef1 184 arpClock.reset();
terryfan 0:dac187b013e0 185 pFlag1 = 1;
terryfan 4:a9c37c60425c 186 } else if(evt == 0x2 && vClock.read_ms() >= VRP) { //vSense
terryfan 4:a9c37c60425c 187 hr_mutex.lock();
terryfan 0:dac187b013e0 188 osSignalSet(senseTid, 0x2);
terryfan 4:a9c37c60425c 189 heart_beats++;
terryfan 0:dac187b013e0 190 vClock.reset();
terryfan 4:a9c37c60425c 191 aClock.reset();
terryfan 4:a9c37c60425c 192 arpClock.reset();
terryfan 4:a9c37c60425c 193 hr_mutex.unlock();
terryfan 4:a9c37c60425c 194 pFlag1 = 1;
terryfan 4:a9c37c60425c 195
terryfan 0:dac187b013e0 196 } else if (evt == 0x3) { //aPace
terryfan 0:dac187b013e0 197 pFlag1 = 1;
terryfan 0:dac187b013e0 198 }
terryfan 0:dac187b013e0 199 }
terryfan 0:dac187b013e0 200 pFlag1 = 0;
terryfan 0:dac187b013e0 201 while(!pFlag2) {
terryfan 3:77efff091ef1 202
terryfan 0:dac187b013e0 203 osEvent ext_signal = osSignalWait(0, osWaitForever);
terryfan 0:dac187b013e0 204 int evt = ext_signal.value.signals;
terryfan 3:77efff091ef1 205
terryfan 4:a9c37c60425c 206 if (evt == 0x1 && arpClock.read_ms() >= ARP) { //aSense
terryfan 0:dac187b013e0 207 osSignalSet(senseTid, 0x1);
terryfan 3:77efff091ef1 208 arpClock.reset();
terryfan 4:a9c37c60425c 209
terryfan 3:77efff091ef1 210 } else if(evt == 0x2) { //vSense
terryfan 2:682a3ac9d7a3 211 hr_mutex.lock();
terryfan 3:77efff091ef1 212 osSignalSet(senseTid, 0x2);
terryfan 2:682a3ac9d7a3 213 heart_beats++;
terryfan 3:77efff091ef1 214 vClock.reset();
terryfan 4:a9c37c60425c 215 aClock.reset();
terryfan 4:a9c37c60425c 216 arpClock.reset();
terryfan 2:682a3ac9d7a3 217 hr_mutex.unlock();
terryfan 0:dac187b013e0 218 pFlag2 = 1;
terryfan 0:dac187b013e0 219 } else if (evt == 0x4) { //vPace
terryfan 0:dac187b013e0 220 pFlag2 = 1;
terryfan 0:dac187b013e0 221 }
terryfan 0:dac187b013e0 222 }
terryfan 0:dac187b013e0 223 pFlag2 = 0;
terryfan 0:dac187b013e0 224 }
terryfan 0:dac187b013e0 225 }
terryfan 3:77efff091ef1 226
terryfan 0:dac187b013e0 227 void PaceSense(void const *args)
terryfan 0:dac187b013e0 228 {
terryfan 3:77efff091ef1 229 int interval;
terryfan 0:dac187b013e0 230 int pFlag1 = 0;
terryfan 0:dac187b013e0 231 int pFlag2 = 0;
terryfan 4:a9c37c60425c 232 int time_sub = 0;
terryfan 4:a9c37c60425c 233 int evt = 0;
terryfan 0:dac187b013e0 234 while(1) {
terryfan 0:dac187b013e0 235 while (!pFlag1) {
terryfan 4:a9c37c60425c 236
terryfan 4:a9c37c60425c 237 time_sub = LRI-AVI - vClock.read_ms();
terryfan 3:77efff091ef1 238
terryfan 4:a9c37c60425c 239 if (time_sub > 0 && !mm_flag) {
terryfan 4:a9c37c60425c 240 osEvent ext_signal = osSignalWait(0, time_sub);
terryfan 4:a9c37c60425c 241 evt = ext_signal.value.signals;
terryfan 4:a9c37c60425c 242 } else if(mm_flag) {
terryfan 4:a9c37c60425c 243 osEvent ext_signal = osSignalWait(0, osWaitForever);
terryfan 4:a9c37c60425c 244 evt = ext_signal.value.signals;
terryfan 4:a9c37c60425c 245 } else {
terryfan 4:a9c37c60425c 246 evt = 0x0;
terryfan 4:a9c37c60425c 247 }
terryfan 4:a9c37c60425c 248
terryfan 4:a9c37c60425c 249 if (evt == 0x0) { //aPace 0x0
terryfan 4:a9c37c60425c 250 aClock.reset();
terryfan 4:a9c37c60425c 251 arpClock.reset();
terryfan 3:77efff091ef1 252 Apace = 1;
terryfan 3:77efff091ef1 253 Thread::wait(1);
terryfan 3:77efff091ef1 254 Apace = 0;
terryfan 3:77efff091ef1 255 osSignalSet(signalTid, 0x3);
terryfan 4:a9c37c60425c 256 osSignalSet(ledTid, 0xC);
terryfan 4:a9c37c60425c 257
terryfan 4:a9c37c60425c 258 interval = AVI;
terryfan 0:dac187b013e0 259 pFlag1 = 1;
terryfan 4:a9c37c60425c 260 } else if (evt == 0x1) { //aSense
terryfan 3:77efff091ef1 261 if(!mm_flag) {
terryfan 4:a9c37c60425c 262 interval = (vClock.read_ms() + AVI >= URI) ? AVI : URI;
terryfan 4:a9c37c60425c 263 time_sub = interval;
terryfan 3:77efff091ef1 264 }
terryfan 4:a9c37c60425c 265 osSignalSet(ledTid, 0xA);
terryfan 3:77efff091ef1 266 pFlag1 = 1;
terryfan 3:77efff091ef1 267 } else if(evt == 0x2) { //vSense
terryfan 4:a9c37c60425c 268 osSignalSet(ledTid, 0xB);
terryfan 4:a9c37c60425c 269 } else if(evt == 0x3) { //apace
terryfan 4:a9c37c60425c 270 pFlag1 = 1;
terryfan 3:77efff091ef1 271 }
terryfan 0:dac187b013e0 272 }
terryfan 0:dac187b013e0 273 pFlag1 = 0;
terryfan 4:a9c37c60425c 274
terryfan 0:dac187b013e0 275 while(!pFlag2) {
terryfan 4:a9c37c60425c 276 time_sub = (interval == AVI) ? AVI - aClock.read_ms() : URI - vClock.read_ms();
terryfan 4:a9c37c60425c 277
terryfan 4:a9c37c60425c 278 if (time_sub > 0 && !mm_flag) {
terryfan 4:a9c37c60425c 279 osEvent ext_signal = osSignalWait(0, time_sub);
terryfan 4:a9c37c60425c 280 evt = ext_signal.value.signals;
terryfan 4:a9c37c60425c 281 } else if(mm_flag) {
terryfan 4:a9c37c60425c 282 osEvent ext_signal = osSignalWait(0, osWaitForever);
terryfan 4:a9c37c60425c 283 evt = ext_signal.value.signals;
terryfan 4:a9c37c60425c 284 } else {
terryfan 4:a9c37c60425c 285 evt = 0x0;
terryfan 4:a9c37c60425c 286 }
terryfan 4:a9c37c60425c 287
terryfan 4:a9c37c60425c 288 if (evt == 0x0) { //vPace 0x0
terryfan 4:a9c37c60425c 289
terryfan 3:77efff091ef1 290 hr_mutex.lock();
terryfan 4:a9c37c60425c 291 heart_beats++;
terryfan 4:a9c37c60425c 292 vClock.reset();
terryfan 4:a9c37c60425c 293 aClock.reset();
terryfan 4:a9c37c60425c 294 arpClock.reset();
terryfan 3:77efff091ef1 295 Vpace = 1;
terryfan 3:77efff091ef1 296 Thread::wait(1);
terryfan 3:77efff091ef1 297 Vpace = 0;
terryfan 3:77efff091ef1 298 osSignalSet(signalTid, 0x4);
terryfan 3:77efff091ef1 299 hr_mutex.unlock();
terryfan 3:77efff091ef1 300
terryfan 4:a9c37c60425c 301 osSignalSet(ledTid, 0xD);
terryfan 0:dac187b013e0 302 pFlag2 = 1;
terryfan 4:a9c37c60425c 303
terryfan 3:77efff091ef1 304 } else if (evt == 0x1) { //aSense
terryfan 4:a9c37c60425c 305 osSignalSet(ledTid, 0xA);
terryfan 3:77efff091ef1 306 } else if(evt == 0x2) { //vSense
terryfan 4:a9c37c60425c 307 osSignalSet(ledTid, 0xB);
terryfan 4:a9c37c60425c 308 pFlag2 = 1;
terryfan 4:a9c37c60425c 309 } else if (evt == 0x4) { //vpace
terryfan 0:dac187b013e0 310 pFlag2 = 1;
terryfan 0:dac187b013e0 311 }
terryfan 0:dac187b013e0 312 }
terryfan 0:dac187b013e0 313 pFlag2 = 0;
terryfan 0:dac187b013e0 314 }
terryfan 0:dac187b013e0 315 }
terryfan 3:77efff091ef1 316
terryfan 0:dac187b013e0 317 void normalmode(void const *args)
terryfan 0:dac187b013e0 318 {
terryfan 0:dac187b013e0 319 initialize_intervals();
terryfan 0:dac187b013e0 320 mode = 'n';
terryfan 0:dac187b013e0 321 upperBound = 100; //beats per msecond
terryfan 0:dac187b013e0 322 lowerBound = 40; //beats per msecond
terryfan 1:e6f6471e2c00 323 hr_mutex.lock();
terryfan 1:e6f6471e2c00 324 heart_beats = 0;
terryfan 1:e6f6471e2c00 325 hr_mutex.unlock();
terryfan 3:77efff091ef1 326
terryfan 3:77efff091ef1 327 vClock.reset();
terryfan 3:77efff091ef1 328 aClock.reset();
terryfan 0:dac187b013e0 329 }
terryfan 3:77efff091ef1 330
terryfan 0:dac187b013e0 331 void exercisemode(void const *args)
terryfan 0:dac187b013e0 332 {
terryfan 0:dac187b013e0 333 initialize_intervals();
terryfan 0:dac187b013e0 334 mode = 'e';
terryfan 0:dac187b013e0 335 upperBound = 175; //beats per msecond
terryfan 0:dac187b013e0 336 lowerBound = 100; //beats per msecond
terryfan 0:dac187b013e0 337 ratio = (175.00/100.00 + 100.00/40.00) / 2.00;
terryfan 0:dac187b013e0 338 LRI /= ratio;
terryfan 0:dac187b013e0 339 URI /= ratio;
terryfan 1:e6f6471e2c00 340 //reset obs interval
terryfan 1:e6f6471e2c00 341 hr_mutex.lock();
terryfan 1:e6f6471e2c00 342 heart_beats = 0;
terryfan 1:e6f6471e2c00 343 hr_mutex.unlock();
terryfan 3:77efff091ef1 344
terryfan 3:77efff091ef1 345 vClock.reset();
terryfan 3:77efff091ef1 346 aClock.reset();
terryfan 0:dac187b013e0 347 }
terryfan 3:77efff091ef1 348
terryfan 0:dac187b013e0 349 void sleepmode(void const *args)
terryfan 0:dac187b013e0 350 {
terryfan 0:dac187b013e0 351 initialize_intervals();
terryfan 0:dac187b013e0 352 mode = 's';
terryfan 0:dac187b013e0 353 upperBound = 60; //beats per msecond
terryfan 0:dac187b013e0 354 lowerBound = 30; //beats per msecond v-v 0.5s
terryfan 0:dac187b013e0 355 ratio = (60.00/100.00 + 30.00/40.00) / 2.00;
terryfan 0:dac187b013e0 356 LRI /= ratio;
terryfan 0:dac187b013e0 357 URI /= ratio;
terryfan 1:e6f6471e2c00 358 hr_mutex.lock();
terryfan 1:e6f6471e2c00 359 heart_beats = 0;
terryfan 1:e6f6471e2c00 360 hr_mutex.unlock();
terryfan 3:77efff091ef1 361
terryfan 3:77efff091ef1 362 vClock.reset();
terryfan 3:77efff091ef1 363 aClock.reset();
terryfan 0:dac187b013e0 364 }
terryfan 3:77efff091ef1 365
terryfan 1:e6f6471e2c00 366 void m_vpace()
terryfan 1:e6f6471e2c00 367 {
terryfan 0:dac187b013e0 368 vClock.reset();
terryfan 4:a9c37c60425c 369 aClock.reset();
terryfan 4:a9c37c60425c 370 arpClock.reset();
terryfan 0:dac187b013e0 371 Vpace = 1;
terryfan 3:77efff091ef1 372 Thread::wait(1);
terryfan 0:dac187b013e0 373 Vpace = 0;
terryfan 0:dac187b013e0 374 osSignalSet(signalTid, 0x4);
terryfan 4:a9c37c60425c 375 osSignalSet(senseTid, 0x4);
terryfan 1:e6f6471e2c00 376 hr_mutex.lock();
terryfan 0:dac187b013e0 377 heart_beats++;
terryfan 1:e6f6471e2c00 378 hr_mutex.unlock();
terryfan 4:a9c37c60425c 379
terryfan 4:a9c37c60425c 380 osSignalSet(ledTid, 0xD);
terryfan 0:dac187b013e0 381 }
terryfan 3:77efff091ef1 382
terryfan 1:e6f6471e2c00 383 void m_apace()
terryfan 1:e6f6471e2c00 384 {
terryfan 0:dac187b013e0 385 aClock.reset();
terryfan 4:a9c37c60425c 386 arpClock.reset();
terryfan 0:dac187b013e0 387 Apace = 1;
terryfan 3:77efff091ef1 388 Thread::wait(1);
terryfan 0:dac187b013e0 389 Apace = 0;
terryfan 4:a9c37c60425c 390 osSignalSet(senseTid, 0x3);
terryfan 0:dac187b013e0 391 osSignalSet(signalTid, 0x3);
terryfan 4:a9c37c60425c 392 osSignalSet(ledTid, 0xC);
terryfan 0:dac187b013e0 393 }
terryfan 3:77efff091ef1 394
terryfan 0:dac187b013e0 395 void manualmode(void const *args)
terryfan 0:dac187b013e0 396 {
terryfan 0:dac187b013e0 397 upperBound = 175; //beats per msecond
terryfan 0:dac187b013e0 398 lowerBound = 30; //beats per msecond
terryfan 0:dac187b013e0 399 mode = 'm';
terryfan 1:e6f6471e2c00 400 LRI = 2125; // max V-V (LRI) based on exercise mode
terryfan 1:e6f6471e2c00 401 URI = 675; // min V-V (URI) based on sleep mode
terryfan 3:77efff091ef1 402
terryfan 0:dac187b013e0 403 while(1) {
terryfan 0:dac187b013e0 404 osEvent evt = signal_q.get();
terryfan 0:dac187b013e0 405 if(evt.status == osEventMessage) {
terryfan 0:dac187b013e0 406 if((char)evt.value.p == 'v') {
terryfan 0:dac187b013e0 407 m_vpace();
terryfan 0:dac187b013e0 408 } else if((char)evt.value.p == 'a') {
terryfan 0:dac187b013e0 409 m_apace();
terryfan 0:dac187b013e0 410 }
terryfan 0:dac187b013e0 411 }
terryfan 0:dac187b013e0 412 }
terryfan 0:dac187b013e0 413 }
terryfan 3:77efff091ef1 414
terryfan 1:e6f6471e2c00 415 void obsinterval()
terryfan 1:e6f6471e2c00 416 {
terryfan 1:e6f6471e2c00 417 char newObsInt[8];
terryfan 1:e6f6471e2c00 418 int isChangingObsInt = 1;
terryfan 1:e6f6471e2c00 419 int i = 0;
terryfan 1:e6f6471e2c00 420 while(isChangingObsInt) {
terryfan 1:e6f6471e2c00 421 osEvent evt = obsint_q.get();
terryfan 1:e6f6471e2c00 422 if(evt.status == osEventMessage) {
terryfan 1:e6f6471e2c00 423 key = (char)evt.value.p;
terryfan 1:e6f6471e2c00 424 if(key != '\r' && i < 7 ) {
terryfan 1:e6f6471e2c00 425 newObsInt[i] = key;
terryfan 1:e6f6471e2c00 426 i++;
terryfan 1:e6f6471e2c00 427 } else if((key == '\r') && (i > 0)) {
terryfan 1:e6f6471e2c00 428 heart_beats = 0;
terryfan 1:e6f6471e2c00 429 int obsint;
terryfan 1:e6f6471e2c00 430 newObsInt[i] = '\0';
terryfan 1:e6f6471e2c00 431 sscanf(newObsInt, "%d", &obsint);
terryfan 4:a9c37c60425c 432
terryfan 4:a9c37c60425c 433 if(obsint < 300) {
terryfan 4:a9c37c60425c 434 observation_interval = 300.0;
terryfan 4:a9c37c60425c 435 } else if (obsint > 10000) {
terryfan 4:a9c37c60425c 436 observation_interval = 10000.0;
terryfan 4:a9c37c60425c 437 } else {
terryfan 4:a9c37c60425c 438 observation_interval = (double)obsint;
terryfan 4:a9c37c60425c 439 }
terryfan 1:e6f6471e2c00 440 isChangingObsInt = 0;
terryfan 4:a9c37c60425c 441
terryfan 1:e6f6471e2c00 442 }
terryfan 1:e6f6471e2c00 443 }
terryfan 1:e6f6471e2c00 444 }
terryfan 1:e6f6471e2c00 445 }
terryfan 3:77efff091ef1 446
terryfan 0:dac187b013e0 447 osThreadDef(PaceSignal, osPriorityNormal, DEFAULT_STACK_SIZE);
terryfan 0:dac187b013e0 448 osThreadDef(PaceSense, osPriorityNormal, DEFAULT_STACK_SIZE);
terryfan 1:e6f6471e2c00 449 osThreadDef(alarmThread, osPriorityBelowNormal, DEFAULT_STACK_SIZE); //priority BelowNormal
terryfan 4:a9c37c60425c 450 osThreadDef(ledThread, osPriorityBelowNormal, DEFAULT_STACK_SIZE);
terryfan 3:77efff091ef1 451
terryfan 1:e6f6471e2c00 452 osThreadDef(displayThread, osPriorityLow, DEFAULT_STACK_SIZE); //priority Low
terryfan 0:dac187b013e0 453 osThreadDef(manualmode, osPriorityNormal, DEFAULT_STACK_SIZE);
terryfan 3:77efff091ef1 454
terryfan 0:dac187b013e0 455 int main()
terryfan 0:dac187b013e0 456 {
terryfan 1:e6f6471e2c00 457 alarmTid = osThreadCreate(osThread(alarmThread), NULL);
terryfan 0:dac187b013e0 458 senseTid = osThreadCreate(osThread(PaceSense), NULL);
terryfan 0:dac187b013e0 459 signalTid = osThreadCreate(osThread(PaceSignal), NULL);
terryfan 0:dac187b013e0 460 displayTid = osThreadCreate(osThread(displayThread), NULL);
terryfan 4:a9c37c60425c 461 ledTid = osThreadCreate(osThread(ledThread), NULL);
terryfan 4:a9c37c60425c 462
terryfan 3:77efff091ef1 463 normalmode(NULL);
terryfan 4:a9c37c60425c 464
terryfan 0:dac187b013e0 465 vsignal.rise(&vsignal_irq); //rising edge of timer
terryfan 0:dac187b013e0 466 asignal.rise(&asignal_irq);
terryfan 3:77efff091ef1 467
terryfan 0:dac187b013e0 468 lcd.cls();
terryfan 3:77efff091ef1 469
terryfan 0:dac187b013e0 470 pc.attach(&Rx_interrupt, RawSerial::RxIrq);
terryfan 0:dac187b013e0 471 while(true) {
terryfan 0:dac187b013e0 472 osEvent evt = mode_q.get();
terryfan 0:dac187b013e0 473 if(evt.status == osEventMessage) {
terryfan 0:dac187b013e0 474 switch((char)evt.value.p) {
terryfan 0:dac187b013e0 475 case('n'):
terryfan 0:dac187b013e0 476 mm_flag = 0;
terryfan 4:a9c37c60425c 477 osSignalSet(senseTid, 0x5);
terryfan 0:dac187b013e0 478 osThreadTerminate (pacemodeTid);
terryfan 1:e6f6471e2c00 479 osThreadTerminate (displayTid);
terryfan 3:77efff091ef1 480 normalmode(NULL);
terryfan 1:e6f6471e2c00 481 displayTid = osThreadCreate(osThread(displayThread), NULL);
terryfan 0:dac187b013e0 482 break;
terryfan 0:dac187b013e0 483 case('s'):
terryfan 0:dac187b013e0 484 mm_flag = 0;
terryfan 4:a9c37c60425c 485 osSignalSet(senseTid, 0x5);
terryfan 0:dac187b013e0 486 osThreadTerminate (pacemodeTid);
terryfan 1:e6f6471e2c00 487 osThreadTerminate (displayTid);
terryfan 3:77efff091ef1 488 sleepmode(NULL);
terryfan 1:e6f6471e2c00 489 displayTid = osThreadCreate(osThread(displayThread), NULL);
terryfan 0:dac187b013e0 490 break;
terryfan 0:dac187b013e0 491 case('e'):
terryfan 0:dac187b013e0 492 mm_flag = 0;
terryfan 4:a9c37c60425c 493 osSignalSet(senseTid, 0x5);
terryfan 0:dac187b013e0 494 osThreadTerminate (pacemodeTid);
terryfan 1:e6f6471e2c00 495 osThreadTerminate (displayTid);
terryfan 3:77efff091ef1 496 exercisemode(NULL);
terryfan 1:e6f6471e2c00 497 displayTid = osThreadCreate(osThread(displayThread), NULL);
terryfan 0:dac187b013e0 498 break;
terryfan 0:dac187b013e0 499 case('m'):
terryfan 0:dac187b013e0 500 mm_flag = 1;
terryfan 0:dac187b013e0 501 osThreadTerminate (pacemodeTid);
terryfan 0:dac187b013e0 502 pacemodeTid = osThreadCreate(osThread(manualmode), NULL);
terryfan 0:dac187b013e0 503 manual_mode = 1;
terryfan 0:dac187b013e0 504 break;
terryfan 0:dac187b013e0 505 case('o'):
terryfan 3:77efff091ef1 506 obsinterval();
terryfan 1:e6f6471e2c00 507 osThreadTerminate (displayTid);
terryfan 1:e6f6471e2c00 508 displayTid = osThreadCreate(osThread(displayThread), NULL);
terryfan 0:dac187b013e0 509 break;
terryfan 0:dac187b013e0 510 }
terryfan 0:dac187b013e0 511 }
terryfan 0:dac187b013e0 512 }
terryfan 4:a9c37c60425c 513 }