Changeset - 4f2720815741
[Not reviewed]
default
0 6 0
ethanzonca@CL-SEC241-08.cedarville.edu - 12 years ago 2012-12-03 21:30:51
ethanzonca@CL-SEC241-08.cedarville.edu
Initial data request infrastructure complete
6 files changed with 132 insertions and 72 deletions:
0 comments (0 inline, 0 general)
master/master/config.h
Show inline comments
 
@@ -30,12 +30,14 @@
 
#define ERROR_SD_PARTITION 3
 
 
// --------------------------------------------------------------------------
 
// Slave Sensors config (slavesensors.c)
 
// --------------------------------------------------------------------------
 
 
// NOT USED. Could integrate into slavesensors.c setup function for configurability eventually.
 
// Currently manual configuration of sensors is done in slavesensors.c
 
#define SLAVE0_SENSORS BOARDTEMP
 
#define SLAVE1_SENSORS BOARDTEMP | HUMIDITY | TEMPERATURE | PRESSURE | AMBIENTLIGHT
 
#define SLAVE2_SENSORS BOARDTEMP | GEIGER
 
#define SLAVE3_SENSORS BOARDTEMP | CAMERA
 
#define SLAVE4_SENSORS NONE
 
#define SLAVE5_SENSORS NONE
 
@@ -100,13 +102,13 @@
 
#define DIGI_PATH1      "WIDE2"
 
#define DIGI_PATH1_TTL  1
 

	
 
// APRS comment: this goes in the comment portion of the APRS message. You
 
// might want to keep this short. The longer the packet, the more vulnerable
 
// it is to noise.
 
#define APRS_COMMENT    "Custom payload data here, eventually..."
 
#define APRS_COMMENT    "Payload data..."
 
 
// Transmit the APRS sentence every X milliseconds
 
#define APRS_TRANSMIT_PERIOD 5000
 

	
 

	
 
// --------------------------------------------------------------------------
master/master/lib/aprs.c
Show inline comments
 
@@ -12,15 +12,15 @@
 
 
#include "../config.h"
 
#include "aprs.h"
 
#include "ax25.h"
 
#include <stdio.h>
 

	
 
const char *gps_aprs_lat = "omgmylatitude";
 
const char *gps_aprs_lon = "omgmylongitude";
 
const char *gps_time = "omgmygpstime";
 
const char *gps_aprs_lat = "latitude";
 
const char *gps_aprs_lon = "longitude";
 
const char *gps_time = "gpstime";
 
float gps_altitude = 123.5;
 
int gps_course = 5;
 
int gps_speed = 13;
 

	
 
float meters_to_feet(float m)
 
{
master/master/lib/serparser.c
Show inline comments
 
@@ -59,26 +59,26 @@ static void setParserState(uint8_t state
 
	// Every time we change state, we have parsed a byte
 
	bufferParsePosition = (bufferParsePosition + 1) % BUFFER_SIZE;
 
}
 
 
// Receive data on USART
 
 
char buffmeh[16];
 
char debugBuff[16];
 
 
ISR(USART0__RX_vect)
 
{
 
	led_on(POWER);
 
	buffer[bufferDataPosition % BUFFER_SIZE] = UDR0;
 
	bufferDataPosition = (bufferDataPosition + 1) % BUFFER_SIZE;
 
	/*sprintf(buffmeh, "bdp: %d, bpp: %d \r\n", bufferDataPosition, bufferParsePosition);
 
	serial0_sendString((buffmeh)); */
 
	/*sprintf(debugBuff, "bdp: %d, bpp: %d \r\n", bufferDataPosition, bufferParsePosition);
 
	serial0_sendString((debugBuff)); */
 
}
 
 
 
 
#define DEBUG
 
//#define DEBUG
 
 
// Parse data from circular buffer
 
int serparser_parse(void)
 
{
 
	
 
	char byte;
 
@@ -91,86 +91,86 @@ int serparser_parse(void)
 
		// Reset 
 
		if(parserState == STATE_RESET)
 
		{
 
			if(byte == '[') // Start of frame; keep parsing
 
			{
 
				#ifdef DEBUG
 
				serial0_sendString("start ok\r\n");
 
				serial0_sendString("start\r\n");
 
				#endif
 
				setParserState(STATE_GETID);
 
			}
 
			else // Not start of frame, reset
 
			{
 
				#ifdef DEBUG
 
				serial0_sendString("not start\r\n");
 
				//serial0_sendString("invalid\r\n");
 
				#endif
 
				setParserState(STATE_RESET);
 
				return PARSERESULT_NODATA; // no valid start bit; better luck next time. run the function the next time around the main loop.
 
			}
 
		}
 
		
 
		// Get destination module ID
 
		else if(parserState == STATE_GETID)
 
		{
 
			if(byte == MODULE_ID) // Message intended for this module; keep parsing
 
			{
 
				#ifdef DEBUG
 
				serial0_sendString("dest ok\r\n");
 
				serial0_sendString("dest\r\n");
 
				#endif
 
				checksumCalc += byte;
 
				setParserState(STATE_GETDATATYPE);
 
			}
 
			else // Transmission is intended for another module; reset
 
			{
 
				#ifdef DEBUG
 
				serial0_sendString("bad dest\r\n");
 
				//serial0_sendString("bad dest\r\n");
 
				#endif
 
				setParserState(STATE_RESET);
 
			}
 
		}
 
		
 
		// Get payload type ID
 
		else if(parserState == STATE_GETDATATYPE)
 
		{
 
			#ifdef DEBUG
 
			serial0_sendString("type ok\r\n");
 
			serial0_sendString("type\r\n");
 
			#endif
 
			receivedDataType = byte; // Store the type of data receiving
 
			checksumCalc += byte;
 
			setParserState(STATE_GETDATA);
 
		}
 
		
 
		// Get payload data
 
		else if(parserState == STATE_GETDATA)
 
		{		
 
			if (byte == ']') // End of frame
 
			{
 
				#ifdef DEBUG
 
				serial0_sendString("eof ok\r\n");
 
				sprintf(buffmeh, "recvd %d bytes data\r\n", dataLength);
 
				serial0_sendString((buffmeh));
 
				serial0_sendString("eof\r\n");
 
				sprintf(debugBuff, "%d B, sum=%d\r\n", dataLength, checksumCalc);
 
				serial0_sendString((debugBuff));
 
				#endif
 
				
 
				setParserState(STATE_GETCHECKSUM);
 
				// Checksum is now after the close bracket to solve bug FS#29		
 
				
 
 
			}
 
			else // Still receiving data
 
			{
 
				#ifdef DEBUG
 
				serial0_sendString("data ok\r\n");
 
				serial0_sendString("data\r\n");
 
				#endif
 
				receivedPayload[dataLength] = byte;
 
				dataLength++;
 
				checksumCalc += byte;
 
				
 
				// Data buffer overrun protection
 
				if(dataLength > MAX_PAYLOAD_LEN) {
 
					#ifdef DEBUG
 
					serial0_sendString("data ovf\r\n");
 
					serial0_sendString("ovf\r\n");
 
					#endif
 
					setParserState(STATE_RESET);
 
					return PARSERESULT_FAIL;
 
				}
 
				else {
 
					// Set state. MUST call even though state is maintained to update parse position
 
@@ -182,17 +182,23 @@ int serparser_parse(void)
 
 
		}
 
		else if(STATE_GETCHECKSUM)
 
		{
 
			// TODO: Compare checksums
 
			if(byte == checksumCalc) {
 
				serial0_sendString("checksum ok\r\n");
 
				serial0_sendString("check\r\n");
 
				setParserState(STATE_RESET);
 
				return PARSERESULT_PARSEOK;
 
			}
 
			else {
 
				serial0_sendString("checksum fail\r\n");
 
				serial0_sendString("bcheck\r\n");
 
				setParserState(STATE_RESET);
 
				return PARSERESULT_FAIL;
 
			}
 
			
 
			/*
 
			if(bufferParsePosition == bufferDataPosition)
 
			{
 
				// We are at the end of the line. No more data to parse.
 
				setParserState(STATE_RESET);
 
				return PARSERESULT_PARSEOK;
 
			}
 
@@ -200,11 +206,12 @@ int serparser_parse(void)
 
			{
 
				setParserState(STATE_RESET);
 
				// we could choose to keep parsing now, or parse the next message next loop around (better idea).
 
				// return now so we hit it the next time around
 
				return PARSERESULT_PARSEOK;
 
			}
 
			*/
 
		}			
 
	}
 
	return PARSERESULT_NODATA;
 
	
 
}
 
\ No newline at end of file
master/master/lib/slavesensors.c
Show inline comments
 
@@ -12,12 +12,13 @@
 
 
#include <avr/io.h>
 
#include <stdbool.h>
 
#include "../config.h"
 
#include "serial.h"
 
#include "serparser.h"
 
#include "slavesensors.h"
 

	
 
// Serial Commands
 
enum sensorTypes // CMD ID#
 
{
 
	NONE = 0,
 
	BOARDTEMP = (1<<0),
 
@@ -26,71 +27,123 @@ enum sensorTypes // CMD ID#
 
	TEMPERATURE = (1<<3),
 
	HUMIDITY = (1<<4),
 
	AMBIENTLIGHT = (1<<5),
 
	CAMERA = (1<<5),
 
};
 

	
 
uint8_t receptionFinished = 0;
 
uint8_t currentSlave = 0;
 
uint8_t currentSlaveSensor = 0;
 
 
uint8_t maxSlave = 8;
 
uint16_t slaves[8];
 
uint8_t maxSensorsPerSlave = 8;
 
uint16_t slaves[8][8];
 
 
bool requesting = false;
 
 
void slavesensors_setup() 
 
{
 
	// Empty array
 
	for(int i=0; i<8; i++) 
 
	for(int i=0; i<maxSlave; i++) 
 
	{
 
		slaves[i] = 0;
 
		for(int j=0; j<maxSensorsPerSlave; j++) 
 
		{
 
			slaves[i][j] = NONE;
 
		}			
 
	}	
 
	
 
	// Configure sensors
 
	slaves[0] = SLAVE0_SENSORS;
 
	slaves[1] = SLAVE1_SENSORS;
 
	slaves[2] = SLAVE2_SENSORS;
 
	slaves[3] = SLAVE3_SENSORS;
 
	slaves[4] = SLAVE4_SENSORS;
 
	slaves[5] = SLAVE5_SENSORS;
 
	slaves[6] = SLAVE6_SENSORS;
 
	slaves[7] = SLAVE7_SENSORS;	
 
	// Slave Configuration
 
		
 
	// slave 0
 
	slaves[0][0] = BOARDTEMP;
 
	
 
	// slave 1
 
	slaves[1][0] = BOARDTEMP;
 
	slaves[1][1] = HUMIDITY;
 
	slaves[1][2] = TEMPERATURE;
 
	slaves[1][3] = PRESSURE;
 
	slaves[1][4] = AMBIENTLIGHT;
 
	
 
	// slave 2
 
	slaves[2][0] = BOARDTEMP;
 
	slaves[2][1] = GEIGER;
 
	
 
	// slave 3
 
	slaves[3][0] = BOARDTEMP;
 
	slaves[3][1] = CAMERA;
 
	
 
}
 
 
bool slavesensors_isrequesting() 
 
{
 
	return requesting;	
 
}
 
 
void slavesensors_startprocess() 
 
{
 
	requesting = true;
 
	slavesensors_request();		
 
}
 
 
static void slavesensors_request() 
 
{
 
	serial_sendCommand(currentSlave + 0x30, currentSlaveSensor + 0x30, "");
 
}
 
 
bool slavesensors_process(uint8_t parseResult) 
 
void slavesensors_process(uint8_t parseResult) 
 
{
 
	// Periodic: Every Iteration
 
		
 
	// maybe we should do this in an ISR on byte received. only problem is that this could interrupt things,
 
	// but we only care about interruption during logging and such. don't log when parsing a message?
 
	
 
	if(!requesting) {
 
		// we got a command when we didn't request anything. probably skip it.
 
		return;
 
	}
 
	
 
	// TODO: timeout. If we're at NODATA for a long time and we are requesting, that's an issue.
 
	else if(parseResult == PARSERESULT_NODATA) {
 
		// Wait for data
 
	}
 
	
 
	// not anymore:
 
	//receptionFinished = serparser_parse();
 
	// now we need some way to know if a transmission finished. Probably set a flag in main from the
 
	// return that is "hasUnhandledTransmission = true"
 
		
 
	// Finished reception of a message (one sensor data value). If not finished, send out command to get the next one
 
	if(parseResult == PARSERESULT_PARSEOK)
 
	else if(parseResult == PARSERESULT_PARSEOK)
 
	{
 
		bool weFinishedTHeLastSlaveSensor = false; // ex.
 
		// if we finished the final reception for this slave, set gettingValues = false;
 
		if(currentSlave >= maxSlave && weFinishedTHeLastSlaveSensor)
 
		// If we finished all sensors for all slaves
 
		if(slaves[currentSlave+1][0] == NONE && slaves[currentSlave][currentSlaveSensor+1] == NONE) // If next sensor is none and finished all slaves, reset
 
		{
 
			currentSlave = 0;
 
			return false; // We're done for now!
 
			currentSlaveSensor = 0;
 
			requesting = false;
 
		}
 
		// If we finished up one slave, go to the next
 
		else if(slaves[currentSlave][currentSlaveSensor+1] == NONE) 
 
		{
 
			currentSlave++;
 
			currentSlaveSensor = 0;
 
			requesting = true;
 
			slavesensors_request();
 
		}
 
		// If we haven't finished a slave (or all of them), just get the next sensor of the current slave
 
		else
 
		{
 
			// Request data from the next slave
 
			currentSlave++;
 
			
 
			// Need to check the next bit over to see if it has that...
 
			
 
			serial_sendCommand(currentSlave, 'a', ""); // send req for data
 
			return true; // Keep going...
 
			// request data for the current sensor of the current slave
 
			currentSlaveSensor++;
 
			requesting = true;
 
			slavesensors_request();	
 
		}
 
	}
 
	// TODO: Handle errors. If we got a parse fail, then we probably need to retransmit the message. etc.
 
	else 
 
	
 
	// If fail, try retransmit. Or we could skip and hit it next time.
 
	// TODO: Maximum number of retransmissions
 
	else if(parseResult == PARSERESULT_FAIL) {
 
		if(requesting) {
 
			slavesensors_request();	// re-request
 
		}			
 
	}
 
	
 
	
 
	else if(parseResult == PARSERESULT_STILLPARSING)
 
	{
 
		return true; // Keep going...
 
		return; // do nothing
 
	}
 
	else {
 
		// something is terribly wrong!
 
		return;
 
	}
 
}		
 
\ No newline at end of file
master/master/lib/slavesensors.h
Show inline comments
 
@@ -12,12 +12,15 @@
 
 
 
#ifndef SLAVESENSORS_H_
 
#define SLAVESENSORS_H_
 
 
#include <stdbool.h>
 
#include <inttypes.h>
 
 
bool slavesensors_isrequesting();
 
void slavesensors_setup();
 
bool slavesensors_process();
 
 
void slavesensors_startprocess();
 
static void slavesensors_request();
 
void slavesensors_process(uint8_t parseResult);
 
 
#endif /* SLAVESENSORS_H_ */
 
\ No newline at end of file
master/master/master.c
Show inline comments
 
@@ -61,18 +61,14 @@ int main(void)
 
	const char* logBufPtr = logbuf;
 
	
 
	// Software timers	
 
	uint32_t lastAprsBroadcast = 0;
 
	uint32_t lastLog = 0;
 
	
 
	// If we are currently processing sensor data
 
	bool isProcessing = false;
 
	
 
	// Result of last parser run
 
	int parseResult = PARSERESULT_NODATA;
 
	bool haveDataToHandle = false;
 
	
 
	// Write CSV header to SD card
 
	logger_log("ProgramTime,LastAprsBroadcast,LastLog\n");
 
	
 
	while(1)
 
    {
 
@@ -103,22 +99,21 @@ int main(void)
 
		{
 
			while(afsk_busy());
 
			aprs_send(); // non-blocking
 
			//serial0_sendString("Initiating APRS transmission...\r\n");
 
			
 
			// Start getting values for next transmission
 
			isProcessing = true;
 
			// TODO: Check ifRequesting first. If we are still requesting, something is terribly wrong.
 
			if(!slavesensors_isrequesting())
 
			{
 
				slavesensors_startprocess();
 
			}
 
			
 
			lastAprsBroadcast = time_millis();
 
		}			
 
		
 
		parseResult = serparser_parse();
 
		
 
		// TODO: If we receive a command, we should still process it even if we aren't isProcessing, right?
 
		// Maybe we should isolate the received command handling ("Execution") and the issuing of requests.
 
		//if(isProcessing) 
 
		//{
 
		//	isProcessing = slavesensors_process(parseResult);
 
		//}
 
		slavesensors_process(parseResult);
 

	
 
		wdt_reset();
 
    }
 
}
 
\ No newline at end of file
0 comments (0 inline, 0 general)