/******************************************************************************* OpenAirInterface Copyright(c) 1999 - 2014 Eurecom OpenAirInterface is free software: you can redistribute it and/or modify it under the terms of the GNU General Public License as published by the Free Software Foundation, either version 3 of the License, or (at your option) any later version. OpenAirInterface is distributed in the hope that it will be useful, but WITHOUT ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License for more details. You should have received a copy of the GNU General Public License along with OpenAirInterface.The full GNU General Public License is included in this distribution in the file called "COPYING". If not, see <http://www.gnu.org/licenses/>. Contact Information OpenAirInterface Admin: openair_admin@eurecom.fr OpenAirInterface Tech : openair_tech@eurecom.fr OpenAirInterface Dev : openair4g-devel@eurecom.fr Address : Eurecom, Campus SophiaTech, 450 Route des Chappes, CS 50193 - 06904 Biot Sophia Antipolis cedex, FRANCE *******************************************************************************/ #define MIH_C_INTERFACE #define MIH_C_HEADER_CODEC_C #include "MIH_C_header_codec.h" //----------------------------------------------------------------------------- int MIH_C_HEADER2String(MIH_C_HEADER_T* headerP, char* bufP) { //----------------------------------------------------------------------------- unsigned int buffer_index = 0; buffer_index += sprintf(&bufP[buffer_index], "HEADER.version: "); buffer_index += MIH_C_VERSION2String(&headerP->version, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\nHEADER.ack_req: "); buffer_index += MIH_C_ACK_REQ2String(&headerP->ack_req, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\nHEADER.ack_rsp: "); buffer_index += MIH_C_ACK_RSP2String(&headerP->ack_rsp, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\nHEADER.uir: "); buffer_index += MIH_C_UIR2String(&headerP->uir, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\nHEADER.more_fragment: "); buffer_index += MIH_C_M2String(&headerP->more_fragment, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\nHEADER.fragment_number: "); buffer_index += MIH_C_FN2String(&headerP->more_fragment, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\nHEADER.service_identifier: "); buffer_index += MIH_C_SID2String(&headerP->service_identifier, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\nHEADER.operation_code: "); buffer_index += MIH_C_OPCODE2String(&headerP->operation_code, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\nHEADER.action_identifier: "); buffer_index += MIH_C_AID2String(&headerP->action_identifier, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\nHEADER.transaction_id: "); buffer_index += MIH_C_TRANSACTION_ID2String(&headerP->transaction_id, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\nHEADER.payload_length: "); buffer_index += MIH_C_VARIABLE_PAYLOAD_LENGTH2String(&headerP->payload_length, &bufP[buffer_index]); buffer_index += sprintf(&bufP[buffer_index], "\n"); return buffer_index; } //----------------------------------------------------------------------------- int MIH_C_Link_Header_Encode(Bit_Buffer_t* bbP, MIH_C_HEADER_T* headerP) { //----------------------------------------------------------------------------- u_int8_t reserved = 0; int status ; if ((bbP != NULL) && (headerP != NULL)) { status = MIH_HEADER_ENCODE_OK; BitBuffer_write8b (bbP, headerP->version, 4); BitBuffer_writeBool (bbP, headerP->ack_req); BitBuffer_writeBool (bbP, headerP->ack_rsp); BitBuffer_writeBool (bbP, headerP->uir); BitBuffer_writeBool (bbP, headerP->more_fragment); BitBuffer_write8b (bbP, headerP->fragment_number, 7); BitBuffer_writeBool (bbP, reserved); BitBuffer_write8b (bbP, headerP->service_identifier, 4); BitBuffer_write8b (bbP, headerP->operation_code, 2); BitBuffer_write16b (bbP, headerP->action_identifier, 10); BitBuffer_write8b (bbP, reserved, 4); BitBuffer_write16b (bbP, headerP->transaction_id, 12); BitBuffer_write16 (bbP, headerP->payload_length); /*DEBUG_ENCODE("%s: version 0x%02X\n", __FUNCTION__, headerP->version); DEBUG_ENCODE("%s: ack_req 0x%02X\n", __FUNCTION__, headerP->ack_req); DEBUG_ENCODE("%s: ack_rsp 0x%02X\n", __FUNCTION__, headerP->ack_rsp); DEBUG_ENCODE("%s: uir 0x%02X\n", __FUNCTION__, headerP->uir); DEBUG_ENCODE("%s: more_fragment 0x%02X\n", __FUNCTION__, headerP->more_fragment); DEBUG_ENCODE("%s: reserved 0x%02X\n", __FUNCTION__, reserved); DEBUG_ENCODE("%s: service_identifier 0x%02X\n", __FUNCTION__, headerP->service_identifier); DEBUG_ENCODE("%s: operation_code 0x%02X\n", __FUNCTION__, headerP->operation_code); DEBUG_ENCODE("%s: action_identifier 0x%04X\n", __FUNCTION__, headerP->action_identifier); DEBUG_ENCODE("%s: reserved 0x%02X\n", __FUNCTION__, reserved); DEBUG_ENCODE("%s: transaction_id 0x%04X\n", __FUNCTION__, headerP->transaction_id); DEBUG_ENCODE("%s: payload_length 0x%02X\n", __FUNCTION__, headerP->payload_length);*/ // may be check for validity of header field -> set MIH_HEADER_DECODE_FAILURE if (BitBuffer_isCheckWriteOverflowOK(bbP, 0) == BIT_BUFFER_FALSE) { memset(headerP, 0, sizeof(MIH_C_HEADER_T)); return MIH_HEADER_ENCODE_TOO_SHORT; } else if (status == MIH_HEADER_ENCODE_FAILURE) { memset(headerP, 0, sizeof(MIH_C_HEADER_T)); return MIH_HEADER_ENCODE_FAILURE; } else { return MIH_HEADER_ENCODE_OK; } } else { memset(headerP, 0, sizeof(MIH_C_HEADER_T)); return MIH_HEADER_ENCODE_BAD_PARAMETER; } } //----------------------------------------------------------------------------- int MIH_C_Link_Header_Decode(Bit_Buffer_t* bbP, MIH_C_HEADER_T* headerP) { //----------------------------------------------------------------------------- u_int8_t reserved ; int status ; if ((bbP != NULL) && (headerP != NULL)) { status = MIH_HEADER_DECODE_OK; headerP->version = (MIH_C_VERSION_T)BitBuffer_read(bbP, 4); headerP->ack_req = (MIH_C_ACK_REQ_T)BitBuffer_readBool(bbP); headerP->ack_rsp = (MIH_C_ACK_RSP_T)BitBuffer_readBool(bbP); headerP->uir = (MIH_C_UIR_T)BitBuffer_readBool(bbP); headerP->more_fragment = (MIH_C_M_T)BitBuffer_readBool(bbP); headerP->fragment_number = (MIH_C_FN_T)BitBuffer_read(bbP, 7); reserved = BitBuffer_readBool(bbP); headerP->service_identifier = (MIH_C_SID_T) BitBuffer_read(bbP, 4); headerP->operation_code = (MIH_C_OPCODE_T) BitBuffer_read(bbP, 2); headerP->action_identifier = (MIH_C_AID_T) BitBuffer_read(bbP, 10); reserved = BitBuffer_read(bbP, 4); headerP->transaction_id = (MIH_C_TRANSACTION_ID_T) BitBuffer_read(bbP, 12); headerP->payload_length = (MIH_C_VARIABLE_PAYLOAD_LENGTH_T)BitBuffer_read16(bbP); /*DEBUG_DECODE("%s: version 0x%02X\n", __FUNCTION__, headerP->version); DEBUG_DECODE("%s: ack_req 0x%02X\n", __FUNCTION__, headerP->ack_req); DEBUG_DECODE("%s: ack_rsp 0x%02X\n", __FUNCTION__, headerP->ack_rsp); DEBUG_DECODE("%s: uir 0x%02X\n", __FUNCTION__, headerP->uir); DEBUG_DECODE("%s: more_fragment 0x%02X\n", __FUNCTION__, headerP->more_fragment); DEBUG_DECODE("%s: reserved 0x%02X\n", __FUNCTION__, reserved); DEBUG_DECODE("%s: service_identifier 0x%02X\n", __FUNCTION__, headerP->service_identifier); DEBUG_DECODE("%s: operation_code 0x%02X\n", __FUNCTION__, headerP->operation_code); DEBUG_DECODE("%s: action_identifier 0x%04X\n", __FUNCTION__, headerP->action_identifier); DEBUG_DECODE("%s: reserved 0x%02X\n", __FUNCTION__, reserved); DEBUG_DECODE("%s: transaction_id 0x%04X\n", __FUNCTION__, headerP->transaction_id); DEBUG_DECODE("%s: payload_length 0x%02X\n", __FUNCTION__, headerP->payload_length);*/ // may be check for validity of header field -> set MIH_HEADER_DECODE_FAILURE if (BitBuffer_isCheckReadOverflowOK(bbP, 0) == BIT_BUFFER_FALSE) { memset(headerP, 0, sizeof(MIH_C_HEADER_T)); return MIH_HEADER_DECODE_TOO_SHORT; } else if (status == MIH_HEADER_DECODE_FAILURE) { memset(headerP, 0, sizeof(MIH_C_HEADER_T)); return MIH_HEADER_DECODE_FAILURE; } else { return MIH_HEADER_DECODE_OK; } } else { memset(headerP, 0, sizeof(MIH_C_HEADER_T)); return MIH_HEADER_DECODE_BAD_PARAMETER; } }