Ejemplo n.º 1
0
// How to handle static variables with multiple sensors?  objects? add to gpspacket?
int read_gps(struct gps *gpsData_ptr)
{
	cyg_io_handle_t port_handle;
	cyg_serial_buf_info_t buff_info;
	unsigned int len = sizeof (buff_info);

	// get serial port handle
	cyg_io_lookup( gpsData_ptr->portName, &port_handle );
	
	cyg_io_get_config (port_handle, CYG_IO_GET_CONFIG_SERIAL_BUFFER_INFO,\
			&buff_info, &len);
	unsigned int bytesInBuffer = buff_info.rx_count;
	unsigned int bytesReadThisCall =0;;
	unsigned short msgPayloadSize = 0, bytesToRead = 0, bytesRead = 0;
	int status =0;
	
	// Initialization of persistent local buffer
	if (gpsData_ptr->localBuffer == NULL)
	{
		gpsData_ptr->localBuffer = (unsigned char*) malloc (1024 * sizeof (unsigned char));
	}

	// First check if there are any bytes in the serial buffer, return if none
	if( bytesInBuffer == 0 )
		return -1;

	// Get localBuffer stored in gps packet. This is to keep the following code readable
	localBuffer = gpsData_ptr->localBuffer;
	bytesInLocalBuffer= gpsData_ptr->bytesInLocalBuffer;
	readState = gpsData_ptr->readState;

	//fprintf(stderr, "read state is %d (before while)\n", readState);

	// Keep reading until we've processed all of the bytes in the buffer
	while (bytesReadThisCall < bytesInBuffer){
		
		//fprintf(stderr, "read state is %d (after while)\n", readState);

		switch (readState){
			case 0: //Look for packet header bytes
				// Read in up to 4 bytes to the first open location in the local buffer
				bytesRead = read(gpsData_ptr->port,&localBuffer[bytesInLocalBuffer],4-bytesInLocalBuffer);
				bytesReadThisCall += bytesRead; // keep track of bytes read during this call
					
				if (localBuffer[0] == '$'){ // Check for first header byte
					bytesInLocalBuffer = 1;

					//fprintf(stderr, "case 0, $ header type \n");

					if (localBuffer[1] == 'B'){ // Check for second header byte
						bytesInLocalBuffer = 2;
						if (localBuffer[2] == 'I'){ // Check for third header byte
							bytesInLocalBuffer = 3;
							if (localBuffer[3] == 'N'){ // Check for fourth header byte
								bytesInLocalBuffer = 4;
								readState++; // header complete, move to next stage
							}
						}
					}
				}
				else {
					gpsData_ptr->err_type = noPacketHeader;
				}
				break;	// end case 0
				
			case 1: // Look for block ID and data length
				// Find how many bytes need to be read for block ID (2) + data length (2) - bytes already read (includes 4 byte header)
				bytesToRead = 8 - bytesInLocalBuffer;
			
				// Read in bytes to the last location in the local buffer
				bytesRead = read(gpsData_ptr->port,&localBuffer[bytesInLocalBuffer],bytesToRead);
				bytesInLocalBuffer += bytesRead; // keep track of bytes in local buffer
				bytesReadThisCall += bytesRead; // keep track of bytes read during this call
				
				if (bytesRead == bytesToRead){
					readState++;
					//printf ("\n<GPS>: Got msgID: %d and Data Length: %d", localBuffer[5]*256 + localBuffer[4], localBuffer[7]*256 + localBuffer[6]);
				}
				else{
					gpsData_ptr->err_type = incompletePacket;
				}
				break;	// end case 1
		
			case 2: //Read payload, checksum, and stop bytes
				// Find message payload size
				msgPayloadSize = localBuffer[7]*256 + localBuffer[6]; // data is in little endian format
				
				// Error checking on payload size. If size is bigger than expected, dump packet
				if(msgPayloadSize > GPS_MAX_MSG_SIZE){			
					gpsData_ptr->err_type = incompletePacket;
					reset_localBuffer();
				}
				
				// Find how many bytes need to be read for the total message (Header (4)  + ID (2) + Size (2) + Payload + checksum (2) + stop (2) - bytes already read )
				bytesToRead = msgPayloadSize + 12 - bytesInLocalBuffer;
				
				// Read in the remainder of the message to the local buffer, starting at the first empty location
				bytesRead = read (gpsData_ptr->port, &localBuffer[bytesInLocalBuffer], bytesToRead);
				bytesInLocalBuffer += bytesRead; // keep track of bytes in local buffer
				bytesReadThisCall += bytesRead; // keep track of bytes read during this call
				
				if (bytesRead == bytesToRead){
					//printf ("\n<GPS>: Got complete message! Tried for %d, got %d",bytesToRead,bytesRead);
					//printf ("\n<GPS>: My checksum: %d  Recv: %d",do_chksum(localBuffer, 8, msgPayloadSize+8),(localBuffer[8+msgPayloadSize+1]*256 + localBuffer[8+msgPayloadSize]));
					// Checksum verification
					if ( do_chksum(localBuffer, 8, msgPayloadSize+8) == (localBuffer[8+msgPayloadSize+1]*256 + localBuffer[8+msgPayloadSize]) ){
						// If it's OK, extract data
						parse_gps( gpsData_ptr );
						gpsData_ptr->err_type = data_valid;
						//printf ("\n<GPS>: Success!");
						status = 1;
					}										
					else{ 
						//printf ("\n<GPS>: Checksum mismatch!");
						gpsData_ptr->err_type = checksum_err;
					}
					reset_localBuffer();
				}
				else{
					//printf ("\n<GPS>: Didn't get complete message. Tried for %d, got %d",bytesToRead,bytesRead);
					gpsData_ptr->err_type= incompletePacket;
					
					status = 0;									
				}
				break;	// end case 2
				
				default:
					reset_localBuffer();
					printf ("\n<GPS>: Why are you here?");
					status = 0;
				break; // end default
		
		} // end switch (readState)

	} // end while (bytesReadThisCall < bytesInBuffer)	

	// Store local buffer in gps packet
	gpsData_ptr->localBuffer = localBuffer;
	gpsData_ptr->bytesInLocalBuffer = bytesInLocalBuffer;
	gpsData_ptr->readState = readState;
	
	return status;
}
Ejemplo n.º 2
0
int read_gps(struct gps *gpsData_ptr)
{
	// serial port buffer handle
	cyg_io_handle_t port_handle;
	cyg_serial_buf_info_t buff_info;
	unsigned int len = sizeof (buff_info);

	// get serial port handle
	cyg_io_lookup( gpsData_ptr->portName, &port_handle );	
	
	cyg_io_get_config (port_handle, CYG_IO_GET_CONFIG_SERIAL_BUFFER_INFO,\
			&buff_info, &len);
	unsigned int bytesInBuffer = buff_info.rx_count;
	unsigned int bytesReadThisCall =0;;
	unsigned short msgPayloadSize = 0, bytesToRead = 0, bytesRead = 0;
	int status = 0;
	
	// Initialization of persistent local buffer
	if (gpsData_ptr->localBuffer == NULL)
	{
		gpsData_ptr->localBuffer = (unsigned char*) malloc (1024 * sizeof (unsigned char));
	}

	// First check if there are any bytes in the serial buffer, return if none
	if( bytesInBuffer == 0 )
		return -1;

	// Get localBuffer stored in gps packet. This is to keep the following code readable
	localBuffer = gpsData_ptr->localBuffer;
	bytesInLocalBuffer= gpsData_ptr->bytesInLocalBuffer;
	readState = gpsData_ptr->readState;
	
	// Keep reading until we've processed all of the bytes in the buffer
	while (bytesReadThisCall < bytesInBuffer){
		
		switch (readState){
			case 0: //Look for packet header bytes
				// Read in up to 2 bytes to the first open location in the local buffer
				bytesRead = read(gpsData_ptr->port,&localBuffer[bytesInLocalBuffer],2-bytesInLocalBuffer);
				bytesReadThisCall += bytesRead; // keep track of bytes read during this call
					
				if (localBuffer[0] == 0xA0){ // Check for first header byte
					bytesInLocalBuffer = 1;
					if (localBuffer[1] == 0xA2){ // Check for second header byte
						bytesInLocalBuffer = 2;
						readState++; // header complete, move to next stage
					}
				}
				else {
					gpsData_ptr->err_type = noPacketHeader;
				}
			break;	// end case 0
			
			case 1: //Look for message size bytes
				// Find how many bytes need to be read for data length (2) - bytes already read (includes 2 byte header)
				bytesToRead = 4 - bytesInLocalBuffer;	
		
				// Read in up to 2 bytes to the first open location in the local buffer
				bytesRead = read(gpsData_ptr->port,&localBuffer[bytesInLocalBuffer],bytesToRead);
				bytesReadThisCall += bytesRead; // keep track of bytes read during this call
				bytesInLocalBuffer += bytesRead; // keep track of bytes in local buffer
				
				if (bytesRead == bytesToRead){
					readState++; // size bytes complete, move to next stage
				}
				else{
					//printf ("\n<GPS>: Failed to get size bytes");
					gpsData_ptr->err_type = incompletePacket;				
				}
			break;	// end case 1
		
			case 2: //Read payload, checksum, and stop bytes
				// Find message payload size
				msgPayloadSize = getbeuw(localBuffer,2)&0x7FFF; // packet size is 15 bits. bitwise AND ensures only 15 bits are used.
				
				//printf("<GPS>: msgPayloadSize: %d\n",msgPayloadSize);
				
				// Error checking on payload size. If size is bigger than expected, dump packet
				if(msgPayloadSize > GPS_MAX_MSG_SIZE){			
					gpsData_ptr->err_type = incompletePacket;
					reset_localBuffer();
				}
				
				// Find how many bytes need to be read for the total message (Header (2) + Size (2) + Payload + checksum (2) + stop (2) - bytes already read )
				bytesToRead = msgPayloadSize + 8 - bytesInLocalBuffer;
				
				// Read in the remainder of the message to the local buffer, starting at the first empty location
				bytesRead = read (gpsData_ptr->port, &localBuffer[bytesInLocalBuffer], bytesToRead);
				bytesInLocalBuffer += bytesRead; // keep track of bytes in local buffer
				bytesReadThisCall += bytesRead; // keep track of bytes read during this call
				
				if (bytesRead == bytesToRead){
					//printf ("\n<GPS>: Got complete message! Tried for %d, got %d",bytesToRead,bytesRead);
					//printf("<GPS>: Packet ID %d \n", localBuffer[4]);
					//printf("<GPS>: msgPayloadSize: %d\n",msgPayloadSize);
					//printf("<GPS>: My checksum: %d  Recv: %d\n",do_chksum(localBuffer, 4, msgPayloadSize+4),getbeuw(localBuffer,4+msgPayloadSize));

					// Checksum verification (15-bit, big endian)
					if ( (do_chksum(localBuffer, 4, msgPayloadSize+4)&0x7FFF) == (getbeuw(localBuffer,4+msgPayloadSize)&0x7FFF) ){
						// If it's OK, extract data
						parse_gps( gpsData_ptr );
						gpsData_ptr->err_type = data_valid;
						//printf ("\n<GPS>: Success!");
						status = 1;
					}
					else{
						//printf ("\n<GPS>: Checksum mismatch!");
						gpsData_ptr->err_type = checksum_err;
					}
					reset_localBuffer(); // Clear the local buffer regardless
				}
				else{
					//printf ("<GPS>: Didn't get complete message. Tried for %d, got %d. %d\n",bytesToRead,bytesRead,msgPayloadSize);
					gpsData_ptr->err_type= incompletePacket;
					
					status = 0;
				}
			break;	// end case 2
				
			default:
				reset_localBuffer();
				printf ("\n<GPS>: Why are you here?");
				status = 0;
			break;	// end default
		
		} // end switch (readState)

	} // end while (bytesReadThisCall < bytesInBuffer)
	
	// Store local buffer in gps packet
	gpsData_ptr->localBuffer = localBuffer;
	gpsData_ptr->bytesInLocalBuffer = bytesInLocalBuffer;
	gpsData_ptr->readState = readState;
	
	return status;
}
Ejemplo n.º 3
0
// How to handle static variables with multiple sensors?  objects? add to gpspacket?
int read_gps(struct gps *gpsData_ptr)
{
	cyg_io_handle_t port_handle;
	cyg_serial_buf_info_t buff_info;
	unsigned int len = sizeof (buff_info);

	// get serial port handle
	cyg_io_lookup( gpsData_ptr->portName, &port_handle );
	
	cyg_io_get_config (port_handle, CYG_IO_GET_CONFIG_SERIAL_BUFFER_INFO,\
			&buff_info, &len);
	unsigned int bytesInBuffer = buff_info.rx_count;
	unsigned int bytesReadThisCall = 0;
	unsigned short msgPayloadSize = 0, bytesToRead = 0, bytesRead = 0;
    unsigned long CRC_computed, CRC_read;
	int j, status =0;
	
	// Initialization of persistent local buffer
	if (gpsData_ptr->localBuffer == NULL)
	{
		gpsData_ptr->localBuffer = (unsigned char*) malloc (1024 * sizeof (unsigned char));
	}

	// First check if there are any bytes in the serial buffer, return if none
	if( bytesInBuffer == 0 )
		return -1;

	// Get localBuffer stored in gps packet. This is to keep the following code readable
	localBuffer = gpsData_ptr->localBuffer;
	bytesInLocalBuffer= gpsData_ptr->bytesInLocalBuffer;
	readState = gpsData_ptr->readState;

	while (bytesReadThisCall < bytesInBuffer){

        switch (readState){
            case 0: //Look for packet header bytes
                // Read in up to 3 bytes to the first open location in the local buffer
                //fprintf(stderr,"bytesInLocalBuffer is %d\n",bytesInLocalBuffer);
                
                bytesRead = read(gpsData_ptr->port,&localBuffer[bytesInLocalBuffer],3-bytesInLocalBuffer);
                
                //fprintf(stderr,"The first three bytes are %0X %0X %0X\n",localBuffer[0],localBuffer[1],localBuffer[2]);    
                //fprintf(stderr,"bytesRead is %d\n",bytesRead);
                //fprintf(stderr,"Read %d bytes, The first three bytes are %0X %0X %0X\n", bytesRead,localBuffer[0],localBuffer[1],localBuffer[2]);    
                
                bytesReadThisCall += bytesRead; // keep track of bytes read during this call
                
                if (localBuffer[0] == 0xAA){ // Check for first header byte
                    bytesInLocalBuffer = 1;
                    //fprintf(stderr, "case 0, 0xAA header type \n");
                    if (localBuffer[1] == 0x44){ // Check for second header byte
                        bytesInLocalBuffer = 2;
                        if (localBuffer[2] == 0x12){ // Check for third header byte
                            bytesInLocalBuffer = 3;
                            readState++;
                        }
                    }
                }
                else {
                    gpsData_ptr->err_type = noPacketHeader;
                }
                break;	// end case 0
                
            case 1: // Look for block ID and data length
                // Read 28 Header Bytes
                bytesToRead = 28 - bytesInLocalBuffer;
                
                // Read in bytes to the last location in the local buffer
                bytesRead = read(gpsData_ptr->port,&localBuffer[bytesInLocalBuffer],bytesToRead);
                bytesInLocalBuffer += bytesRead; // keep track of bytes in local buffer
                bytesReadThisCall += bytesRead;  // keep track of bytes read during this call
                
                if (bytesRead == bytesToRead){
                    readState++;
                    //fprintf (stderr,"<GPS>: Got msgID: %d and Data Length: %d\n", localBuffer[5]*256 + localBuffer[4], localBuffer[9]*256 + localBuffer[8]);
                    //printf ("<GPS>: localBuffer[0] = %02X localBuffer[1] = %02X localBuffer[2] = %02X localBuffer[3] = %02X localBuffer[4] = %02X localBuffer[5] = %02X \n", localBuffer[0], localBuffer[1], localBuffer[2], localBuffer[3], localBuffer[4], localBuffer[5]);
                }
                else{
                    gpsData_ptr->err_type = incompletePacket;
                }
                break;  // end case 1
        
            case 2: //Read payload
                // Find message payload size
                msgPayloadSize = localBuffer[9]*256 + localBuffer[8]; // data is in little endian format
                
                // Error checking on payload size. If size is bigger than expected, dump packet
                if(msgPayloadSize > GPS_MAX_MSG_SIZE){			
                    gpsData_ptr->err_type = incompletePacket;
                    reset_localBuffer();
                }
                
                // Find how many bytes need to be read for the total message (Sync (3)  + Remaining Header (25) + Payload - bytes already read )
                bytesToRead = msgPayloadSize + 28 - bytesInLocalBuffer;
                
                //printf("bytesInLocalBuffer is %d bytesToRead is %d \n",bytesInLocalBuffer,bytesToRead);
                
                // Read in the remainder of the message to the local buffer, starting at the first empty location
                bytesRead = read (gpsData_ptr->port, &localBuffer[bytesInLocalBuffer], bytesToRead);
                bytesInLocalBuffer += bytesRead; // keep track of bytes in local buffer
                bytesReadThisCall += bytesRead; // keep track of bytes read during this call
                
                if (bytesRead == bytesToRead){
                    //printf ("<GPS>: Got complete message! Tried for %d, got %d\n",bytesToRead,bytesRead);
					readState++;
				}
				else {
					gpsData_ptr->err_type = incompletePacket;
				}
				
				break; // end case 2
				
			case 3: // read CRC bytes (4 bytes)
				bytesToRead = 4;
				bytesRead = read (gpsData_ptr->port, &localBuffer[bytesInLocalBuffer], bytesToRead);
				bytesInLocalBuffer += bytesRead;
				bytesReadThisCall += bytesRead;
					
				if(bytesRead == bytesToRead) {
					// CRC verification
					CRC_computed = CalculateBlockCRC32(bytesInLocalBuffer-4,localBuffer);
					endian_swap(localBuffer,140,4);
					CRC_read = *(uint32_t *) (localBuffer+140);
                    if (CRC_computed == CRC_read) {
                        gpsData_ptr->err_type = data_valid;
						parse_gps(gpsData_ptr);
                        //fprintf (stderr,"<GPS t = %9.3lf>: Success!\n",gpsData_ptr->GPS_TOW);
                    }
                    else{ 
						send_status("GPS CRC ERR");
                        //fprintf (stderr,"<GPS>: Checksum mismatch!\n");
						/* ============= DEBUG CHECKSUM ERROR ================
						fprintf (stderr,"<GPS %d>: Checksum mismatch! Buffer: %02X%02X%02X%02X Read: %08lX Computed: %08lX\n",localBuffer[5]*256 + localBuffer[4],localBuffer[140],localBuffer[141],localBuffer[142],localBuffer[143],CRC_read,CRC_computed);
                        fprintf (stderr,"Hex: \n");
                            for (j = 0; j < bytesInLocalBuffer; j++) {
                                fprintf(stderr,"%02X ",localBuffer[j]);
                                if(j%8==7) 
                                    fprintf(stderr,"\n");
                            }
						*/
						gpsData_ptr->err_type = checksum_err;
                    }
                    
                    reset_localBuffer();
                }
                else{
                    //printf ("\n<GPS>: Didn't get complete message. Tried for %d, got %d",bytesToRead,bytesRead);
                    gpsData_ptr->err_type= incompletePacket;
                    
                    status = 0;									
                }
                break;	// end case 3
                
                default:
                    reset_localBuffer();
                    printf ("\n<GPS>: Why are you here?");
                    status = 0;
                break; // end default
        
        } // end switch (readState)

    } // end while (bytesReadThisCall < bytesInBuffer)	

    // Store local buffer in gps packet
    gpsData_ptr->localBuffer = localBuffer;
    gpsData_ptr->bytesInLocalBuffer = bytesInLocalBuffer;
    gpsData_ptr->readState = readState;
    
    return status;
}