#include <90s8515.h> #include //for debugging using printf, etc #include #define TESTPHONE 1 #define t1 10 #define MAXPHONENO 4 #define NULLADDRESS 0x0f #define NULLLATCH 0x07 #define DIALTONEPATTERN 0x04 #define ACTIVATEDIALTONE 0x00 #define DEACTIVATEDIALTONE 0x07 #define BUSYTONEPATTERN 0x06 #define ACTIVATEBUSYTONE 0x02 #define DEACTIVATEBUSYTONE 0x07 #define RINGTONEPATTERN 0x05 #define ACTIVATERINGTONE 0x01 #define DEACTIVATERINGTONE 0x07 #define DTMFnomsk 0x0f #define BUSYTONEON 7 // 500/(t1*MAXPHONENO) #define BUSYTONEOFF 7// 500/(t1*MAXPHONENO) #define RINGTONEON 25// 2000/(t1*MAXPHONENO) #define RINGTONEOFF 50 // 2000/(t1*MAXPHONENO) #define IDLE 1 #define CALLEROFFHOOK 2 #define WAITBUTTONRELEASE1 3 #define WAITBUTTONRELEASE2 4 #define BUSYTONEGENON 5 #define BUSYTONEGENOFF 6 #define CHECKRECEIVER 7 #define RINGTONEGENON 8 #define RINGTONEGENOFF 9 #define SENDTALKING 10 #define RINGING 11 #define RECTALKING 12 void task1(void); //start a new conversion void initialize(void); //all the usual mcu stuff void checkhookswreg(void); void checkDTMFreg(void); void enabledialtone(void); void disabledialtone(void); void enablebusytone(void); void disablebusytone(void); void enableringtone(void); void disableringtone(void); void enableringer(void); void disableringer(void); void enableswitching(void); void disableswitching(void); unsigned char reload, time1, phoneindex, temp1, hookswreg, ringerswreg, DTMFvalid, temp2; unsigned char phoneoffhook, recphoneoffhook, phonering; unsigned char stateofphone[MAXPHONENO],tmp1,tmp2,tmp3; unsigned char phonemsk[MAXPHONENO] = {0x01, 0x02, 0x04, 0x08}; unsigned char addrofphlatch[MAXPHONENO] = {0x1f, 0x2f, 0x3f, 0x4f}; unsigned char addrofDTMF[MAXPHONENO] = {0x5f, 0x6f, 0x7f, 0x8f}; unsigned char DTMFreg[MAXPHONENO]; unsigned char DTMFno[MAXPHONENO]; unsigned char switchtable[MAXPHONENO] = {0x0f, 0x17, 0x27, 0x47}; int oninterval[MAXPHONENO]; int offinterval[MAXPHONENO]; //timer 0 overflow ISR interrupt [TIM0_OVF] void timer0_overflow(void) { //reload to force 1 mSec overflow TCNT0=reload; if (time1>0) --time1; } void main(void) { initialize(); //main task scheduler loop -- never exits! while(1) { if (time1==0) { task1(); phoneindex++; if (phoneindex == MAXPHONENO) phoneindex = 0; } } } void task1(void) { time1 = t1; if (tmp1 != stateofphone[0] || tmp2 != stateofphone[1] || tmp3 != stateofphone[2]) { printf("P1=%d P2=%d P3=%d \n\r",stateofphone[0],stateofphone[1],stateofphone[2]); tmp1= stateofphone[0]; tmp2= stateofphone[1]; tmp3= stateofphone[2]; } if (stateofphone[phoneindex] == IDLE) { // // if (phoneindex == TESTPHONE) printf("IDLE\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; phonering = ringerswreg & phonemsk[phoneindex]; if ((phoneoffhook != 0) && (phonering != 0)) stateofphone[phoneindex] = RECTALKING; else if ((phoneoffhook != 0) && (phonering == 0)) { enabledialtone(); stateofphone[phoneindex] = CALLEROFFHOOK; } else if ((phoneoffhook == 0) && (phonering != 0)) stateofphone[phoneindex] = RINGING; } else if (stateofphone[phoneindex] == CALLEROFFHOOK) { // // if (phoneindex == TESTPHONE) printf("CALLEROFFHOOK\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; if (phoneoffhook == 0) { disabledialtone(); stateofphone[phoneindex] = IDLE; } else { checkDTMFreg(); if (DTMFvalid == 1) { DTMFno[phoneindex] = DTMFreg[phoneindex] & DTMFnomsk; // if (phoneindex == TESTPHONE) printf("Number = %d\n\r", DTMFno[phoneindex]); if ((DTMFno[phoneindex] >=1) && (DTMFno[phoneindex] <= MAXPHONENO)) { disabledialtone(); stateofphone[phoneindex] = WAITBUTTONRELEASE1; } else { disabledialtone(); stateofphone[phoneindex] = WAITBUTTONRELEASE2; } } } } else if (stateofphone[phoneindex] == WAITBUTTONRELEASE1) { // if (phoneindex == TESTPHONE) printf("WAITBUTTONRELEASE1\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; if (phoneoffhook == 0) stateofphone[phoneindex] = IDLE; else { checkDTMFreg(); if (DTMFvalid == 0) stateofphone[phoneindex] = CHECKRECEIVER; } } else if (stateofphone[phoneindex] == WAITBUTTONRELEASE2) { // if (phoneindex == TESTPHONE) printf("WAITBUTTONRELEASE2\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; if (phoneoffhook == 0) stateofphone[phoneindex] = IDLE; else { checkDTMFreg(); if (DTMFvalid == 0) { oninterval[phoneindex] = BUSYTONEON; enablebusytone(); stateofphone[phoneindex] = BUSYTONEGENON; } } } else if (stateofphone[phoneindex] == BUSYTONEGENON) { // if (phoneindex == TESTPHONE) printf("BUSYTONEGENON\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; if (phoneoffhook == 0) { disablebusytone(); stateofphone[phoneindex] = IDLE; } else { oninterval[phoneindex]--; if (oninterval[phoneindex] == 0) { offinterval[phoneindex] = BUSYTONEOFF; disablebusytone(); stateofphone[phoneindex] = BUSYTONEGENOFF; } } } else if (stateofphone[phoneindex] == BUSYTONEGENOFF) { // if (phoneindex == TESTPHONE) printf("BUSYTONEGENOFF\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; if (phoneoffhook == 0) stateofphone[phoneindex] = IDLE; else { offinterval[phoneindex]--; if (offinterval[phoneindex] == 0) { oninterval[phoneindex] = BUSYTONEON; enablebusytone(); stateofphone[phoneindex] = BUSYTONEGENON; } } } else if (stateofphone[phoneindex] == CHECKRECEIVER) { // if (phoneindex == TESTPHONE) printf("CHECKRECEIVER\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; if (phoneoffhook == 0) stateofphone[phoneindex] = IDLE; else if (stateofphone[DTMFno[phoneindex] - 1] != IDLE) { oninterval[phoneindex] = BUSYTONEON; enablebusytone(); stateofphone[phoneindex] = BUSYTONEGENON; } else { oninterval[phoneindex] = RINGTONEON; ringerswreg = ringerswreg | phonemsk[DTMFno[phoneindex] - 1]; enableringer(); enableringtone(); stateofphone[phoneindex] = RINGTONEGENON; } } else if (stateofphone[phoneindex] == RINGTONEGENON) { // if (phoneindex == TESTPHONE) printf("RINGTONEGENON\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; recphoneoffhook = hookswreg & phonemsk[DTMFno[phoneindex] - 1]; if (phoneoffhook == 0) { disableringer(); disableringtone(); ringerswreg = ringerswreg & ~phonemsk[DTMFno[phoneindex] - 1]; stateofphone[phoneindex] = IDLE; stateofphone[DTMFno[phoneindex] - 1] = IDLE; } else { if (recphoneoffhook == 0) { oninterval[phoneindex]--; if (oninterval[phoneindex] == 0) { offinterval[phoneindex] = RINGTONEOFF; disableringer(); disableringtone(); stateofphone[phoneindex] = RINGTONEGENOFF; } } else { disableringer(); disableringtone(); enableswitching(); ringerswreg = ringerswreg & ~phonemsk[DTMFno[phoneindex] - 1]; stateofphone[phoneindex] = SENDTALKING; } } } else if (stateofphone[phoneindex] == RINGTONEGENOFF) { // if (phoneindex == TESTPHONE) printf("RINGTONEGENOFF\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; recphoneoffhook = hookswreg & phonemsk[DTMFno[phoneindex] - 1]; if (phoneoffhook == 0) { stateofphone[phoneindex] = IDLE; // if (phoneindex == TESTPHONE) printf("call to %d (ringoff)\n\r",DTMFno[phoneindex] - 1); stateofphone[DTMFno[phoneindex] - 1] = IDLE; ringerswreg = ringerswreg & ~phonemsk[DTMFno[phoneindex] - 1]; } else { if (recphoneoffhook == 0) { offinterval[phoneindex]--; if (offinterval[phoneindex] == 0) { oninterval[phoneindex] = RINGTONEON; enableringer(); enableringtone(); stateofphone[phoneindex] = RINGTONEGENON; } } else { enableswitching(); ringerswreg = ringerswreg & ~phonemsk[DTMFno[phoneindex] - 1]; stateofphone[phoneindex] = SENDTALKING; } } } else if (stateofphone[phoneindex] == SENDTALKING) { // if (phoneindex == TESTPHONE) printf("SENDTALKING\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; if (phoneoffhook == 0) { disableswitching(); stateofphone[phoneindex] = IDLE; stateofphone[DTMFno[phoneindex] - 1] = IDLE; } } else if (stateofphone[phoneindex] == RINGING) { // if (phoneindex == TESTPHONE) printf("RINGING\n\r"); checkhookswreg(); phoneoffhook = hookswreg & phonemsk[phoneindex]; if (phoneoffhook != 0) stateofphone[phoneindex] = RECTALKING; } else if (stateofphone[phoneindex] == RECTALKING) { // if (phoneindex == TESTPHONE) printf("RECTALKING\n\r"); } } void checkhookswreg(void) { DDRA = 0xf0; PORTA = 0x0f; delay_us(10); temp2 = PINA; hookswreg = ~temp2; // if (phoneindex == TESTPHONE) printf("hoowswreg = %d", hookswreg); } void enabledialtone(void) { DDRC = 0xff; PORTC = DIALTONEPATTERN; delay_us(5); PORTA = addrofphlatch[phoneindex]; delay_us(5); PORTC = ACTIVATEDIALTONE; delay_us(5); PORTA = NULLADDRESS; } void disabledialtone(void) { DDRC = 0xff; PORTC = DEACTIVATEDIALTONE; delay_us(5); PORTA = addrofphlatch[phoneindex]; delay_us(5); PORTA = NULLADDRESS; } void enablebusytone(void) { DDRC = 0xff; PORTC = BUSYTONEPATTERN; delay_us(5); PORTA = addrofphlatch[phoneindex]; delay_us(5); PORTC = ACTIVATEBUSYTONE; delay_us(5); PORTA = NULLADDRESS; } void disablebusytone(void) { DDRC = 0xff; PORTC = DEACTIVATEBUSYTONE; delay_us(5); PORTA = addrofphlatch[phoneindex]; delay_us(5); PORTA = NULLADDRESS; } void enableringtone(void) { DDRC = 0xff; PORTC = RINGTONEPATTERN; delay_us(5); PORTA = addrofphlatch[phoneindex]; delay_us(5); PORTC = ACTIVATERINGTONE; delay_us(5); PORTA = NULLADDRESS; } void disableringtone(void) { DDRC = 0xff; PORTC = DEACTIVATERINGTONE; delay_us(5); PORTA = addrofphlatch[phoneindex]; delay_us(5); PORTA = NULLADDRESS; } void enableringer(void) { PORTB = ~ringerswreg; } void disableringer(void) { temp1 = ringerswreg & ~phonemsk[DTMFno[phoneindex] - 1]; PORTB = ~temp1; } void enableswitching(void) { DDRC = 0xff; PORTC = switchtable[phoneindex]; delay_us(5); PORTA = addrofphlatch[phoneindex]; delay_us(5); PORTA = addrofphlatch[DTMFno[phoneindex] - 1]; delay_us(5); PORTA = NULLADDRESS; } void disableswitching(void) { DDRC = 0xff; PORTC = NULLLATCH; delay_us(5); PORTA = addrofphlatch[phoneindex]; delay_us(5); PORTA = addrofphlatch[DTMFno[phoneindex] - 1]; delay_us(5); PORTA = NULLADDRESS; } void checkDTMFreg(void) { DDRC = 0x00; PORTC = 0x00; PORTA = addrofDTMF[phoneindex]; delay_us(10); if (PINC.4 == 1) { DTMFvalid = 1; DTMFreg[phoneindex] = PINC; } else DTMFvalid = 0; delay_us(5); PORTA = NULLADDRESS; } void initialize(void) { //serial port set up UCR = 0x10 + 0x08; UBRR = 25; DDRA = 0xf0; PORTA = 0x0f; //set up timer 0 reload=256-62; //value for 1 Msec TCNT0=reload; //preload timer 1 so that is interrupts after 1 mSec. TCCR0=3; //prescalar to 64 TIMSK=2; //turn on timer 0 overflow ISR //init the task timer time1=t1; hookswreg = 0x00; ringerswreg = 0x00; for (phoneindex = 0; phoneindex < MAXPHONENO; phoneindex++) { stateofphone[phoneindex] = IDLE; DDRC = 0xff; PORTC = NULLLATCH; delay_us(5); PORTA = addrofphlatch[phoneindex]; delay_us(5); PORTA = NULLADDRESS; } //initialize ringer DDRB = 0xff; PORTB = 0xff; phoneindex = 0; DTMFvalid = 0; //crank up the ISRs #asm sei #endasm }