System Integration and Software Codes
Christian Rivera

1. Multiplexer Notes
2. Opto-Isolator Circuit
3. Diagnostic Codes
4. Dialing Codes
5. Sentinel Codes
6. Testing Codes

back to CE150




1. Multiplexer Notes      TOP

S0 - S3 Correspond to the status lines of the parallel port. There is an opto-isolator between the port pin and this output of the multiplexer, though.

C0 - C2 Correspond to the control lines of the parallel port. There is also an opto-isolator here too, as in most of the interfaced pins of the parallel port

Input Devices A, B, C, D is where the individual components of the security system.



2. Opto-Isolator Circuit      TOP

-an array of 18 opto-isolators will be needed for interfacing with the parallel port (8 data lines, 5 status, 4 (1 ground) control lines).

-circuit is logic one by default; changes signal bringing it down to logic 0 (an input of 0.8 V yields an output of 0.2 V.

to go back to CE 150 section


two ewb files being constructed - please come back soon




3. Diagnostic Codes      TOP

/*	This program sends and reads data off the ports of the parallel
	ports. Each process and echoed to screen to let user confirm
	these with his hardware

	17 September 2001
	by Christian Rivera

#include
#include
#include
#include
#include
*/

const int STATUS 	= 0x379;		//parallel port addresses
const int CONTROL	= 0x37a;
const int DATA		= 0x378;
const int DELAY		= 500;

char *tobinary(int number, int length);		//converts dec to binary

int getstatus(void)                         //discards least
{						//3 significant bits (S0, S1, S2)
	int status = inportb(STATUS);		//which are randomly
	return (status & 0xf8);			//generated by computer
}

/*************************************************************************
	TESTS type 1 tests are manual. User must press key to proceed
		  type 0 tests are automatic.
***************************************************************************/

void datalinetest(int lag, int type)
{
	printf("\nTesting DATA lines...\n\n");
	int bits = 1;
	for(int i = 0; i <= 8; i++)
	{
		if(i == 8) bits = 255;
		outportb(DATA, bits);
		printf("Sending %s to %x...\n",
			tobinary(bits, 8), DATA);
		bits = bits << 1;
		delay(lag);
		if (type == 1) getch();
	}

}


void controllinetest(int lag, int type)
{
	int bits = 1;
	printf("\nTesting CONTROL lines...\n\n");
	for(int j = 0; j <=4; j++)
	{
		if(j == 4) bits = 15;
		outport(CONTROL, bits);
		printf("Sending %s to %x...\n",
			tobinary(bits, 4), CONTROL);
		bits = bits << 1;
		delay(lag);
		if (type == 1) getch();
	}

}

void statuslinetest(int lag, int type, int test)	// 0 test: automatic
{
	int bits, ctr = 1;
	char ch;
	printf("\nTesting status lines...\n\n");
	if(test == 0) ctr = 5;
	while(1)
	{
		bits = getstatus();
		printf("Receiving %s from %x...\n",
			tobinary(bits, 8), STATUS);
		delay(lag);
		if(type == 1)
		{
			ch = getch();			//pressing q quits test
			if((ch == 'q') || (ch == 'Q')) break;
		}
		else ctr--;
		if(ctr == 0) break;
	}
}

int porttest(int testtype)		//0 = automatic (500ms delay between tests
{					//1 = manual (user must prompt proceed)\
	outportb(DATA, 0x00);
	outportb(CONTROL, 0x00);
	int tdelay  = DELAY, test = 0;
	if(testtype == 1)
	{
		tdelay = 0;
		test = 1;
	}
//	datalinetest(tdelay, testtype);
//	controllinetest(tdelay, testtype);
	statuslinetest(tdelay, testtype, test);
}

/*
int main(void)
{
//	porttest(0);
//	porttest(1);
	char prompt;
	do
	{
		int	control;
		printf("Control byte: ");
		scanf("%x", &control);
		outport(CONTROL, control);
		printf("Sending %s to %x\n", tobinary(control,4), CONTROL);
		int data = getstatus(STATUS);
		printf("Receiving %s from %x\n", tobinary(data,8), STATUS);
		prompt = getch();
	} while(prompt != 'q');
}
*/
/*******Conversion of numbers to binary***********/

char *tobinary(int quotient, int length)
{
	char *str = new char [length];
	for(int i = length-1; i >= 0; i--)
	{
		int remainder = quotient % 2;
		if(remainder == 1) str[i] = '1';
		else str[i] = '0';
		quotient = quotient / 2;
	}
	str[length] = '\0';
	return str;
}







4. Dialing Codes      TOP

//This code courtesy of Mr. Tristan Calasanz
//modified by Christian Rivera for the Sentinel
//security system



//Modem Commands
unsigned char *NumericOn		= {"atv0\r"};
unsigned char *IgnoreDial		= {"atx0\r"};
unsigned char *reportprog		= {"atx4\r"};
unsigned char *liftphone		= {"ath1\r"};
unsigned char *FinalResp		= {"atw0\r"};
unsigned char *Connect			= {"ath1\r"};
unsigned char *AutoAnswer		= {"ats0=1\r"};
unsigned char *SilentModem		= {"atx0\r"};
unsigned char *AT				= {"at\r"};
unsigned char *LiftPhone		= {"ath1\r"};
unsigned char *HangUp			= {"ath0\r"};
unsigned char *NoEcho			= {"ate0\r"};
int DataSerPort					= 0x2f8;
int CtrlSerPort					= 0x2fc;
int StatSerPort					= 0x2fd;
int NormalWait					= 20;
int AllowedDelay;				/* number of clock ticks */
int RxBufferEmpty				= 0;	/* 1 for empty */
int PortChar					= 0;
int Response1					= 0;
int Response2					= 0;
int CommPort					= 1;
int CommByte					= 0x8a;
int ModemStat					= 0;
int IsRdy						= 0;

int TellModem(char *msg2modem);
int Wait4PortChar(unsigned long AllowedDelay);
int In(void);
int Out(char Byte);
void PreparePort(void);
void Disconnect(void);

unsigned long CLK_Timer()
{
	unsigned long PortTime 	= 0;
	PortTime = peek(0x40,0x6c);
	return PortTime;
}

int Wait4PortChar(unsigned long AllowedDelay)
{
	int RxRdy			= 0;

	unsigned long TimeNow 		= 0;
	unsigned long TimeLater 	= 0;
	unsigned long TimeLapsed	= 0;
	TimeNow = CLK_Timer();
	while(RxRdy != 1)
	{
		RxRdy = inportb(StatSerPort);
		RxRdy = RxRdy & 0x1;
		TimeLater = CLK_Timer();
		TimeLapsed = TimeLater - TimeNow;
		if(TimeLapsed > AllowedDelay)
		{
			TimeLapsed = TimeLapsed / 18.2;
			RxBufferEmpty = 1;
			printf("\nPlease check your modem and/or connections . . .\n");
			return -1;	//i don't want to turn sentinel off
		}
		if(RxRdy == 1)
			PortChar = inportb(DataSerPort);
	}
}

int TellModem(char *msg2modem)
{
	int ctr=0;
	do
	{
		Out(msg2modem[ctr]);
		delay(5);
		PortChar = Wait4PortChar(20);
		if(PortChar == -1) return -1;
		delay(5);
		ctr++;
	} while(msg2modem[ctr] != '\r');
	Out(msg2modem[ctr]);
	delay(5);
	PortChar = Wait4PortChar(20);
	delay(5);
	Response1 = Wait4PortChar(5000);
	Response2 = Wait4PortChar(5000);
	return Response1;
}


void PreparePort()
{
	bioscom(0,0x83,1);
	outportb(DataSerPort+4,3);
	inportb(DataSerPort);
}

void Disconnect()
{
	TellModem(HangUp);
}

int Out(char Byte)
{
	int XmRdy = 0;
	XmRdy = inportb(StatSerPort);
	XmRdy = XmRdy & 0x60;
	while(XmRdy != 0x60)
	{
		XmRdy = inportb(StatSerPort);
		XmRdy = XmRdy & 0x60;
	}
	delay(NormalWait);
	outportb(DataSerPort,Byte);
}

int In()
{
	int RxRdy = 0;
	PortChar = 0;
	RxRdy = inportb(StatSerPort);
	RxRdy = RxRdy & 0x1e;
	if(RxRdy == 0x00)
		PortChar = inportb(DataSerPort);
	else
		PortChar = 0;
	return PortChar;
}



/***************** dialing routine*********/
int makephonecall(char *wheretocall)
{
	PreparePort();
	ModemStat = bioscom(0, CommByte, CommPort);
	outportb(CtrlSerPort, 0x03);
	ModemStat = inportb(DataSerPort);
	while(RxBufferEmpty != 0)
	{
		ModemStat = Wait4PortChar(1);
		if(ModemStat == -1) return 1; //call fails....
	}
	ModemStat = TellModem(NumericOn);
			if(ModemStat == -1) return 1; //call fails....
	ModemStat = TellModem(liftphone);
			if(ModemStat == -1) return 1; //call fails....
	ModemStat = TellModem(reportprog);
			if(ModemStat == -1) return 1; //call fails....
	int callfail = 0;			//phone call has been made...
	int GoAhead = '0';
	int ctr = 0;
	do
	{
		GoAhead = '0';
		ModemStat = TellModem(wheretocall);
		ctr++;
		if(ModemStat == '6')
		{
			printf("\nThere is no dial tone\n");
			GoAhead = '0';
			callfail = 1;
		}
		if(ModemStat == '7')
		{
			printf("\nThe line is busy\n");
			GoAhead = '0';
			callfail = 1;
		}
		if(ModemStat == '8')
		{
			printf("\nThe other party does not answer\n");
			GoAhead = '0';
			callfail = 1;
		}
		if(GoAhead == '0')
		{
			delay(2000);
			if(ctr > 1)
			{
				printf("\nHanging up\n");
				break;
			}
			else
				printf("\nRedialing...\n");
		}
	} while(GoAhead != '1');
	ModemStat = TellModem(HangUp);
	return callfail;
}








5. Sentinel Codes      TOP

/*  Ateneo Supevisory Control And Data Acquisition (SCADA) Project
	Sentinel Prototype Security System

   Supervisor Program developed by Christian Rivera
*/

#include
#include
#include
#include
#include
#include
#include
#include
#include

//Some macros (LPT1 was used in the interface)

const int CONTROL = 0x37a;
const int STATUS = 0x379;
const int DATA = 0x378;
const int DELAY = 500;

#include"keypad.cpp"
int access(){ return keypad();}	//door.cpp calls this function
#include"door.cpp"
#include"irdetek.cpp"
#include"dial.cpp"			//courtesy of Sir Tris ^_^

//Call this number in the meantime; additional numbers may be called
char *SUPERVISOR = {"atdt4266001,,\r"};

//Flags
int motiondetector = 1;				//turn it on
int peopleinside = 0;				//enable presence alert

//check detector status and take appropriate actions
//return 1 means something's fishy going on

int firecheck(void);
int presencecheck(void);
void securitycheck(void);
void prompt(void);

void main(void)
{
	clrscr();
	printf("\nSentinel On.\n");
	delay(DELAY);		//this is just a display delay. All subsequent occurences
	securitycheck();	//apply
}

//Function definitions; others are in the included files (see above)

//you may change the argument in makephonecall with your chosen
//phone number; just make sure it's "atdtxxxxxx\r" since it only
//commands the modem. Check dial.cpp

//monitors the fire/smoke detector
int firecheck(void)
{
	int firestatus = inportb(STATUS);
	firestatus = firestatus & 0x80;
	if(firestatus == 0x80)			//S7 is inverted
	{
		clrscr();
		printf("HEAT EMERGENCY: Possible fire in the room\n");
		if(motiondetector == 0) motiondetector = 1;
			//turn motiondetector on
		if(makephonecall(SUPERVISOR))
		{
			printf("\nSUPERVISOR CANNOT BE CONTACTED.\n");
			delay(DELAY);
		}
		door();		//let the people out
		return 1;
	}
	return 0;
}


//monitors the IR array
int motioncheck(void)
{
	irmotion();         //check with irdetek.cpp
	if((irmotion() == 2) && (motiondetector == 1))
	{
		clrscr();
		printf("\nSomething moved.\n");
		if(makephonecall(SUPERVISOR))
			printf("Cannot contact supervisor\n");
		delay(DELAY);
		return 1;
	}
	return 0;
}

//Monitors the laser presence detector

int presencecheck(void)
{
	outportb(CONTROL, 0x00);
	int presence = inportb(STATUS);
	presence = presence & 0x40;
	if(presence == 0x40 && peopleinside == 0)
	{
		clrscr();
		printf("Possible intruder.\n");
		if(makephonecall(SUPERVISOR)) printf("Phone call failed...\n");
		delay(DELAY);
		return 1;
	}
	else clrscr();
	return 0;
}


//continually polls the system's components to monitor any
//events
void securitycheck(void)
{
	int entry;
	for(;;)
	{
		firecheck();
		if(access())
		{
			motiondetector = 0;
			peopleinside = 1;
			printf("\nTurning off security\n");
			door();
			entry = 0;
		}
		presencecheck();
		motioncheck();
		if(kbhit()) prompt();		//enable commands
	}
}


//takes 'hotkeys' from user
void prompt(void)
{
	char command, response;
	for(;;)
	{
		command = getch();
		switch(command)
		{
			case 'Q':
			case 'q':
				printf("\nTurn off Sentinel? ");
				response = getche();
				if(response == 'y' || response == 'Y') exit(0);
				return;
			case 'L':
			case 'l':
				printf("\nLogout? ");
				response = getche();
				if(response == 'y' || response == 'Y')
				{
					printf("\nLogging out\n");
					door();
					motiondetector = 1;
					peopleinside = 0;
				}
				printf("\n");
				return;
			case 'O':
			case 'o':
				door();
				printf("Opening door...");
				return;
			case 'M':
			case 'm':
				if((motiondetector == 0) || (peopleinside == 1))
				{
					printf("\nTurning on motion 
						and presence detectors...\n");
					delay(DELAY);
					motiondetector = 1;
					peopleinside = 0;
				}
				else printf("\nDetectors ARE on.\n");
				return;
			case 'S':
			case 's':
				printf("\nStopping monitoring...\n");
				delay(DELAY);
				peopleinside = 1;
				motiondetector = 0;
				return;
			case 'R':		//necessary since the door 
							only goes one way or the other
			case 'r':		//this sends a command to 
							the DC motor to stop
				printf("\nResetting door.\n");
				outport(CONTROL, 0x00);
				outport(DATA, 0x80);
				outport(DATA, 0x00);
				return;
		}
	}
}








6. Testing Codes      TOP

/*	This program sends and reads data off the ports of the parallel
	ports. Each process and echoed to screen to let user confirm
	these with his hardware

	17 September 2001
	by Christian Rivera
*/
#include
#include
#include
#include
#include


const int STATUS 	= 0x379;		//parallel port addresses
const int CONTROL	= 0x37a;
const int DATA		= 0x378;
const int DELAY		= 500;

char *tobinary(int number, int length);		//converts dec to binary

int getstatus(int port)                         //discards least
{						//3 significant bits (S0, S1, S2)
	int status = inportb(STATUS);		//which are randomly
	return (status & 0xf8);			//generated by computer
}

/*************************************************************************
	TESTS type 1 tests are manual. User must press key to proceed
		  type 0 tests are automatic.
***************************************************************************/

void datalinetest(int lag, int type)
{
	printf("\nTesting DATA lines...\n\n");
	int bits = 1;
	for(int i = 0; i <= 8; i++)
	{
		if(i == 8) bits = 255;
		outportb(DATA, bits);
		printf("Sending %s to %x...\n",
			tobinary(bits, 8), DATA);
		bits = bits << 1;
		delay(lag);
		if (type == 1) getch();
	}

}


void controllinetest(int lag, int type)
{
	int bits = 1;
	printf("\nTesting CONTROL lines...\n\n");
	for(int j = 0; j <=4; j++)
	{
		if(j == 4) bits = 15;
		outport(CONTROL, bits);
		printf("Sending %s to %x...\n",
			tobinary(bits, 4), CONTROL);
		bits = bits << 1;
		delay(lag);
		if (type == 1) getch();
	}

}

void statuslinetest(int lag, int type, int test)	// 0 test: automatic
{
	int bits, ctr = 1;
	char ch;
	printf("\nTesting status lines...\n\n");
	if(test == 0) ctr = 5;
	while(1)
	{
		bits = getstatus(STATUS);
		printf("Receiving %s from %x...\n",
			tobinary(bits, 8), STATUS);
		delay(lag);
		if(type == 1)
		{
			ch = getch();			//pressing q quits test
			if((ch == 'q') || (ch == 'Q')) break;
		}
		else ctr--;
		if(ctr == 0) break;
	}
}

int porttest(int testtype)		//0 = automatic (500ms delay between tests
{					//1 = manual (user must prompt proceed)\
//	outportb(DATA, 0x00);
//	outportb(CONTROL, 0x00);
	int tdelay  = DELAY, test = 0;
	if(testtype == 1)
	{
		tdelay = 0;
		test = 1;
	}
	datalinetest(tdelay, testtype);
//	controllinetest(tdelay, testtype);
//	statuslinetest(tdelay, testtype, test);
}


int main(void)
{
//	porttest(0);
	char ch;
	do
	{
		porttest(1);
		ch = getch();
	} while (ch != 'q');
/*	char prompt;
	do
	{
		int	control;
		printf("Control byte: ");
		scanf("%x", &control);
		outport(CONTROL, control);
		printf("Sending %s to %x\n", tobinary(control,4), CONTROL);
		int data = getstatus(STATUS);
		printf("Receiving %s from %x\n", tobinary(data,8), STATUS);
		prompt = getch();
	} while(prompt != 'q');*/
}

/*******Conversion of numbers to binary***********/

char *tobinary(int quotient, int length)
{
	char *str = new char [length];
	for(int i = length-1; i >= 0; i--)
	{
		int remainder = quotient % 2;
		if(remainder == 1) str[i] = '1';
		else str[i] = '0';
		quotient = quotient / 2;
	}
	str[length] = '\0';
	return str;
}



back to CE150