FreeCalypso > hg > fc-tourmaline
diff src/g23m-fad/t30/t30_bcsf.c @ 1:fa8dc04885d8
src/g23m-*: import from Magnetite
author | Mychaela Falconia <falcon@freecalypso.org> |
---|---|
date | Fri, 16 Oct 2020 06:25:50 +0000 |
parents | |
children |
line wrap: on
line diff
--- /dev/null Thu Jan 01 00:00:00 1970 +0000 +++ b/src/g23m-fad/t30/t30_bcsf.c Fri Oct 16 06:25:50 2020 +0000 @@ -0,0 +1,819 @@ +/* ++----------------------------------------------------------------------------- +| Project : GSM-F&D (8411) +| Modul : t30_bcsf ++----------------------------------------------------------------------------- +| Copyright 2002 Texas Instruments Berlin, AG +| All rights reserved. +| +| This file is confidential and a trade secret of Texas +| Instruments Berlin, AG +| The receipt of or possession of this file does not convey +| any rights to reproduce or disclose its contents or to +| manufacture, use, or sell anything it may describe, in +| whole, or in part, without the specific written consent of +| Texas Instruments Berlin, AG. ++----------------------------------------------------------------------------- +| Purpose : This Modul defines the procedures and functions for +| the component T30 of the mobile station ++----------------------------------------------------------------------------- +*/ + +#ifndef T30_BCSF_C +#define T30_BCSF_C +#endif + +#define ENTITY_T30 + +/*==== INCLUDES ===================================================*/ + +#include <string.h> +#include <stdlib.h> +#include <stddef.h> +#include "typedefs.h" +#include "pcm.h" +#include "vsi.h" +#include "macdef.h" +#include "pconst.cdg" +#include "mconst.cdg" +#include "message.h" +#include "ccdapi.h" +#include "custom.h" +#include "gsm.h" +#include "prim.h" +#include "cnf_t30.h" +#include "mon_t30.h" +#include "pei.h" +#include "tok.h" +#include "dti.h" /* functionality of the dti library */ +#include "t30.h" + +/*==== CONST =======================================================*/ + +/*==== TYPES =======================================================*/ + +/*==== VAR EXPORT ==================================================*/ + +/*==== VAR LOCAL ===================================================*/ + + +LOCAL const USHORT crctab[256] = +{ + 0x0000, 0x1021, 0x2042, 0x3063, 0x4084, 0x50A5, 0x60C6, 0x70E7, + 0x8108, 0x9129, 0xA14A, 0xB16B, 0xC18C, 0xD1AD, 0xE1CE, 0xF1EF, + 0x1231, 0x0210, 0x3273, 0x2252, 0x52B5, 0x4294, 0x72F7, 0x62D6, + 0x9339, 0x8318, 0xB37B, 0xA35A, 0xD3BD, 0xC39C, 0xF3FF, 0xE3DE, + 0x2462, 0x3443, 0x0420, 0x1401, 0x64E6, 0x74C7, 0x44A4, 0x5485, + 0xA56A, 0xB54B, 0x8528, 0x9509, 0xE5EE, 0xF5CF, 0xC5AC, 0xD58D, + 0x3653, 0x2672, 0x1611, 0x0630, 0x76D7, 0x66F6, 0x5695, 0x46B4, + 0xB75B, 0xA77A, 0x9719, 0x8738, 0xF7DF, 0xE7FE, 0xD79D, 0xC7BC, + 0x48C4, 0x58E5, 0x6886, 0x78A7, 0x0840, 0x1861, 0x2802, 0x3823, + 0xC9CC, 0xD9ED, 0xE98E, 0xF9AF, 0x8948, 0x9969, 0xA90A, 0xB92B, + 0x5AF5, 0x4AD4, 0x7AB7, 0x6A96, 0x1A71, 0x0A50, 0x3A33, 0x2A12, + 0xDBFD, 0xCBDC, 0xFBBF, 0xEB9E, 0x9B79, 0x8B58, 0xBB3B, 0xAB1A, + 0x6CA6, 0x7C87, 0x4CE4, 0x5CC5, 0x2C22, 0x3C03, 0x0C60, 0x1C41, + 0xEDAE, 0xFD8F, 0xCDEC, 0xDDCD, 0xAD2A, 0xBD0B, 0x8D68, 0x9D49, + 0x7E97, 0x6EB6, 0x5ED5, 0x4EF4, 0x3E13, 0x2E32, 0x1E51, 0x0E70, + 0xFF9F, 0xEFBE, 0xDFDD, 0xCFFC, 0xBF1B, 0xAF3A, 0x9F59, 0x8F78, + 0x9188, 0x81A9, 0xB1CA, 0xA1EB, 0xD10C, 0xC12D, 0xF14E, 0xE16F, + 0x1080, 0x00A1, 0x30C2, 0x20E3, 0x5004, 0x4025, 0x7046, 0x6067, + 0x83B9, 0x9398, 0xA3FB, 0xB3DA, 0xC33D, 0xD31C, 0xE37F, 0xF35E, + 0x02B1, 0x1290, 0x22F3, 0x32D2, 0x4235, 0x5214, 0x6277, 0x7256, + 0xB5EA, 0xA5CB, 0x95A8, 0x8589, 0xF56E, 0xE54F, 0xD52C, 0xC50D, + 0x34E2, 0x24C3, 0x14A0, 0x0481, 0x7466, 0x6447, 0x5424, 0x4405, + 0xA7DB, 0xB7FA, 0x8799, 0x97B8, 0xE75F, 0xF77E, 0xC71D, 0xD73C, + 0x26D3, 0x36F2, 0x0691, 0x16B0, 0x6657, 0x7676, 0x4615, 0x5634, + 0xD94C, 0xC96D, 0xF90E, 0xE92F, 0x99C8, 0x89E9, 0xB98A, 0xA9AB, + 0x5844, 0x4865, 0x7806, 0x6827, 0x18C0, 0x08E1, 0x3882, 0x28A3, + 0xCB7D, 0xDB5C, 0xEB3F, 0xFB1E, 0x8BF9, 0x9BD8, 0xABBB, 0xBB9A, + 0x4A75, 0x5A54, 0x6A37, 0x7A16, 0x0AF1, 0x1AD0, 0x2AB3, 0x3A92, + 0xFD2E, 0xED0F, 0xDD6C, 0xCD4D, 0xBDAA, 0xAD8B, 0x9DE8, 0x8DC9, + 0x7C26, 0x6C07, 0x5C64, 0x4C45, 0x3CA2, 0x2C83, 0x1CE0, 0x0CC1, + 0xEF1F, 0xFF3E, 0xCF5D, 0xDF7C, 0xAF9B, 0xBFBA, 0x8FD9, 0x9FF8, + 0x6E17, 0x7E36, 0x4E55, 0x5E74, 0x2E93, 0x3EB2, 0x0ED1, 0x1EF0 +}; + +/*==== FUNCTIONS ===================================================*/ + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_build_report | ++--------------------------------------------------------------------+ + + PURPOSE : build the T30_REPORT_IND primitive out of a send/rec. frame + +*/ + +LOCAL void bcs_build_report(UBYTE *frame, USHORT len, T_T30_REPORT_IND *t30_report_ind) +{ + if (t30_data->bitorder & FBO_REV_STATUS) /* reverse the bitorder of each byte */ + { + memcpy(t30_report_ind->sdu.buf, frame, len); + } + else + { + USHORT i; + for (i=0; i<len; i++) + t30_report_ind->sdu.buf[i] = BIT_MIRROR[frame[i]]; + } + + t30_report_ind->sdu.l_buf = (len << 3); + t30_report_ind->sdu.o_buf = 0; +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_init | ++--------------------------------------------------------------------+ + + PURPOSE : initialize BCS formatter + +*/ + +GLOBAL void bcs_init(T_T30_DATA *pt30_data) +{ + TRACE_FUNCTION ("bcs_init()"); + memset (pt30_data->bcs_frm, 0, BCS_FRM_SIZE); +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_check_frames | ++--------------------------------------------------------------------+ + + PURPOSE : This function checks the final flag and the frame checking sequence. +*/ + +LOCAL UBYTE bcs_check_frames(UBYTE *idx_max) +{ + + T_sdu *sdu = (T_sdu*)t30_data->bcs_frm; + UBYTE idx; + + for (idx = 0; idx < *idx_max; idx++) + { +#ifdef _SIMULATION_ /* FCS generating/checking off */ + if (t30_data->test_mode & TST_FCS) + { + } + else +#endif + { + USHORT crctt = 0xffff; /* initialize crc */ + + /* shift each bit through polynomial */ + USHORT pos; + for (pos = t30_data->frm[idx].beg; pos <= t30_data->frm[idx].end; pos++) + { + SHORT tmp = (crctt >> 8) ^ sdu->buf[pos]; + crctt = ((crctt << 8) ^ crctab[tmp & 0xff]) & 0xffff; + } + if (crctt NEQ 0x1D0F) /* check remainder */ + return CHK_FCS_ERR; + } +#if defined _SIMULATION_ || defined KER_DEBUG_BCS + ker_debug ("BCS_DATA_IND", (UBYTE*)&sdu->buf[t30_data->frm[idx].beg], (USHORT)(t30_data->frm[idx].end-t30_data->frm[idx].beg)); +#endif + /* count final flags */ + if (sdu->buf[t30_data->frm[idx].beg + 1] & 0x08) + { + *idx_max = (UBYTE)idx + 1; + return CHK_OK; + } + } +#ifdef _SIMULATION_ /* Control checking OFF */ + if (t30_data->test_mode & TST_CTRL) + return CHK_OK; +#endif + return CHK_FIN_ERR; +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_frame_pos | ++--------------------------------------------------------------------+ + + PURPOSE : This function extracts + the beginning, the end and the length of each frame. +*/ + +LOCAL UBYTE bcs_frame_pos(UBYTE *flag_vector, UBYTE *idx_max) +{ + USHORT idx = 0; + T_sdu *sdu = (T_sdu*)t30_data->bcs_frm; + + *idx_max = 0; + while (idx < sdu->l_buf) + { + /* skip flags */ + while (idx < sdu->l_buf AND flag_vector[idx]) + idx++; + + /* ready if last byte is a flag */ + if (idx EQ sdu->l_buf) + return FRM_OK; + + /* save begin of frame */ + t30_data->frm[*idx_max].beg = idx; + + /* search flag */ + while (idx < sdu->l_buf AND !flag_vector[idx]) + idx++; + + /* error if no flag found */ + if (idx EQ sdu->l_buf) + { + t30_data->frm[*idx_max].beg = 0; + return FRM_OK; /* return FRM_ERR_NO_FLAG; ??? */ + } + + /* save end of fame and length of frame */ + t30_data->frm[*idx_max].end = idx - 1; + t30_data->frm[*idx_max].len = idx - t30_data->frm[*idx_max].beg; + + /* error if too many frames received */ + if (++(*idx_max) EQ FRAMES_MAX) + return FRM_ERR_TOO_MANY_FRAMES; + + /* next frame */ + idx++; + } + return FRM_OK; +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_report_rcv | ++--------------------------------------------------------------------+ + + PURPOSE : This function reports the received HDLC frames to MMI + if desired. +*/ + +LOCAL void bcs_report_rcv(UBYTE idx_max) +{ + T_sdu *sdu = (T_sdu*)t30_data->bcs_frm; + USHORT idx; + + for (idx = 0 ; idx < idx_max ; idx++) + { + if (t30_data->frm[idx].len >= 2) + { + PALLOC_SDU (t30_report_ind, T30_REPORT_IND, REPORT_SIZE_BITS); + bcs_build_report (&sdu->buf[t30_data->frm[idx].beg], (USHORT)(t30_data->frm[idx].len - 2), t30_report_ind); + t30_report_ind->dir = DIR_RCV; + PSENDX (MMI, t30_report_ind); + } + } +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_decode | ++--------------------------------------------------------------------+ + + PURPOSE : This function decodes each hdlc frame and sends the + decoded data to the kernel. +*/ + +/* this function is only necessary because of an iarm compiler failure */ +LOCAL void bcs_clear_flag (UBYTE *ptr) +{ + if (*ptr & 0x70) + *ptr &= 0x7F; +} + +LOCAL UBYTE bcs_decode(UBYTE idx_max) +{ + T_sdu *sdu = (T_sdu*)t30_data->bcs_frm; + UBYTE idx; + + for (idx = 0; idx < idx_max; idx++) + { + USHORT begin = t30_data->frm[idx].beg + 2; + + /* set direction flag to zero for CCD decoding */ + bcs_clear_flag (sdu->buf + begin); + + /* set offset and length of current frame */ + sdu->o_buf = begin << 3; + sdu->l_buf = ((USHORT)(t30_data->frm[idx].len - 4) << 3); + +#ifdef _SIMULATION_ /* show contents of buffer */ + if (t30_data->test_mode /* & TST_BUF */) + { + ker_debug ("ccd_decode", &sdu->buf[begin], (USHORT)(sdu->l_buf >> 3)); + } +#endif + + if (ccd_decodeMsg(CCDENT_T30, DOWNLINK, (T_MSGBUF*)sdu, _decodedMsg, HDLC_ADDR) EQ ccdError) + { + TRACE_EVENT ("ERROR: ccd_decode"); + return CCD_ERR; + } + sig_bcs_ker_bdat_ind(); /* send signal to kernel */ + } + return CCD_OK; +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_destuff | ++--------------------------------------------------------------------+ + + PURPOSE : This function de-stuffs the received BCS data. +*/ + +LOCAL void bcs_destuff(UBYTE *flag_vector) +{ + T_sdu *sdu = (T_sdu*)t30_data->bcs_frm; + SHORT bcs_tmp_len = 0; + SHORT ones = 0; + SHORT bits = 8; + UBYTE flag = 0; + UBYTE *bcs_tmp; + SHORT i; + +#ifdef _SIMULATION_ /* bit stuffing/destuffing OFF */ + if (t30_data->test_mode & TST_STUFF) + { + for (i = 0; i < sdu->l_buf; i++) + { + if (sdu->buf[i] EQ HDLC_FLAG) + flag_vector[i] = 1; + } + if (flag_vector[sdu->l_buf-1] NEQ 1) // trailing HDLC_FLAG is missed + { + sdu->l_buf++; + sdu->buf[sdu->l_buf-1] = HDLC_FLAG; + flag_vector[sdu->l_buf-1] = 1; + } + return; + } +#endif + + MALLOC(bcs_tmp, sdu->l_buf); + + for (i = 0 ; i < sdu->l_buf ; i++) + { + UBYTE bit_ptr = 0x80; /* points initially to MSB */ + + do /* check each byte for destuffing */ + { + if (sdu->buf[i] & bit_ptr) /* bit pointed to is 1 */ + { + ones++; + bcs_tmp[bcs_tmp_len] = (bcs_tmp[bcs_tmp_len] << 1) | 1; + flag = (flag << 1) | 1; + + if (! --bits) /* counter of byte's bits*/ + { + bcs_tmp_len++; + bits = 8; + } + } + else /* bit is 0 */ + { + if (ones != 5) + { + bcs_tmp[bcs_tmp_len] <<= 1; + flag <<= 1; + + if (ones EQ 6 && flag EQ HDLC_FLAG) + flag_vector[bcs_tmp_len] = 1; + + if (! --bits) /* whole byte is scanned */ + { + bcs_tmp_len++; + bits = 8; + } + } + ones = 0; + } + bit_ptr >>= 1; + } + while (bit_ptr); + } + /* copy destuffed BCS frame back to sdu */ + memcpy (sdu->buf, bcs_tmp, bcs_tmp_len); + MFREE(bcs_tmp); + + sdu->l_buf = bcs_tmp_len; /* adjust buffer length */ + if (flag_vector[sdu->l_buf-1] NEQ 1) // trailing HDLC_FLAG is missed + { + sdu->l_buf++; + sdu->buf[sdu->l_buf-1] = HDLC_FLAG; + flag_vector[sdu->l_buf-1] = 1; + } +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_bcs_decode | ++--------------------------------------------------------------------+ + + PURPOSE : This function gets the frame positions, + checks the frames, + reports the contents to MMI if desired, + decodes the contents and sends the contents to the kernel. +*/ + +GLOBAL void bcs_bcs_decode(void) +{ + UBYTE *flag_vector, idx_max, ret; + + MALLOC(flag_vector, BCS_FRM_SIZE); + memset(flag_vector, 0, BCS_FRM_SIZE); + bcs_destuff(flag_vector); + ret = bcs_frame_pos(flag_vector, &idx_max); /* determines "idx_max" */ + MFREE(flag_vector); + + switch (ret) + { + case FRM_OK: + ret = bcs_check_frames(&idx_max); + if (t30_data->hdlc_report) + { + bcs_report_rcv(idx_max); + } + switch (ret) + { + case CHK_OK: + switch (bcs_decode(idx_max)) + { + case CCD_OK: + return; + + case CCD_ERR: + sig_bcs_ker_err_ind(ERR_CCD_DEC); + return; + } + break; /* dummy */ + + case CHK_FCS_ERR: + sig_bcs_ker_err_ind(ERR_FCS); + return; + + case CHK_FIN_ERR: + sig_bcs_ker_err_ind(ERR_FINAL); + return; + } + break; + + case FRM_ERR_NO_FLAG: + sig_bcs_ker_err_ind(ERR_FRAME_NO_FLAG); + return; + + case FRM_ERR_TOO_MANY_FRAMES: + sig_bcs_ker_err_ind(ERR_FRAME_TOO_MANY_FRAMES); + return; + } +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_report_snd | ++--------------------------------------------------------------------+ + + PURPOSE : This function reports the sent HDLC frames to MMI + if desired. +*/ + +LOCAL void bcs_report_snd(void) +{ + T_sdu *BCI_stream = (T_sdu*)t30_data->BCI_stream; // Binary Coded Information + + PALLOC_SDU(t30_report_ind, T30_REPORT_IND, REPORT_SIZE_BITS); + + bcs_build_report(&BCI_stream->buf[0], (USHORT)((BCI_stream->l_buf >> 3) + 2), t30_report_ind); + t30_report_ind->dir = DIR_SND; + PSENDX (MMI, t30_report_ind); +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_fcs_gen | ++--------------------------------------------------------------------+ + + PURPOSE : This function generates the frame checking sequence + for one HDLC frame. +*/ + +LOCAL void bcs_fcs_gen (void) +{ + T_sdu *sdu = (T_sdu*)t30_data->BCI_stream; + USHORT end = (sdu->l_buf >> 3) + 2; + USHORT pos; + UBYTE i; + +#ifdef _SIMULATION_ /* FCS generating/checking OFF */ + if (t30_data->test_mode & TST_FCS) + { + pos = end; + sdu->buf[pos++] = 0x12; + sdu->buf[pos++] = 0xEF; + } + else +#endif + { + USHORT crctt = 0xffff; + for (pos = 0; pos < end; pos++) + { + SHORT tmp = (crctt >> 8) ^ sdu->buf[pos]; + crctt = ((crctt << 8) ^ crctab[tmp & 0xff]) & 0xffff; + } + sdu->buf[pos++] = (~(crctt & 0xffff) & 0xffff) >> 8;/*lint !e661 !e662 (Warning -- Possible access/creation of out-of-bounds pointer)*/ + sdu->buf[pos++] = (~(crctt & 0xffff) & 0xff);/*lint !e661 !e662 (Warning -- Possible access/creation of out-of-bounds pointer)*/ + } + + sdu->l_buf += 32; /* 4 bytes more */ + + for (i = 0; i < HDLC_FLAGS; i++) + { + sdu->buf[pos++] = HDLC_FLAG;/*lint !e661 !e662 (Warning -- Possible access/creation of out-of-bounds pointer)*/ + sdu->l_buf += 8; + } + sdu->o_buf = 0; +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_stuff | ++--------------------------------------------------------------------+ + + PURPOSE : This function stuffs the BCS data. +*/ + +LOCAL void bcs_stuff (UBYTE final) +{ + T_sdu *sdu_inp = (T_sdu*)t30_data->BCI_stream; + T_sdu *sdu_out = &t30_data->fad_data_req->sdu; + + UBYTE *buf_in = sdu_inp->buf; + USHORT len_in = sdu_inp->l_buf >> 3; + UBYTE *buf_out; + USHORT len_out = sdu_out->l_buf >> 3; + USHORT i; + +#ifdef _SIMULATION_ /* bit stuffing/destuffing OFF */ + if (t30_data->test_mode & TST_STUFF) + { + buf_out = &sdu_out->buf[len_out]; + memcpy (buf_out, buf_in, len_in); + sdu_out->l_buf = (len_out + len_in) << 3; + return; + } +#endif + + buf_out = sdu_out->buf; + + for (i = 0; i < len_in; i++) + { + USHORT bit_ptr = 0x80; + UBYTE stuff = 1; + /* + check HDLC_FLAGS + */ + if (buf_in[i] EQ HDLC_FLAG) + { + USHORT k; + for (k = 0; k < HDLC_FLAGS; k++) + { + if (i EQ len_in - k - 1) + { + stuff = 0; + break; + } + } + } + do + { + switch (buf_in[i] & bit_ptr) + { + default: + buf_out[len_out] = (buf_out[len_out] << 1) | 1; + if (! --t30_data->stuff_bits) + { + len_out++; + t30_data->stuff_bits = 8; + } + if (!stuff) + { + t30_data->stuff_ones = 0; + break; + } + if (++t30_data->stuff_ones != 5) + break; + /* + * otherwise fall through + */ + + case 0: + buf_out[len_out] <<= 1; + t30_data->stuff_ones = 0; + + if (! --t30_data->stuff_bits) + { + len_out++; + t30_data->stuff_bits = 8; + } + break; + } + bit_ptr >>= 1; + } while (bit_ptr); + } + + if (final EQ FINAL_YES AND t30_data->stuff_bits NEQ 8) + { + buf_out[len_out] <<= t30_data->stuff_bits; + len_out++; + } + + sdu_out->l_buf = len_out << 3; + + if (final EQ FINAL_YES) + { + t30_data->stuff_ones = 0; + t30_data->stuff_bits = 8; + } +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_bcs_encode | ++--------------------------------------------------------------------+ + + PURPOSE : This function encodes the HDLC frames, + reports the HDLC frames to MMI if desired, + generates the frame checking sequence and stuffs the bits. +*/ + +GLOBAL void bcs_bcs_encode(UBYTE ctrl, UBYTE final) +{ + T_sdu *sdu = (T_sdu*)t30_data->BCI_stream; + + switch (sdu->buf[2])/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + { + case BCS_DIS: + TRACE_EVENT ("Send BCS_DIS"); + break; + case BCS_CSI: + TRACE_EVENT ("Send BCS_CSI"); + break; + case BCS_NSF: + TRACE_EVENT ("Send BCS_NSF"); + break; + case BCS_DTC: + TRACE_EVENT ("Send BCS_DTC"); + break; + case BCS_CIG: + TRACE_EVENT ("Send BCS_CIG"); + break; + case BCS_NSC: + TRACE_EVENT ("Send BCS_NSC"); + break; + case BCS_PWD_POLL: + TRACE_EVENT ("Send BCS_PWD_POLL"); + break; + case BCS_SEP: + TRACE_EVENT ("Send BCS_SEP"); + break; + + case BCS_CFR: + TRACE_EVENT ("Send BCS_CFR"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_CRP: + TRACE_EVENT ("Send BCS_CRP"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_DCN: + TRACE_EVENT ("Send BCS_DCN"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_DCS: + TRACE_EVENT ("Send BCS_DCS"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_EOM: + TRACE_EVENT ("Send BCS_EOM"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_EOP: + TRACE_EVENT ("Send BCS_EOP"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_FTT: + TRACE_EVENT ("Send BCS_FTT"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_MCF: + TRACE_EVENT ("Send BCS_MCF"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_MPS: + TRACE_EVENT ("Send BCS_MPS"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_NSS: + TRACE_EVENT ("Send BCS_NSS"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_PIN: + TRACE_EVENT ("Send BCS_PIN"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_PIP: + TRACE_EVENT ("Send BCS_PIP"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_PRI_EOM: + TRACE_EVENT ("Send BCS_PRI_EOM"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_PRI_EOP: + TRACE_EVENT ("Send BCS_PRI_EOP"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_PRI_MPS: + TRACE_EVENT ("Send BCS_PRI_MPS"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_PWD_SND: + TRACE_EVENT ("Send BCS_PWD_SND"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_RTN: + TRACE_EVENT ("Send BCS_RTN"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_RTP: + TRACE_EVENT ("Send BCS_RTP"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_SUB: + TRACE_EVENT ("Send BCS_SUB"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + case BCS_TSI: + TRACE_EVENT ("Send BCS_TSI"); + sdu->buf[2] |= t30_data->dir;/*lint !e415 !e416 (Warning -- access/creation of out-of-bounds pointer)*/ + break; + } + + sdu->buf[0] = HDLC_ADDR; + sdu->buf[1] = ctrl;/*lint !e415 (Warning -- access of out-of-bounds pointer)*/ + + if (t30_data->hdlc_report) + { + bcs_report_snd(); + } + bcs_fcs_gen(); + bcs_stuff(final); +} + +/* ++--------------------------------------------------------------------+ +| PROJECT : GSM-F&D (8411) MODULE : T30_BCSF | +| STATE : code ROUTINE : bcs_fill_bcs_frm | ++--------------------------------------------------------------------+ + + PURPOSE : This function checks if the BCS frame buffer has enough + space to append the received data. + If there is enough space the data is appended. + If not than BCS_FRM_FULL is returned. + +*/ + +GLOBAL UBYTE bcs_fill_bcs_frm (T_FAD_DATA_IND *fad_data_ind) +{ + USHORT data_len = fad_data_ind->sdu.l_buf >> 3; + T_sdu *sdu = (T_sdu*)t30_data->bcs_frm; + + TRACE_FUNCTION("bcs_fill_bcs_frm()"); + + if (sdu->l_buf + data_len < BCS_FRM_SIZE) + { + memcpy (&sdu->buf[sdu->l_buf], fad_data_ind->sdu.buf, data_len); + sdu->l_buf += data_len; + return ((fad_data_ind->final) ? BCS_FRM_FILLED : BCS_FRM_FILLING); + } + else + { + sdu->l_buf = BCS_FRM_SIZE; + return (BCS_FRM_FULL); + } +} +