/* These routines work together to send and receive data packets of */ /* any size between two systems. They can be turned into a file */ /* xfer protocol if need be. */ #define PROTOCOL_PACKET_MAX 4096 #define SYNC_CHAR 85 #include "crctable.h" /*----------------------------------------------------------------------------*/ int protocol_send_packet(int modem_port_no,char the_packet[],unsigned short packet_length,int common_debug_level_current) { /* Max. packet length passed is restricted to PROTOCOL_PACKET_MAX, which is defined above. */ div_t result; /* For outputting "unsigned short"s in two separate bytes. */ unsigned short current_character_pointer=0; /* Position in packet data we're processing. */ long computed_crc=0; char char_to_send; computed_crc = modem_port_no; /* These 2 lines are to eliminate warning message. */ computed_crc = 0; if (!fossil_cd(fossil_current_port)) /* Lost carrier? */ return(2); /* common_debug_message(common_debug_level_current,"protocol_send_packet()"); */ if (packet_length > PROTOCOL_PACKET_MAX) { /* common_debug_message(common_debug_level_current,"Packet length > PROTOCOL_PACKET_MAX."); */ return(1); /* ...indicating failure to send as requested; too long. */ } port_out(SYNC_CHAR); /* Send two bytes which signal start of packet. */ port_out(SYNC_CHAR); /* common_debug_message_w_no(common_debug_level_current,"Outgoing packet length:",(long)packet_length); */ result = div(packet_length,256); /* Output the packet length, MSB, then LSB. */ port_out(result.quot); /* Send out the 2 length bytes. */ port_out(result.rem); while (current_character_pointer < packet_length) { char_to_send = the_packet[current_character_pointer]; computed_crc = update_crc32(char_to_send,computed_crc); /* common_debug_message_w_no(common_debug_level_current+1,"CRC is now:",computed_crc); */ /* common_debug_message_w_no(common_debug_level_current+1,"Character was:",(long)char_to_send); */ port_out(char_to_send); current_character_pointer++; } if (!fossil_cd(fossil_current_port)) /* Lost carrier? Catch that before completing packet. */ return(2); /* common_debug_message_w_no(common_debug_level_current+1,"CRC MSB: ",(computed_crc>>24)&255); */ port_out((computed_crc >> 24) & 255); /* common_debug_message_w_no(common_debug_level_current+1,"CRC MSB2:",(computed_crc>>16)&255); */ port_out((computed_crc >> 16) & 255); /* common_debug_message_w_no(common_debug_level_current+1,"CRC LSB2:",(computed_crc>>8)&255); */ port_out((computed_crc >> 8) & 255); /* common_debug_message_w_no(common_debug_level_current+1,"CRC LSB2:",computed_crc&255); */ port_out( computed_crc & 255); /* common_debug_message(common_debug_level_current,"Successful packet send."); */ return(0); /* Barring comm. errors, we have just sent a packet! */ } /*----------------------------------------------------------------------------*/ unsigned short protocol_get_packet(int modem_port_no,int timeout_seconds,char the_packet[],int common_debug_level_current) { /* Returns 0 for failure to receive a good packet within the timeout */ /* or length of received packet. */ unsigned short packet_length,current_character_pointer=0; long computed_crc=0,received_crc,crc_msb,crc_msb2,crc_lsb2,crc_lsb; int char_from_modem, timeout_seconds_left; unsigned char temp_unsigned_char; time_t starting_time,ending_time; /* common_debug_message(common_debug_level_current,"protocol_get_packet()"); */ starting_time = time(NULL); /* Begin tracking the timeout period. */ ending_time = starting_time + timeout_seconds; sync_byte_loop: /* Keep coming back to here until we get a sync byte. */ timeout_seconds_left = ending_time - time(NULL); char_from_modem = get_char_from_modem_with_timeout(modem_port_no,timeout_seconds_left); /* MSB */ if (char_from_modem == -1) { /* common_debug_message(common_debug_level_current,"Timeout on first sync (NULL) byte."); */ return(0); } if (char_from_modem != SYNC_CHAR) /* Did we receive a sync character? */ goto sync_byte_loop; timeout_seconds_left = ending_time - time(NULL); /* Get the next byte and check to see if IT's null. */ if (timeout_seconds_left < 0) timeout_seconds_left = 0; char_from_modem = get_char_from_modem_with_timeout(modem_port_no,timeout_seconds_left); /* MSB */ if (char_from_modem == -1) { /* common_debug_message(common_debug_level_current,"Timeout on byte after first sync byte."); */ return(0); } if (char_from_modem != SYNC_CHAR) /* Did we receive correct byte? */ goto sync_byte_loop; timeout_seconds_left = ending_time - time(NULL); /* Start by getting the packet length. */ if (timeout_seconds_left < 0) timeout_seconds_left = 0; char_from_modem = get_char_from_modem_with_timeout(modem_port_no,timeout_seconds_left); /* MSB */ if (char_from_modem == -1) { /* common_debug_message(common_debug_level_current,"Timeout on MSB of packet_length."); */ return(0); } packet_length = char_from_modem * 256; if (time(NULL) > ending_time) { /* common_debug_message(common_debug_level_current,"Timeout after getting MSB of packet_length."); */ return(0); } timeout_seconds_left = ending_time - time(NULL); if (timeout_seconds_left < 0) timeout_seconds_left = 0; char_from_modem = get_char_from_modem_with_timeout(modem_port_no,timeout_seconds_left); /* LSB */ if (char_from_modem == -1) { /* common_debug_message(common_debug_level_current,"Timeout on LSB of packet_length."); */ return(0); } packet_length += char_from_modem; /* common_debug_message_w_no(common_debug_level_current,"Packet length:",(long)packet_length); */ if (packet_length > PROTOCOL_PACKET_MAX) { /* common_debug_message(common_debug_level_current,"Packet length > PROTOCOL_PACKET_MAX."); */ goto sync_byte_loop; /* This shouldn't happen, so must be a bad packet. */ } if (time(NULL) > ending_time) { /* common_debug_message(common_debug_level_current,"Timeout after getting LSB of packet_length."); */ return(0); } while (current_character_pointer < packet_length) { if (time(NULL) > ending_time) /* Timeout? This is really the only place we need to check for this timeout up until now. */ { /* common_debug_message(common_debug_level_current,"Timeout while looping for packet data."); */ return(0); } timeout_seconds_left = ending_time - time(NULL); if (timeout_seconds_left < 0) timeout_seconds_left = 0; char_from_modem = get_char_from_modem_with_timeout(modem_port_no,timeout_seconds_left); if (char_from_modem == -1) { /* common_debug_message(common_debug_level_current,"Timeout while waiting for a packet data character."); */ return(0); } the_packet[current_character_pointer] = (char)char_from_modem; computed_crc = update_crc32(the_packet[current_character_pointer],computed_crc); /* common_debug_message_w_no(common_debug_level_current+1,"CRC is now:",computed_crc); */ /* common_debug_message_w_no(common_debug_level_current+1,"Character was:",the_packet[current_character_pointer]); */ current_character_pointer++; } if (time(NULL) > ending_time) { /* common_debug_message(common_debug_level_current,"Timeout after looping for packet data."); */ return(0); } timeout_seconds_left = ending_time - time(NULL); if (timeout_seconds_left < 0) timeout_seconds_left = 0; char_from_modem = get_char_from_modem_with_timeout(modem_port_no,timeout_seconds_left); if (char_from_modem == -1) { /* common_debug_message(common_debug_level_current,"Timeout while waiting for MSB of CRC code."); */ return(0); } crc_msb = char_from_modem; /* common_debug_message_w_no(common_debug_level_current+1,"CRC MSB: ",crc_msb); */ if (time(NULL) > ending_time) { /* common_debug_message(common_debug_level_current,"Timeout after getting MSB of CRC code."); */ return(0); } timeout_seconds_left = ending_time - time(NULL); if (timeout_seconds_left < 0) timeout_seconds_left = 0; char_from_modem = get_char_from_modem_with_timeout(modem_port_no,timeout_seconds_left); if (char_from_modem == -1) { /* common_debug_message(common_debug_level_current,"Timeout while waiting for MSB 2 of CRC code."); */ return(0); } crc_msb2 = char_from_modem; /* common_debug_message_w_no(common_debug_level_current+1,"CRC MSB2:",crc_msb2); */ if (time(NULL) > ending_time) { /* common_debug_message(common_debug_level_current,"Timeout after getting MSB 2 of CRC code."); */ return(0); } timeout_seconds_left = ending_time - time(NULL); if (timeout_seconds_left < 0) timeout_seconds_left = 0; char_from_modem = get_char_from_modem_with_timeout(modem_port_no,timeout_seconds_left); if (char_from_modem == -1) { /* common_debug_message(common_debug_level_current,"Timeout while waiting for LSB 2 of CRC code."); */ return(0); } crc_lsb2 = char_from_modem; /* common_debug_message_w_no(common_debug_level_current+1,"CRC LSB2:",crc_lsb2); */ if (time(NULL) > ending_time) { /* common_debug_message(common_debug_level_current,"Timeout after getting LSB 2 of CRC code."); */ return(0); } timeout_seconds_left = ending_time - time(NULL); if (timeout_seconds_left < 0) timeout_seconds_left = 0; char_from_modem = get_char_from_modem_with_timeout(modem_port_no,timeout_seconds_left); if (char_from_modem == -1) { /* common_debug_message(common_debug_level_current,"Timeout while waiting for LSB of CRC code."); */ return(0); } crc_lsb = char_from_modem; /* common_debug_message_w_no(common_debug_level_current+1,"CRC LSB: ",crc_lsb); */ received_crc = ((crc_msb & 255) << 24) | ((crc_msb2 & 255) << 16) | ((crc_lsb2 & 255) << 8) | (crc_lsb & 255); if (received_crc != computed_crc) { /* common_debug_message(common_debug_level_current,"CRC mismatch."); */ /* common_debug_message_w_no(common_debug_level_current+1,"Computed crc:",computed_crc); */ /* common_debug_message_w_no(common_debug_level_current+1,"Received crc:",received_crc); */ goto sync_byte_loop; /* Give it another chance. */ } return(packet_length); }