
/*
 *
  Copyright (c) Eicon Networks, 2002.
 *
  This source file is supplied for the use with
  Eicon Networks range of DIVA Server Adapters.
 *
  Eicon File Revision :    2.1
 *
  This program 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 2, or (at your option)
  any later version.
 *
  This program is distributed in the hope that it will be useful,
  but WITHOUT ANY WARRANTY OF ANY KIND WHATSOEVER INCLUDING ANY
  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 this program; if not, write to the Free Software
  Foundation, Inc., 675 Mass Ave, Cambridge, MA 02139, USA.
 *
 */





#include "platform.h"
#include "di_defs.h"
#include "pc.h"
#include "capi20.h"
#include "divacapi.h"
#include "mdm_msg.h"
#include "divasync.h"



#define FILE_ "MESSAGE.C"
#define dprintf









/*------------------------------------------------------------------*/
/* This is options supported for all adapters that are server by    */
/* XDI driver. Allo it is not necessary to ask it from every adapter*/
/* and it is not necessary to save it separate for every adapter    */
/* Macrose defined here have only local meaning                     */
/*------------------------------------------------------------------*/
static dword diva_xdi_extended_features = 0;

#define DIVA_CAPI_USE_CMA                 0x00000001
#define DIVA_CAPI_XDI_PROVIDES_SDRAM_BAR  0x00000002
#define DIVA_CAPI_XDI_PROVIDES_NO_CANCEL  0x00000004
#define DIVA_CAPI_XDI_PROVIDES_RX_DMA     0x00000008

/*
  CAPI can request to process all return codes self only if:
  protocol code supports this && xdi supports this
 */
#define DIVA_CAPI_SUPPORTS_NO_CANCEL(__a__)   (((__a__)->manufacturer_features&MANUFACTURER_FEATURE_XONOFF_FLOW_CONTROL)&&    ((__a__)->manufacturer_features & MANUFACTURER_FEATURE_OK_FC_LABEL) &&     (diva_xdi_extended_features   & DIVA_CAPI_XDI_PROVIDES_NO_CANCEL))

/*------------------------------------------------------------------*/
/* local function prototypes                                        */
/*------------------------------------------------------------------*/

static void group_optimization(DIVA_CAPI_ADAPTER   * a, PLCI   * plci);
static void set_group_ind_mask (PLCI   *plci);
static void clear_group_ind_mask_bit (PLCI   *plci, word b);
static byte test_group_ind_mask_bit (PLCI   *plci, word b);
void AutomaticLaw(DIVA_CAPI_ADAPTER   *);
word CapiRelease(word);
word CapiRegister(word);
word api_put(APPL   *, CAPI_MSG   *);
static word api_parse(byte   *, word, byte *, API_PARSE *);
static void api_save_msg(API_PARSE   *in, byte *format, API_SAVE   *out);
static void api_load_msg(API_SAVE   *in, API_PARSE   *out);

word api_remove_start(void);
void api_remove_complete(void);

static void plci_remove(PLCI   *);
static void diva_get_extended_adapter_features (DIVA_CAPI_ADAPTER  * a);
static void diva_ask_for_xdi_sdram_bar (DIVA_CAPI_ADAPTER  *, IDI_SYNC_REQ  *);

void   callback(ENTITY   *);

static void control_rc(PLCI   *, byte, byte, byte, byte, byte);
static void data_rc(PLCI   *, byte);
static void data_ack(PLCI   *, byte);
static void sig_ind(PLCI   *);
static void SendInfo(PLCI   *, dword, byte   * *, byte);
static void SendSetupInfo(APPL   *, PLCI   *, dword, byte   * *, byte);
static void SendSSExtInd(APPL   *, PLCI   * plci, dword Id, byte   * * parms);

static void VSwitchReqInd(PLCI   *plci, dword Id, byte   **parms);

static void nl_ind(PLCI   *);

static byte connect_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte connect_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte connect_a_res(dword,word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte disconnect_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte disconnect_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte listen_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte info_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte info_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte alert_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte facility_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte facility_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte connect_b3_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte connect_b3_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte connect_b3_a_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte disconnect_b3_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte disconnect_b3_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte data_b3_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte data_b3_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte reset_b3_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte reset_b3_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte connect_b3_t90_a_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte select_b_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte manufacturer_req(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
static byte manufacturer_res(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);

static word get_plci(DIVA_CAPI_ADAPTER   *);
static void add_p(PLCI   *, byte, byte   *);
static void add_s(PLCI   * plci, byte code, API_PARSE * p);
static void add_ss(PLCI   * plci, byte code, API_PARSE * p);
static void add_ie(PLCI   * plci, byte code, byte   * p, word p_length);
static void add_d(PLCI   *, word, byte   *);
static void add_ai(PLCI   *, API_PARSE *);
static word add_b1(PLCI   *, API_PARSE *, word, word);
static word add_b23(PLCI   *, API_PARSE *);
static word add_modem_b23 (PLCI  * plci, API_PARSE* bp_parms);
static void sig_req(PLCI   *, byte, byte);
static void nl_req_ncci(PLCI   *, byte, byte);
static void send_req(PLCI   *);
static void send_data(PLCI   *);
static word plci_remove_check(PLCI   *);
static void listen_check(DIVA_CAPI_ADAPTER   *);
static byte AddInfo(byte   **, byte   **, byte   *, byte *);
static byte getChannel(API_PARSE *);
static void IndParse(PLCI   *, word *, byte   **, byte);
static byte ie_compare(byte   *, byte *);
static word find_cip(DIVA_CAPI_ADAPTER   *, byte   *, byte   *);
static word CPN_filter_ok(byte   *cpn,DIVA_CAPI_ADAPTER   *,word);

/*
  XON protocol helpers
  */
static void channel_flow_control_remove (PLCI   * plci);
static void channel_x_off (PLCI   * plci, byte ch, byte flag);
static void channel_x_on (PLCI   * plci, byte ch);
static void channel_request_xon (PLCI   * plci, byte ch);
static void channel_xmit_xon (PLCI   * plci);
static int channel_can_xon (PLCI   * plci, byte ch);
static void channel_xmit_extended_xon (PLCI   * plci);

static byte SendMultiIE(PLCI   * plci, dword Id, byte   * * parms, byte ie_type, dword info_mask, byte setupParse);
static word AdvCodecSupport(DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, byte);
static void CodecIdCheck(DIVA_CAPI_ADAPTER   *, PLCI   *);
static void SetVoiceChannel(PLCI   *, byte   *, DIVA_CAPI_ADAPTER   * );
static void VoiceChannelOff(PLCI   *plci);
static void adv_voice_write_coefs (PLCI   *plci, word write_command);
static void adv_voice_clear_config (PLCI   *plci);

static word get_b1_facilities (PLCI   * plci, byte b1_resource);
static byte add_b1_facilities (PLCI   * plci, byte b1_resource, word b1_facilities);
static void adjust_b1_facilities (PLCI   *plci, byte new_b1_resource, word new_b1_facilities);
static word adjust_b_process (dword Id, PLCI   *plci, byte Rc);
static void adjust_b1_resource (dword Id, PLCI   *plci, API_SAVE   *bp_msg, word b1_facilities, word internal_command);
static void adjust_b_restore (dword Id, PLCI   *plci, byte Rc);
static void reset_b3_command (dword Id, PLCI   *plci, byte Rc);
static void select_b_command (dword Id, PLCI   *plci, byte Rc);
static void fax_connect_ack_command (dword Id, PLCI   *plci, byte Rc);
static void fax_edata_ack_command (dword Id, PLCI   *plci, byte Rc);
static void fax_connect_info_command (dword Id, PLCI   *plci, byte Rc);
static void fax_adjust_b23_command (dword Id, PLCI   *plci, byte Rc);
static void fax_disconnect_command (dword Id, PLCI   *plci, byte Rc);
static void hold_save_command (dword Id, PLCI   *plci, byte Rc);
static void retrieve_restore_command (dword Id, PLCI   *plci, byte Rc);
static void init_b1_config (PLCI   *plci);
static void clear_b1_config (PLCI   *plci);

static void dtmf_command (dword Id, PLCI   *plci, byte Rc);
static byte dtmf_request (dword Id, word Number, DIVA_CAPI_ADAPTER   *a, PLCI   *plci, APPL   *appl, API_PARSE *msg);
static void dtmf_confirmation (dword Id, PLCI   *plci);
static void dtmf_indication (dword Id, PLCI   *plci, byte   *msg, word length);
static void dtmf_parameter_write (PLCI   *plci);


static void mixer_set_bchannel_id_esc (PLCI   *plci, byte bchannel_id);
static void mixer_set_bchannel_id (PLCI   *plci, byte   *chi);
static void mixer_clear_config (PLCI   *plci);
static void mixer_notify_update (PLCI   *plci, byte others);
static void mixer_command (dword Id, PLCI   *plci, byte Rc);
static byte mixer_request (dword Id, word Number, DIVA_CAPI_ADAPTER   *a, PLCI   *plci, APPL   *appl, API_PARSE *msg);
static void mixer_indication_coefs_set (dword Id, PLCI   *plci);
static void mixer_indication_xconnect_from (dword Id, PLCI   *plci, byte   *msg, word length);
static void mixer_indication_xconnect_to (dword Id, PLCI   *plci, byte   *msg, word length);
static void mixer_remove (PLCI   *plci);


static void ec_command (dword Id, PLCI   *plci, byte Rc);
static byte ec_request (dword Id, word Number, DIVA_CAPI_ADAPTER   *a, PLCI   *plci, APPL   *appl, API_PARSE *msg);
static void ec_indication (dword Id, PLCI   *plci, byte   *msg, word length);


static void rtp_connect_b3_req_command (dword Id, PLCI   *plci, byte Rc);
static void rtp_connect_b3_res_command (dword Id, PLCI   *plci, byte Rc);


static int  diva_get_dma_descriptor  (PLCI   *plci, dword   *dma_magic);
static void diva_free_dma_descriptor (PLCI   *plci, int nr);

/*------------------------------------------------------------------*/
/* external function prototypes                                     */
/*------------------------------------------------------------------*/

extern byte MapController (byte);
extern byte UnMapController (byte);
#define MapId(Id) (((Id) & 0xffffff00L) | MapController ((byte)(Id)))
#define UnMapId(Id) (((Id) & 0xffffff00L) | UnMapController ((byte)(Id)))

void   sendf(APPL   *, word, dword, word, byte *, ...);
void   * TransmitBufferSet(APPL   * appl, dword ref);
void   * TransmitBufferGet(APPL   * appl, void   * p);
void TransmitBufferFree(APPL   * appl, void   * p);
void   * ReceiveBufferGet(APPL   * appl, int Num);

int fax_head_line_time (char *buffer);


/*------------------------------------------------------------------*/
/* Global data definitions                                          */
/*------------------------------------------------------------------*/
extern byte max_adapter;
extern byte max_appl;
extern DIVA_CAPI_ADAPTER   * adapter;
extern APPL   * application;







static byte remove_started = FALSE;
static PLCI dummy_plci;


static struct _ftable {
  word command;
  byte * format;
  byte (* function)(dword, word, DIVA_CAPI_ADAPTER   *, PLCI   *, APPL   *, API_PARSE *);
} ftable[] = {
  {_DATA_B3_R,                          "dwww",         data_b3_req},
  {_DATA_B3_I|RESPONSE,                 "w",            data_b3_res},
  {_INFO_R,                             "ss",           info_req},
  {_INFO_I|RESPONSE,                    "",             info_res},
  {_CONNECT_R,                          "wsssssssss",   connect_req},
  {_CONNECT_I|RESPONSE,                 "wsssss",       connect_res},
  {_CONNECT_ACTIVE_I|RESPONSE,          "",             connect_a_res},
  {_DISCONNECT_R,                       "s",            disconnect_req},
  {_DISCONNECT_I|RESPONSE,              "",             disconnect_res},
  {_LISTEN_R,                           "dddss",        listen_req},
  {_ALERT_R,                            "s",            alert_req},
  {_FACILITY_R,                         "ws",           facility_req},
  {_FACILITY_I|RESPONSE,                "ws",           facility_res},
  {_CONNECT_B3_R,                       "s",            connect_b3_req},
  {_CONNECT_B3_I|RESPONSE,              "ws",           connect_b3_res},
  {_CONNECT_B3_ACTIVE_I|RESPONSE,       "",             connect_b3_a_res},
  {_DISCONNECT_B3_R,                    "s",            disconnect_b3_req},
  {_DISCONNECT_B3_I|RESPONSE,           "",             disconnect_b3_res},
  {_RESET_B3_R,                         "s",            reset_b3_req},
  {_RESET_B3_I|RESPONSE,                "",             reset_b3_res},
  {_CONNECT_B3_T90_ACTIVE_I|RESPONSE,   "ws",           connect_b3_t90_a_res},
  {_CONNECT_B3_T90_ACTIVE_I|RESPONSE,   "",             connect_b3_t90_a_res},
  {_SELECT_B_REQ,                       "s",            select_b_req},
  {_MANUFACTURER_R,                     "dws",          manufacturer_req},
  {_MANUFACTURER_I|RESPONSE,            "dws",          manufacturer_res},
  {_MANUFACTURER_I|RESPONSE,            "",             manufacturer_res}
};

static byte * cip_bc[29][2] = {
  { "",                     ""                     }, /* 0 */
  { "\x03\x80\x90\xa3",     "\x03\x80\x90\xa2"     }, /* 1 */
  { "\x02\x88\x90",         "\x02\x88\x90"         }, /* 2 */
  { "\x02\x89\x90",         "\x02\x89\x90"         }, /* 3 */
  { "\x03\x90\x90\xa3",     "\x03\x90\x90\xa2"     }, /* 4 */
  { "\x03\x91\x90\xa5",     "\x03\x91\x90\xa5"     }, /* 5 */
  { "\x02\x98\x90",         "\x02\x98\x90"         }, /* 6 */
  { "\x04\x88\xc0\xc6\xe6", "\x04\x88\xc0\xc6\xe6" }, /* 7 */
  { "\x04\x88\x90\x21\x8f", "\x04\x88\x90\x21\x8f" }, /* 8 */
  { "\x03\x91\x90\xa5",     "\x03\x91\x90\xa5"     }, /* 9 */
  { "",                     ""                     }, /* 10 */
  { "",                     ""                     }, /* 11 */
  { "",                     ""                     }, /* 12 */
  { "",                     ""                     }, /* 13 */
  { "",                     ""                     }, /* 14 */
  { "",                     ""                     }, /* 15 */

  { "\x03\x80\x90\xa3",     "\x03\x80\x90\xa2"     }, /* 16 */
  { "\x03\x90\x90\xa3",     "\x03\x90\x90\xa2"     }, /* 17 */
  { "\x02\x88\x90",         "\x02\x88\x90"         }, /* 18 */
  { "\x02\x88\x90",         "\x02\x88\x90"         }, /* 19 */
  { "\x02\x88\x90",         "\x02\x88\x90"         }, /* 20 */
  { "\x02\x88\x90",         "\x02\x88\x90"         }, /* 21 */
  { "\x02\x88\x90",         "\x02\x88\x90"         }, /* 22 */
  { "\x02\x88\x90",         "\x02\x88\x90"         }, /* 23 */
  { "\x02\x88\x90",         "\x02\x88\x90"         }, /* 24 */
  { "\x02\x88\x90",         "\x02\x88\x90"         }, /* 25 */
  { "\x03\x91\x90\xa5",     "\x03\x91\x90\xa5"     }, /* 26 */
  { "\x03\x91\x90\xa5",     "\x03\x91\x90\xa5"     }, /* 27 */
  { "\x02\x88\x90",         "\x02\x88\x90"         }  /* 28 */
};

static byte * cip_hlc[29] = {
  "",                           /* 0 */
  "",                           /* 1 */
  "",                           /* 2 */
  "",                           /* 3 */
  "",                           /* 4 */
  "",                           /* 5 */
  "",                           /* 6 */
  "",                           /* 7 */
  "",                           /* 8 */
  "",                           /* 9 */
  "",                           /* 10 */
  "",                           /* 11 */
  "",                           /* 12 */
  "",                           /* 13 */
  "",                           /* 14 */
  "",                           /* 15 */

  "\x02\x91\x81",               /* 16 */
  "\x02\x91\x84",               /* 17 */
  "\x02\x91\xa1",               /* 18 */
  "\x02\x91\xa4",               /* 19 */
  "\x02\x91\xa8",               /* 20 */
  "\x02\x91\xb1",               /* 21 */
  "\x02\x91\xb2",               /* 22 */
  "\x02\x91\xb5",               /* 23 */
  "\x02\x91\xb8",               /* 24 */
  "\x02\x91\xc1",               /* 25 */
  "\x02\x91\x81",               /* 26 */
  "\x03\x91\xe0\x01",           /* 27 */
  "\x03\x91\xe0\x02"            /* 28 */
};

/*------------------------------------------------------------------*/

#define V120_HEADER_LENGTH 1
#define V120_HEADER_EXTEND_BIT  0x80
#define V120_HEADER_BREAK_BIT   0x40
#define V120_HEADER_C1_BIT      0x04
#define V120_HEADER_C2_BIT      0x08
#define V120_HEADER_FLUSH_COND  (V120_HEADER_BREAK_BIT | V120_HEADER_C1_BIT | V120_HEADER_C2_BIT)

static byte v120_default_header[] =
{

  0x83                          /*  Ext, BR , res, res, C2 , C1 , B  , F   */

};

static byte v120_break_header[] =
{

  0xc3 | V120_HEADER_BREAK_BIT  /*  Ext, BR , res, res, C2 , C1 , B  , F   */

};


/*------------------------------------------------------------------*/
/* API_PUT function                                                 */
/*------------------------------------------------------------------*/

word api_put(APPL   * appl, CAPI_MSG   * msg)
{
  word i, j, k, l, n;
  word ret;
  byte c;
  byte controller;
  DIVA_CAPI_ADAPTER   * a;
  PLCI   * plci;
  NCCI   * ncci_ptr;
  word ncci;
  CAPI_MSG   *m;
    API_PARSE msg_parms[MAX_MSG_PARMS+1];

  if (msg->header.length < sizeof (msg->header) ||
      msg->header.length > MAX_MSG_SIZE) {
    dbug(1,dprintf("bad len"));
    return _BAD_MSG;
  }

  controller = (byte)((msg->header.controller &0x7f)-1);

  /* controller starts with 0 up to (max_adapter - 1) */
  if ( controller >= max_adapter )
  {
    dbug(1,dprintf("invalid ctrl"));
    return _BAD_MSG;
  }
  
  a = &adapter[controller];
  plci = NULL;
  if ((msg->header.plci != 0) && (msg->header.plci <= a->max_plci) && !a->adapter_disabled)
  {
    dbug(1,dprintf("plci=%x",msg->header.plci));
    plci = &a->plci[msg->header.plci-1];
    ncci = GET_WORD(&msg->header.ncci);
    if (plci->Id
     && (plci->appl
      || (plci->State == INC_CON_PENDING)
      || (plci->State == INC_CON_ALERT)
      || (msg->header.command == (_DISCONNECT_I|RESPONSE)))
     && ((ncci == 0)
      || (msg->header.command == (_DISCONNECT_B3_I|RESPONSE))
      || ((ncci < MAX_NCCI+1) && (a->ncci_plci[ncci] == plci->Id))))
    {
      i = plci->msg_in_read_pos;
      j = plci->msg_in_write_pos;
      if (j >= i)
      {
        if (j + msg->header.length + MSG_IN_OVERHEAD <= MSG_IN_QUEUE_SIZE)
          i += MSG_IN_QUEUE_SIZE - j;
        else
          j = 0;
      }
      else
      {

        n = (((CAPI_MSG   *)(plci->msg_in_queue))->header.length + MSG_IN_OVERHEAD + 3) & 0xfffc;

        if (i > MSG_IN_QUEUE_SIZE - n)
          i = MSG_IN_QUEUE_SIZE - n + 1;
        i -= j;
      }

      if (i <= ((msg->header.length + MSG_IN_OVERHEAD + 3) & 0xfffc))

      {
        dbug(0,dprintf("Q-FULL1(msg) - len=%d write=%d read=%d wrap=%d free=%d",
          msg->header.length, plci->msg_in_write_pos,
          plci->msg_in_read_pos, plci->msg_in_wrap_pos, i));

        return _QUEUE_FULL;
      }
      c = FALSE;
      if ((((byte   *) msg) < ((byte   *)(plci->msg_in_queue)))
       || (((byte   *) msg) >= ((byte   *)(plci->msg_in_queue)) + sizeof(plci->msg_in_queue)))
      {
        if (plci->msg_in_write_pos != plci->msg_in_read_pos)
          c = TRUE;
      }
      if (msg->header.command == _DATA_B3_R)
      {
        if (msg->header.length < 20)
        {
          dbug(1,dprintf("DATA_B3 REQ wrong length %d", msg->header.length));
          return _BAD_MSG;
        }
        ncci_ptr = &(a->ncci[ncci]);
        n = ncci_ptr->data_pending;
        l = ncci_ptr->data_ack_pending;
        k = plci->msg_in_read_pos;
        while (k != plci->msg_in_write_pos)
        {
          if (k == plci->msg_in_wrap_pos)
            k = 0;
          if ((((CAPI_MSG   *)(&((byte   *)(plci->msg_in_queue))[k]))->header.command == _DATA_B3_R)
           && (((CAPI_MSG   *)(&((byte   *)(plci->msg_in_queue))[k]))->header.ncci == ncci))
          {
            n++;
            if (((CAPI_MSG   *)(&((byte   *)(plci->msg_in_queue))[k]))->info.data_b3_req.Flags & 0x0004)
              l++;
          }

          k += (((CAPI_MSG   *)(&((byte   *)(plci->msg_in_queue))[k]))->header.length +
            MSG_IN_OVERHEAD + 3) & 0xfffc;

        }
        if ((n >= MAX_DATA_B3) || (l >= MAX_DATA_ACK))
        {
          dbug(0,dprintf("Q-FULL2(data) - pending=%d/%d ack_pending=%d/%d",
                          ncci_ptr->data_pending, n, ncci_ptr->data_ack_pending, l));

          return _QUEUE_FULL;
        }
        if (plci->req_in || plci->internal_command)
        {
          if ((((byte   *) msg) >= ((byte   *)(plci->msg_in_queue)))
           && (((byte   *) msg) < ((byte   *)(plci->msg_in_queue)) + sizeof(plci->msg_in_queue)))
          {
            dbug(0,dprintf("Q-FULL3(requeue)"));

            return _QUEUE_FULL;
          }
          c = TRUE;
        }
      }
      else
      {
        if (plci->req_in || plci->internal_command)
          c = TRUE;
        else
        {
          plci->command = msg->header.command;
          plci->number = msg->header.number;
        }
      }
      if (c)
      {
        dbug(1,dprintf("enqueue msg(0x%04x,0x%x,0x%x) - len=%d write=%d read=%d wrap=%d free=%d",
          msg->header.command, plci->req_in, plci->internal_command,
          msg->header.length, plci->msg_in_write_pos,
          plci->msg_in_read_pos, plci->msg_in_wrap_pos, i));
        if (j == 0)
          plci->msg_in_wrap_pos = plci->msg_in_write_pos;
        m = (CAPI_MSG   *)(&((byte   *)(plci->msg_in_queue))[j]);
        for (i = 0; i < msg->header.length; i++)
          ((byte   *)(plci->msg_in_queue))[j++] = ((byte   *) msg)[i];
        if (m->header.command == _DATA_B3_R)
        {

          m->info.data_b3_req.Data = (dword)(TransmitBufferSet (appl, m->info.data_b3_req.Data));

        }

        j = (j + 3) & 0xfffc;

        *((APPL   *   *)(&((byte   *)(plci->msg_in_queue))[j])) = appl;
        plci->msg_in_write_pos = j + MSG_IN_OVERHEAD;
        return 0;
      }
    }
    else
    {
      plci = NULL;
    }
  }
  dbug(1,dprintf("com=%x",msg->header.command));

  for(j=0;j<MAX_MSG_PARMS+1;j++) msg_parms[j].length = 0;
  for(i=0, ret = _BAD_MSG;
      i<(sizeof(ftable)/sizeof(struct _ftable));
      i++) {

    if(ftable[i].command==msg->header.command) {
      /* break loop if the message is correct, otherwise continue scan  */
      /* (for example: CONNECT_B3_T90_ACT_RES has two specifications)   */
      if(!api_parse(msg->info.b,(word)(msg->header.length-12),ftable[i].format,msg_parms)) {
        ret = 0;
        break;
      }
      for(j=0;j<MAX_MSG_PARMS+1;j++) msg_parms[j].length = 0;
    }
  }
  if(ret) {
    dbug(1,dprintf("BAD_MSG"));
    if(plci) plci->command = 0;
    return ret;
  }


  c = ftable[i].function(GET_DWORD(&msg->header.controller),
                         msg->header.number,
                         a,
                         plci,
                         appl,
                         msg_parms);

  channel_xmit_extended_xon (plci);

  if(c==1) send_req(plci);
  if(c==2 && plci) plci->req_in = plci->req_in_start = plci->req_out = 0;
  if(plci && !plci->req_in) plci->command = 0;
  return 0;
}


/*------------------------------------------------------------------*/
/* api_parse function, check the format of api messages             */
/*------------------------------------------------------------------*/

word api_parse(byte   * msg, word length, byte * format, API_PARSE * parms)
{
  word i;
  word p;

  for(i=0,p=0; format[i]; i++) {
    if(parms)
    {
      parms[i].info = &msg[p];
    }
    switch(format[i]) {
    case 'b':
      p +=1;
      break;
    case 'w':
      p +=2;
      break;
    case 'd':
      p +=4;
      break;
    case 's':
      if(msg[p]==0xff) {
        parms[i].info +=2;
        parms[i].length = msg[p+1] + (msg[p+2]<<8);
        p +=(parms[i].length +3);
      }
      else {
        parms[i].length = msg[p];
        p +=(parms[i].length +1);
      }
      break;
    }

    if(p>length) return TRUE;
  }
  if(parms) parms[i].info = NULL;
  return FALSE;
}

void api_save_msg(API_PARSE   *in, byte *format, API_SAVE   *out)
{
  word i, j, n = 0;
  byte   *p;

  p = out->info;
  for (i = 0; format[i] != '\0'; i++)
  {
    out->parms[i].info = p;
    out->parms[i].length = in[i].length;
    switch (format[i])
    {
    case 'b':
      n = 1;
      break;
    case 'w':
      n = 2;
      break;
    case 'd':
      n = 4;
      break;
    case 's':
      n = in[i].length + 1;
      break;
    }
    for (j = 0; j < n; j++)
      *(p++) = in[i].info[j];
  }
  out->parms[i].info = NULL;
  out->parms[i].length = 0;
}

void api_load_msg(API_SAVE   *in, API_PARSE   *out)
{
  word i;

  i = 0;
  do
  {
    out[i].info = in->parms[i].info;
    out[i].length = in->parms[i].length;
  } while (in->parms[i++].info);
}


/*------------------------------------------------------------------*/
/* CAPI remove function                                             */
/*------------------------------------------------------------------*/

word api_remove_start(void)
{
  word i;
  word j;

  if(!remove_started) {
    remove_started = TRUE;
    for(i=0;i<max_adapter;i++) {
      if(adapter[i].request) {
        for(j=0;j<adapter[i].max_plci;j++) {
          if(adapter[i].plci[j].Sig.Id) plci_remove(&adapter[i].plci[j]);
        }
      }
    }
    return 1;
  }
  else {
    for(i=0;i<max_adapter;i++) {
      if(adapter[i].request) {
        for(j=0;j<adapter[i].max_plci;j++) {
          if(adapter[i].plci[j].Sig.Id) return 1;
        }
      }
    }
  }
  api_remove_complete();
  return 0;
}


/*------------------------------------------------------------------*/
/* internal command queue                                           */
/*------------------------------------------------------------------*/

static void init_internal_command_queue (PLCI   *plci)
{
  word i;

  dbug (1, dprintf ("%s,%d: init_internal_command_queue",
    (char   *)(FILE_), __LINE__));

  plci->internal_command = 0;
  for (i = 0; i < MAX_INTERNAL_COMMAND_LEVELS; i++)
    plci->internal_command_queue[i] = NULL;
}


static void start_internal_command (dword Id, PLCI   *plci, t_std_internal_command command_function)
{
  word i;

  dbug (1, dprintf ("[%06lx] %s,%d: start_internal_command",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  if (plci->internal_command == 0)
  {
    plci->internal_command_queue[0] = command_function;
    (* command_function)(Id, plci, OK);
  }
  else
  {
    i = 1;
    while (plci->internal_command_queue[i] != 0)
      i++;
    plci->internal_command_queue[i] = command_function;
  }
}


static void next_internal_command (dword Id, PLCI   *plci)
{
  word i;

  dbug (1, dprintf ("[%06lx] %s,%d: next_internal_command",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  plci->internal_command = 0;
  plci->internal_command_queue[0] = NULL;
  while (plci->internal_command_queue[1] != 0)
  {
    for (i = 0; i < MAX_INTERNAL_COMMAND_LEVELS - 1; i++)
      plci->internal_command_queue[i] = plci->internal_command_queue[i+1];
    plci->internal_command_queue[MAX_INTERNAL_COMMAND_LEVELS - 1] = NULL;
    (*(plci->internal_command_queue[0]))(Id, plci, OK);
    if (plci->internal_command != 0)
      return;
    plci->internal_command_queue[0] = NULL;
  }
}


/*------------------------------------------------------------------*/
/* NCCI allocate/remove function                                    */
/*------------------------------------------------------------------*/

static dword ncci_mapping_bug = 0;

static word get_ncci (PLCI   *plci, byte ch, word force_ncci)
{
  DIVA_CAPI_ADAPTER   *a;
  word ncci, i, j, k;

  a = plci->adapter;
  if (!ch || a->ch_ncci[ch])
  {
    ncci_mapping_bug++;
    dbug(1,dprintf("NCCI mapping exists %ld %02x %02x %02x-%02x",
      ncci_mapping_bug, ch, force_ncci, a->ncci_ch[a->ch_ncci[ch]], a->ch_ncci[ch]));
    ncci = ch;
  }
  else
  {
    if (force_ncci)
      ncci = force_ncci;
    else
    {
      if ((ch < MAX_NCCI+1) && !a->ncci_ch[ch])
        ncci = ch;
      else
      {
        ncci = 1;
        while ((ncci < MAX_NCCI+1) && a->ncci_ch[ncci])
          ncci++;
        if (ncci == MAX_NCCI+1)
        {
          ncci_mapping_bug++;
          i = 1;
          do
          {
            j = 1;
            while ((j < MAX_NCCI+1) && (a->ncci_ch[j] != i))
              j++;
            k = j;
            if (j < MAX_NCCI+1)
            {
              do
              {
                j++;
              } while ((j < MAX_NCCI+1) && (a->ncci_ch[j] != i));
            }
          } while ((i < MAX_NL_CHANNEL+1) && (j < MAX_NCCI+1));
          if (i < MAX_NL_CHANNEL+1)
          {
            dbug(1,dprintf("NCCI mapping overflow %ld %02x %02x %02x-%02x-%02x",
              ncci_mapping_bug, ch, force_ncci, i, k, j));
          }
          else
          {
            dbug(1,dprintf("NCCI mapping overflow %ld %02x %02x",
              ncci_mapping_bug, ch, force_ncci));
          }
          ncci = ch;
        }
      }
      a->ncci_plci[ncci] = plci->Id;
      a->ncci_state[ncci] = IDLE;
      if (!plci->ncci_ring_list)
        plci->ncci_ring_list = ncci;
      else
        a->ncci_next[ncci] = a->ncci_next[plci->ncci_ring_list];
      a->ncci_next[plci->ncci_ring_list] = (byte) ncci;
    }
    a->ncci_ch[ncci] = ch;
    a->ch_ncci[ch] = (byte) ncci;
    dbug(1,dprintf("NCCI mapping established %ld %02x %02x %02x-%02x",
      ncci_mapping_bug, ch, force_ncci, ch, ncci));
  }
  return (ncci);
}


static void ncci_free_receive_buffers (PLCI   *plci, word ncci)
{
  DIVA_CAPI_ADAPTER   *a;
  APPL   *appl;
  word i, ncci_code;
  dword Id;

  a = plci->adapter;
  Id = (((dword) ncci) << 16) | (((word)(plci->Id)) << 8) | a->Id;
  if (ncci)
  {
    if (a->ncci_plci[ncci] == plci->Id)
    {
      if (!plci->appl)
      {
        ncci_mapping_bug++;
        dbug(1,dprintf("NCCI mapping appl expected %ld %08lx",
          ncci_mapping_bug, Id));
      }
      else
      {
        appl = plci->appl;
        ncci_code = ncci | (((word) a->Id) << 8);
        for (i = 0; i < appl->MaxBuffer; i++)
        {
          if ((appl->DataNCCI[i] == ncci_code)
           && (((byte)(appl->DataFlags[i] >> 8)) == plci->Id))
          {
            appl->DataNCCI[i] = 0;
          }
        }
      }
    }
  }
  else
  {
    for (ncci = 1; ncci < MAX_NCCI+1; ncci++)
    {
      if (a->ncci_plci[ncci] == plci->Id)
      {
        if (!plci->appl)
        {
          ncci_mapping_bug++;
          dbug(1,dprintf("NCCI mapping no appl %ld %08lx",
            ncci_mapping_bug, Id));
        }
        else
        {
          appl = plci->appl;
          ncci_code = ncci | (((word) a->Id) << 8);
          for (i = 0; i < appl->MaxBuffer; i++)
          {
            if ((appl->DataNCCI[i] == ncci_code)
             && (((byte)(appl->DataFlags[i] >> 8)) == plci->Id))
            {
              appl->DataNCCI[i] = 0;
            }
          }
        }
      }
    }
  }
}


static void cleanup_ncci_data (PLCI   *plci, word ncci)
{
  NCCI   *ncci_ptr;

  if (ncci && (plci->adapter->ncci_plci[ncci] == plci->Id))
  {
    ncci_ptr = &(plci->adapter->ncci[ncci]);
    if (plci->appl)
    {
      while (ncci_ptr->data_pending != 0)
      {
        if (!plci->data_sent || (ncci_ptr->DBuffer[ncci_ptr->data_out].P != plci->data_sent_ptr))
          TransmitBufferFree (plci->appl, ncci_ptr->DBuffer[ncci_ptr->data_out].P);
        (ncci_ptr->data_out)++;
        if (ncci_ptr->data_out == MAX_DATA_B3)
          ncci_ptr->data_out = 0;
        (ncci_ptr->data_pending)--;
      }
    }
    ncci_ptr->data_out = 0;
    ncci_ptr->data_pending = 0;
    ncci_ptr->data_ack_out = 0;
    ncci_ptr->data_ack_pending = 0;
  }
}


static void ncci_remove (PLCI   *plci, word ncci, byte preserve_ncci)
{
  DIVA_CAPI_ADAPTER   *a;
  dword Id;
  word i;

  a = plci->adapter;
  Id = (((dword) ncci) << 16) | (((word)(plci->Id)) << 8) | a->Id;
  if (!preserve_ncci)
    ncci_free_receive_buffers (plci, ncci);
  if (ncci)
  {
    if (a->ncci_plci[ncci] != plci->Id)
    {
      ncci_mapping_bug++;
      dbug(1,dprintf("NCCI mapping doesn't exist %ld %08lx %02x",
        ncci_mapping_bug, Id, preserve_ncci));
    }
    else
    {
      cleanup_ncci_data (plci, ncci);
      dbug(1,dprintf("NCCI mapping released %ld %08lx %02x %02x-%02x",
        ncci_mapping_bug, Id, preserve_ncci, a->ncci_ch[ncci], ncci));
      a->ch_ncci[a->ncci_ch[ncci]] = 0;
      if (!preserve_ncci)
      {
        a->ncci_ch[ncci] = 0;
        a->ncci_plci[ncci] = 0;
        a->ncci_state[ncci] = IDLE;
        i = plci->ncci_ring_list;
        while ((i != 0) && (a->ncci_next[i] != plci->ncci_ring_list) && (a->ncci_next[i] != ncci))
          i = a->ncci_next[i];
        if ((i != 0) && (a->ncci_next[i] == ncci))
        {
          if (i == ncci)
            plci->ncci_ring_list = 0;
          else if (plci->ncci_ring_list == ncci)
            plci->ncci_ring_list = i;
          a->ncci_next[i] = a->ncci_next[ncci];
        }
        a->ncci_next[ncci] = 0;
      }
    }
  }
  else
  {
    for (ncci = 1; ncci < MAX_NCCI+1; ncci++)
    {
      if (a->ncci_plci[ncci] == plci->Id)
      {
        cleanup_ncci_data (plci, ncci);
        dbug(1,dprintf("NCCI mapping released %ld %08lx %02x %02x-%02x",
          ncci_mapping_bug, Id, preserve_ncci, a->ncci_ch[ncci], ncci));
        a->ch_ncci[a->ncci_ch[ncci]] = 0;
        if (!preserve_ncci)
        {
          a->ncci_ch[ncci] = 0;
          a->ncci_plci[ncci] = 0;
          a->ncci_state[ncci] = IDLE;
          a->ncci_next[ncci] = 0;
        }
      }
    }
    if (!preserve_ncci)
      plci->ncci_ring_list = 0;
  }
}


/*------------------------------------------------------------------*/
/* PLCI remove function                                             */
/*------------------------------------------------------------------*/

static void plci_free_msg_in_queue (PLCI   *plci)
{
  word i;

  if (plci->appl)
  {
    i = plci->msg_in_read_pos;
    while (i != plci->msg_in_write_pos)
    {
      if (i == plci->msg_in_wrap_pos)
        i = 0;
      if (((CAPI_MSG   *)(&((byte   *)(plci->msg_in_queue))[i]))->header.command == _DATA_B3_R)
      {

        TransmitBufferFree (plci->appl,
          (byte   *)(((CAPI_MSG   *)(&((byte   *)(plci->msg_in_queue))[i]))->info.data_b3_req.Data));

      }

      i += (((CAPI_MSG   *)(&((byte   *)(plci->msg_in_queue))[i]))->header.length +
        MSG_IN_OVERHEAD + 3) & 0xfffc;

    }
  }
  plci->msg_in_write_pos = MSG_IN_QUEUE_SIZE;
  plci->msg_in_read_pos = MSG_IN_QUEUE_SIZE;
  plci->msg_in_wrap_pos = MSG_IN_QUEUE_SIZE;
}


static void plci_remove(PLCI   * plci)
{

  if(!plci) {
    dbug(1,dprintf("plci_remove(no plci)"));
    return;
  }
  init_internal_command_queue (plci);
  dbug(1,dprintf("plci_remove(%x,tel=%x)",plci->Id,plci->tel));
  if(plci_remove_check(plci))
  {
    return;
  }
  if (plci->Sig.Id == 0xff)
  {
    dbug(1,dprintf("D-channel X.25 plci->NL.Id:%0x", plci->NL.Id));
    if (plci->NL.Id && !plci->nl_remove_id)
    {
      nl_req_ncci(plci,REMOVE,0);
      send_req(plci);
    }
  }
  else
  {
    if (!plci->sig_remove_id
     && (plci->Sig.Id
      || (plci->req_in!=plci->req_out)
      || (plci->nl_req || plci->sig_req)))
    {
      sig_req(plci,HANGUP,0);
      send_req(plci);
    }
  }
  ncci_remove (plci, 0, FALSE);
  plci_free_msg_in_queue (plci);

  plci->channels = 0;
  plci->appl = NULL;
  if ((plci->State == INC_CON_PENDING) || (plci->State == INC_CON_ALERT))
    plci->State = OUTG_DIS_PENDING;
}

/*------------------------------------------------------------------*/
/* Application Group function helpers                               */
/*------------------------------------------------------------------*/

static void set_group_ind_mask (PLCI   *plci)
{
  word i;

  for (i = 0; i < C_IND_MASK_DWORDS; i++)
    plci->group_optimization_mask_table[i] = 0xffffffffL;
}

static void clear_group_ind_mask_bit (PLCI   *plci, word b)
{
  plci->group_optimization_mask_table[b >> 5] &= ~(1L << (b & 0x1f));
}

static byte test_group_ind_mask_bit (PLCI   *plci, word b)
{
  return ((plci->group_optimization_mask_table[b >> 5] & (1L << (b & 0x1f))) != 0);
}

/*------------------------------------------------------------------*/
/* c_ind_mask operations for arbitrary MAX_APPL                     */
/*------------------------------------------------------------------*/

static void clear_c_ind_mask (PLCI   *plci)
{
  word i;

  for (i = 0; i < C_IND_MASK_DWORDS; i++)
    plci->c_ind_mask_table[i] = 0;
}

static byte c_ind_mask_empty (PLCI   *plci)
{
  word i;

  i = 0;
  while ((i < C_IND_MASK_DWORDS) && (plci->c_ind_mask_table[i] == 0))
    i++;
  return (i == C_IND_MASK_DWORDS);
}

static void set_c_ind_mask_bit (PLCI   *plci, word b)
{
  plci->c_ind_mask_table[b >> 5] |= (1L << (b & 0x1f));
}

static void clear_c_ind_mask_bit (PLCI   *plci, word b)
{
  plci->c_ind_mask_table[b >> 5] &= ~(1L << (b & 0x1f));
}

static byte test_c_ind_mask_bit (PLCI   *plci, word b)
{
  return ((plci->c_ind_mask_table[b >> 5] & (1L << (b & 0x1f))) != 0);
}

static void dump_c_ind_mask (PLCI   *plci)
{
static char hex_digit_table[0x10] =
  {'0','1','2','3','4','5','6','7','8','9','a','b','c','d','e','f'};
  word i, j, k;
  dword d;
    char *p;
    char buf[40];

  for (i = 0; i < C_IND_MASK_DWORDS; i += 4)
  {
    p = buf + 36;
    *p = '\0';
    for (j = 0; j < 4; j++)
    {
      if (i+j < C_IND_MASK_DWORDS)
      {
        d = plci->c_ind_mask_table[i+j];
        for (k = 0; k < 8; k++)
        {
          *(--p) = hex_digit_table[d & 0xf];
          d >>= 4;
        }
      }
      else if (i != 0)
      {
        for (k = 0; k < 8; k++)
          *(--p) = ' ';
      }
      *(--p) = ' ';
    }
    dbug(1,dprintf ("c_ind_mask =%s", (char   *) p));
  }
}





#define dump_plcis(a)



/*------------------------------------------------------------------*/
/* translation function for each message                            */
/*------------------------------------------------------------------*/

byte connect_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word ch;
  word i;
  word Info;
  word CIP;
  byte LinkLayer;
  API_PARSE * ai;
  API_PARSE * bp;
    API_PARSE ai_parms[5];
  word channel = 0;
  dword ch_mask;
  byte m;
  static byte esc_chi[35] = {0x02,0x18,0x01};
  static byte lli[2] = {0x01,0x00};
  byte noCh = 0;
  word dir = 0;
  byte   *p_chi = "";

  for(i=0;i<5;i++) ai_parms[i].length = 0;

  dbug(1,dprintf("connect_req(%d)",parms->length));
  Info = _WRONG_IDENTIFIER;
  if(a)
  {
    if(a->adapter_disabled)
    {
      dbug(1,dprintf("adapter disabled"));
      Id = ((word)1<<8)|a->Id;
      sendf(appl,_CONNECT_R|CONFIRM,Id,Number,"w",0);
      sendf(appl, _DISCONNECT_I, Id, 0, "w", _L1_ERROR);
      return FALSE;
    }
    Info = _OUT_OF_PLCI;
    if((i=get_plci(a)))
    {
      Info = 0;
      plci = &a->plci[i-1];
      plci->appl = appl;
      plci->call_dir = CALL_DIR_OUT | CALL_DIR_ORIGINATE;
      /* check 'external controller' bit for codec support */
      if(Id & EXT_CONTROLLER)
      {
        if(AdvCodecSupport(a, plci, appl, 0) )
        {
          plci->Id = 0;
          sendf(appl, _CONNECT_R|CONFIRM, Id, Number, "w", _WRONG_IDENTIFIER);
          return 2;
        }
      }
      ai = &parms[9];
      bp = &parms[5];
      ch = 0;
      if(bp->length)LinkLayer = bp->info[3];
      else LinkLayer = 0;
      if(ai->length)
      {
        ch=0xffff;
        if(!api_parse(&ai->info[1],(word)ai->length,"ssss",ai_parms))
        {
          ch = 0;
          if(ai_parms[0].length)
          {
            ch = GET_WORD(ai_parms[0].info+1);
            if(ch>4) ch=0; /* safety -> ignore ChannelID */
            if(ch==4) /* explizit CHI in message */
            {
              /* check length of B-CH struct */
              if((ai_parms[0].info)[3]>=1)
              {
                if((ai_parms[0].info)[4]==CHI)
                {
                  p_chi = &((ai_parms[0].info)[5]);
                }
                else
                {
                  p_chi = &((ai_parms[0].info)[3]);
                }
                if(p_chi[0]>35) /* check length of channel ID */
                {
                  Info = _WRONG_MESSAGE_FORMAT;    
                }
              }
              else Info = _WRONG_MESSAGE_FORMAT;    
            }

            if(ch==3 && ai_parms[0].length>=7 && ai_parms[0].length<=36)
            {
              dir = GET_WORD(ai_parms[0].info+3);
              ch_mask = 0;
              m = 0x3f;
              for(i=0; i+5<=ai_parms[0].length; i++)
              {
                if(ai_parms[0].info[i+5]!=0)
                {
                  if((ai_parms[0].info[i+5] | m) != 0xff)
                    Info = _WRONG_MESSAGE_FORMAT;
                  else
                  {
                    if (ch_mask == 0)
                      channel = i;
                    ch_mask |= 1L << i;
                  }
                }
                m = 0;
              }
              if (ch_mask == 0)
                Info = _WRONG_MESSAGE_FORMAT;
              if (!Info)
              {
                if ((ai_parms[0].length == 36) || (ch_mask != ((dword)(1L << channel))))
                {
                  esc_chi[0] = (byte)(ai_parms[0].length - 2);
                  for(i=0; i+5<=ai_parms[0].length; i++)
                    esc_chi[i+3] = ai_parms[0].info[i+5];
                }
                else
                  esc_chi[0] = 2;
                esc_chi[2] = (byte)channel;
                plci->b_channel = (byte)channel; /* not correct for ETSI ch 17..31 */
                add_p(plci,LLI,lli);
                add_p(plci,ESC,esc_chi);
                plci->State = LOCAL_CONNECT;
                if(!dir) plci->call_dir |= CALL_DIR_FORCE_OUTG_NL;     /* dir 0=DTE, 1=DCE */
              }
            }
          }
        }
        else  Info = _WRONG_MESSAGE_FORMAT;
      }

      dbug(1,dprintf("ch=%x,dir=%x,p_ch=%d",ch,dir,channel));
      plci->command = _CONNECT_R;
      plci->number = Number;
      /* x.31 or D-ch free SAPI in LinkLayer? */
      if(ch==1 && LinkLayer!=3 && LinkLayer!=12) noCh = TRUE;
      if((ch==0 || ch==2 || noCh || ch==3 || ch==4) && !Info)
      {
        /* B-channel used for B3 connections (ch==0), or no B channel    */
        /* is used (ch==2) or perm. connection (3) is used  do a CALL    */
        if(noCh) Info = add_b1(plci,&parms[5],2,0);    /* no resource    */
        else     Info = add_b1(plci,&parms[5],ch,0); 
        add_s(plci,OAD,&parms[2]);
        add_s(plci,OSA,&parms[4]);
        add_s(plci,BC,&parms[6]);
        add_s(plci,LLC,&parms[7]);
        add_s(plci,HLC,&parms[8]);
        CIP = GET_WORD(parms[0].info);
        if (a->Info_Mask[appl->Id-1] & 0x200)
        {
          /* early B3 connect (CIP mask bit 9) no release after a disc */
          add_p(plci,LLI,"\x01\x01");
        }
        if(GET_WORD(parms[0].info)<29) {
          add_p(plci,BC,cip_bc[GET_WORD(parms[0].info)][a->u_law]);
          add_p(plci,HLC,cip_hlc[GET_WORD(parms[0].info)]);
        }
        add_p(plci,UID,"\x06\x43\x61\x70\x69\x32\x30");
        sig_req(plci,ASSIGN,DSIG_ID);
      }
      else if(ch==1) {

        /* D-Channel used for B3 connections */
        plci->Sig.Id = 0xff;
        Info = 0;
      }

      if(!Info && ch!=2 && !noCh ) {
        Info = add_b23(plci,&parms[5]);
        if(!Info) {
          if(!(plci->tel && !plci->adv_nl))nl_req_ncci(plci,ASSIGN,0);
        }
      }

      if(!Info)
      {
        if(ch==0 || ch==2 || ch==3 || noCh || ch==4)
        {
          if(plci->spoofed_msg==SPOOFING_REQUIRED)
          {
            api_save_msg(parms, "wsssssssss", &plci->saved_msg);
            plci->spoofed_msg = CALL_REQ;
            plci->internal_command = BLOCK_PLCI;
            plci->command = 0;
            dbug(1,dprintf("Spoof"));
            send_req(plci);
            return FALSE;
          }
          if(ch==4)add_p(plci,CHI,p_chi);
          add_s(plci,CPN,&parms[1]);
          add_s(plci,DSA,&parms[3]);
          if(noCh) add_p(plci,ESC,"\x02\x18\xfd");  /* D-channel, no B-L3 */
          add_ai(plci,&parms[9]);
          if(!dir)sig_req(plci,CALL_REQ,0);
          else
          {
            plci->command = PERM_LIST_REQ;
            plci->appl = appl;
            sig_req(plci,LISTEN_REQ,0);
            send_req(plci);
            return FALSE;
          }
        }
        send_req(plci);
        return FALSE;
      }
      plci->Id = 0;
    }
  }
  sendf(appl,
        _CONNECT_R|CONFIRM,
        Id,
        Number,
        "w",Info);
  return 2;
}

byte connect_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word i, Info;
  word Reject;
  static byte cau_t[] = {0,0,0x90,0x91,0xac,0x9d,0x86,0xd8,0x9b};
  static byte esc_t[] = {0x03,0x08,0x00,0x00};
  API_PARSE * ai;
    API_PARSE ai_parms[5];
  word ch=0;

  if(!plci) {
    dbug(1,dprintf("connect_res(no plci)"));
    return 0;  /* no plci, no send */
  }

  dbug(1,dprintf("connect_res(State=0x%x)",plci->State));
  for(i=0;i<5;i++) ai_parms[i].length = 0;
  ai = &parms[5];
  dbug(1,dprintf("ai->length=%d",ai->length));

  if(ai->length)
  {
    if(!api_parse(&ai->info[1],(word)ai->length,"ssss",ai_parms))
    {
      dbug(1,dprintf("ai_parms[0].length=%d/0x%x",ai_parms[0].length,GET_WORD(ai_parms[0].info+1)));
      ch = 0;
      if(ai_parms[0].length)
      {
        ch = GET_WORD(ai_parms[0].info+1);
        dbug(1,dprintf("BCH-I=0x%x",ch));
      }
    }
  }

  if(plci->State==INC_CON_CONNECTED_ALERT)
  {
    dbug(1,dprintf("Connected Alert Call_Res"));
    if (a->Info_Mask[appl->Id-1] & 0x200)
    {
    /* early B3 connect (CIP mask bit 9) no release after a disc */
      add_p(plci,LLI,"\x01\x01");
    }
    add_s(plci, CONN_NR, &parms[2]);
    add_s(plci, LLC, &parms[4]);
    add_ai(plci, &parms[5]);
    plci->State = INC_CON_ACCEPT;
    sig_req(plci, CALL_RES,0);
    return 1;
  }
  else if(plci->State==INC_CON_PENDING || plci->State==INC_CON_ALERT) {
    clear_c_ind_mask_bit (plci, (word)(appl->Id-1));
    dump_c_ind_mask (plci);
    Reject = GET_WORD(parms[0].info);
    dbug(1,dprintf("Reject=0x%x",Reject));
    if(Reject) 
    {
      if(c_ind_mask_empty (plci)) 
      {
        if((Reject&0xff00)==0x3400) 
        {
          esc_t[2] = ((byte)(Reject&0x00ff)) | 0x80;
          add_p(plci,ESC,esc_t);
          add_ai(plci, &parms[5]);
          sig_req(plci,REJECT,0);
        }      
        else if(Reject==1 || Reject>9) 
        {
          add_ai(plci, &parms[5]);
          sig_req(plci,HANGUP,0);
        }
        else 
        {
          esc_t[2] = cau_t[(Reject&0x000f)];
          add_p(plci,ESC,esc_t);
          add_ai(plci, &parms[5]);
          sig_req(plci,REJECT,0);
        }
        plci->appl = appl;
      }
      else 
      {
        sendf(appl, _DISCONNECT_I, Id, 0, "w", _OTHER_APPL_CONNECTED);
      }
    }
    else {
      plci->appl = appl;
      if(Id & EXT_CONTROLLER){
        if(AdvCodecSupport(a, plci, appl, 0)){
          dbug(1,dprintf("connect_res(error from AdvCodecSupport)"));
          sig_req(plci,HANGUP,0);
          return 1;
        }
        if(plci->tel == ADV_VOICE && a->AdvCodecPLCI)
        {
          Info = add_b23(plci, &parms[1]);
          if (Info)
          {
            dbug(1,dprintf("connect_res(error from add_b23)"));
            sig_req(plci,HANGUP,0);
            return 1;
          }
          if(plci->adv_nl)
          {
            nl_req_ncci(plci, ASSIGN, 0);
          }
        }
      }
      else
      {
        plci->tel = 0;
        if(ch!=2)
        {
          Info = add_b23(plci, &parms[1]);
          if (Info)
          {
            dbug(1,dprintf("connect_res(error from add_b23 2)"));
            sig_req(plci,HANGUP,0);
            return 1;
          }
        }
        nl_req_ncci(plci, ASSIGN, 0);
      }

      if(plci->spoofed_msg==SPOOFING_REQUIRED)
      {
        api_save_msg(parms, "wsssss", &plci->saved_msg);
        plci->spoofed_msg = CALL_RES;
        plci->internal_command = BLOCK_PLCI;
        plci->command = 0;
        dbug(1,dprintf("Spoof"));
      }
      else
      {
        add_b1 (plci, &parms[1], ch, plci->B1_facilities);
        if (a->Info_Mask[appl->Id-1] & 0x200)
        {
          /* early B3 connect (CIP mask bit 9) no release after a disc */
          add_p(plci,LLI,"\x01\x01");
        }
        add_s(plci, CONN_NR, &parms[2]);
        add_s(plci, LLC, &parms[4]);
        add_ai(plci, &parms[5]);
        plci->State = INC_CON_ACCEPT;
        sig_req(plci, CALL_RES,0);
      }

      for(i=0; i<max_appl; i++) {
        if(test_c_ind_mask_bit (plci, i)) {
          sendf(&application[i], _DISCONNECT_I, Id, 0, "w", _OTHER_APPL_CONNECTED);
        }
      }
    }
  }
  return 1;
}

byte connect_a_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * msg)
{
  dbug(1,dprintf("connect_a_res"));
  return FALSE;
}

byte disconnect_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * msg)
{
  word Info;
  word i;

  dbug(1,dprintf("disconnect_req"));

  Info = _WRONG_IDENTIFIER;

  if(plci)
  {
    if(plci->State==INC_CON_PENDING || plci->State==INC_CON_ALERT)
    {
      clear_c_ind_mask_bit (plci, (word)(appl->Id-1));
      plci->appl = appl;
      for(i=0; i<max_appl; i++)
      {
        if(test_c_ind_mask_bit (plci, i))
          sendf(&application[i], _DISCONNECT_I, Id, 0, "w", 0);
      }
      plci->State = OUTG_DIS_PENDING;
    }
    if(plci->Sig.Id && plci->appl)
    {
      Info = 0;
        if(plci->Sig.Id!=0xff)
        {
          if(plci->State!=INC_DIS_PENDING)
          {
            add_ai(plci, &msg[0]);
            sig_req(plci,HANGUP,0);
            plci->State = OUTG_DIS_PENDING;
            return 1;
          }
        }
        else
        {
          if (plci->NL.Id && !plci->nl_remove_id)
          {
            mixer_remove (plci);
            nl_req_ncci(plci,REMOVE,0);
          sendf(appl,_DISCONNECT_R|CONFIRM,Id,Number,"w",0);
          sendf(appl, _DISCONNECT_I, Id, 0, "w", 0);
          plci->State = INC_DIS_PENDING;
          }
          return 1;
        }
      }
    }

  if(!appl)  return FALSE;
  sendf(appl, _DISCONNECT_R|CONFIRM, Id, Number, "w",Info);
  return FALSE;
}

byte disconnect_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * msg)
{
  dbug(1,dprintf("disconnect_res"));
  if(plci)
  {
        /* clear ind mask bit, just in case of collsion of          */
        /* DISCONNECT_IND and CONNECT_RES                           */
    clear_c_ind_mask_bit (plci, (word)(appl->Id-1));
    ncci_free_receive_buffers (plci, 0);
    if(plci_remove_check(plci))
    {
      return 0;
    }
    if(plci->State==INC_DIS_PENDING
    || plci->State==SUSPENDING) {
      if(c_ind_mask_empty (plci)) {
        if(plci->State!=SUSPENDING)plci->State = IDLE;
        dbug(1,dprintf("chs=%d",plci->channels));
        if(!plci->channels) {
          plci_remove(plci);
        }
      }
    }
  }
  return 0;
}

byte listen_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word Info;
  byte i;

  dbug(1,dprintf("listen_req(Appl=0x%x)",appl->Id));

  Info = _WRONG_IDENTIFIER;
  if(a) {
    Info = 0;
    a->Info_Mask[appl->Id-1] = GET_DWORD(parms[0].info);
    a->CIP_Mask[appl->Id-1] = GET_DWORD(parms[1].info);
    dbug(1,dprintf("CIP_MASK=0x%lx",GET_DWORD(parms[1].info)));
    if (a->Info_Mask[appl->Id-1] & 0x200){ /* early B3 connect provides */
      a->Info_Mask[appl->Id-1] |=  0x10;   /* call progression infos    */
    }

    /* check if external controller listen and switch listen on or off*/
    if(Id&EXT_CONTROLLER && GET_DWORD(parms[1].info)){
      if(a->profile.Global_Options & ON_BOARD_CODEC) {
        dummy_plci.State = IDLE;
        a->codec_listen[appl->Id-1] = &dummy_plci;
        a->TelOAD[0] = (byte)(parms[3].length);
        for(i=1;parms[3].length>=i && i<22;i++) {
          a->TelOAD[i] = parms[3].info[i];
        }
        a->TelOAD[i] = 0;
        a->TelOSA[0] = (byte)(parms[4].length);
        for(i=1;parms[4].length>=i && i<22;i++) {
          a->TelOSA[i] = parms[4].info[i];
        }
        a->TelOSA[i] = 0;
      }
      else Info = 0x2002; /* wrong controller, codec not supported */
    }
    else{               /* clear listen */
      a->codec_listen[appl->Id-1] = (PLCI   *)0;
    }
  }
  sendf(appl,
        _LISTEN_R|CONFIRM,
        Id,
        Number,
        "w",Info);

  if (a) listen_check(a);
  return FALSE;
}

byte info_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * msg)
{
  word i;
  API_PARSE * ai;
  PLCI   * rc_plci = NULL;
    API_PARSE ai_parms[5];
  word Info = 0;

  dbug(1,dprintf("info_req"));
  for(i=0;i<5;i++) ai_parms[i].length = 0;

  ai = &msg[1];

  if(ai->length)
  {
    if(api_parse(&ai->info[1],(word)ai->length,"ssss",ai_parms))
    {
      dbug(1,dprintf("AddInfo wrong"));
      Info = _WRONG_MESSAGE_FORMAT;
    }
  }
  if(!a) Info = _WRONG_STATE;

  if(!Info && plci)
  {                /* no fac, with CPN, or KEY */
    rc_plci = plci;
    if(!ai_parms[3].length && plci->State && (msg[0].length || ai_parms[1].length) )
    {
      /* overlap sending option */
      dbug(1,dprintf("OvlSnd"));
      add_s(plci,CPN,&msg[0]);
      add_s(plci,KEY,&ai_parms[1]);
      sig_req(plci,INFO_REQ,0);
      send_req(plci);
      return FALSE;
    }

    if(plci->State && ai_parms[2].length)
    {
      /* User_Info option */
      dbug(1,dprintf("UUI"));
      add_s(plci,UUI,&ai_parms[2]);
      sig_req(plci,USER_DATA,0);
    }
    else if(plci->State && ai_parms[3].length)
    {
      /* Facility option */
      dbug(1,dprintf("FAC"));
      add_s(plci,CPN,&msg[0]);
      add_ai(plci, &msg[1]);
      sig_req(plci,FACILITY_REQ,0);
    }
    else
    {
      Info = _WRONG_STATE;
    }
  }
  else if((ai_parms[1].length || ai_parms[2].length || ai_parms[3].length) && !Info)
  {
    /* NCR_Facility option -> send UUI and Keypad too */
    dbug(1,dprintf("NCR_FAC"));
    if((i=get_plci(a)))
    {
      rc_plci = &a->plci[i-1];
      appl->NullCREnable  = TRUE;
      rc_plci->internal_command = C_NCR_FAC_REQ;
      rc_plci->appl = appl;
      add_p(rc_plci,CAI,"\x01\x80");
      add_p(rc_plci,UID,"\x06\x43\x61\x70\x69\x32\x30");
      sig_req(rc_plci,ASSIGN,DSIG_ID);
      send_req(rc_plci);
    }
    else
    {
      Info = _OUT_OF_PLCI;
    }

    if(!Info)
    {
      add_s(rc_plci,CPN,&msg[0]);
      add_ai(rc_plci, &msg[1]);
      sig_req(rc_plci,NCR_FACILITY,0);
      send_req(rc_plci);
      return FALSE;
     /* for application controlled supplementary services    */
    }
  }

  if (!rc_plci)
  {
    Info = _WRONG_MESSAGE_FORMAT;
  }

  if(!Info)
  {
    send_req(rc_plci);
  }
  else
  {  /* appl is not assigned to a PLCI or error condition */
    dbug(1,dprintf("localInfoCon"));
    sendf(appl,
          _INFO_R|CONFIRM,
          Id,
          Number,
          "w",Info);
  }
  return FALSE;
}

byte info_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * msg)
{
  dbug(1,dprintf("info_res"));
  return FALSE;
}

byte alert_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * msg)
{
  word Info;
  byte ret;

  dbug(1,dprintf("alert_req"));

  Info = _WRONG_IDENTIFIER;
  ret = FALSE;
  if(plci) {
    Info = _ALERT_IGNORED;
    if(plci->State!=INC_CON_ALERT) {
      Info = _WRONG_STATE;
      if(plci->State==INC_CON_PENDING) {
        Info = 0;
        plci->State=INC_CON_ALERT;
        add_ai(plci, &msg[0]);
        sig_req(plci,CALL_ALERT,0);
        ret = 1;
      }
    }
  }
  sendf(appl,
        _ALERT_R|CONFIRM,
        Id,
        Number,
        "w",Info);
  return ret;
}

byte facility_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * msg)
{
  word Info = 0;
  word i    = 0;

  word selector;
  word SSreq;
  long relatedPLCIvalue;
  DIVA_CAPI_ADAPTER   * relatedadapter;
  byte * SSparms  = "";
    byte RCparms[]  = "\x05\x00\x00\x02\x00\x00";
    byte SSstruct[] = "\x09\x00\x00\x06\x00\x00\x00\x00\x00\x00";
  API_PARSE * parms;
    API_PARSE ss_parms[11];
  PLCI   *rplci;
    byte cai[15];
  dword d;
    API_PARSE dummy;

  dbug(1,dprintf("facility_req"));
  for(i=0;i<9;i++) ss_parms[i].length = 0;

  parms = &msg[1];

  if(!a)
  {
    dbug(1,dprintf("wrong Ctrl"));
    Info = _WRONG_IDENTIFIER;
  }

  selector = GET_WORD(msg[0].info);

  if(!Info)
  {
    switch(selector)
    {
      case SELECTOR_HANDSET:
        Info = AdvCodecSupport(a, plci, appl, HOOK_SUPPORT);
        break;

      case SELECTOR_SU_SERV:
        if(!msg[1].length)
        {
          Info = _WRONG_MESSAGE_FORMAT;
          break;
        }
        SSreq = GET_WORD(&(msg[1].info[1]));
        PUT_WORD(&RCparms[1],SSreq);
        SSparms = RCparms;
        switch(SSreq)
        {
          case S_GET_SUPPORTED_SERVICES:
            if((i=get_plci(a)))
            {
              rplci = &a->plci[i-1];
              rplci->appl = appl;
              add_p(rplci,CAI,"\x01\x80");
              add_p(rplci,UID,"\x06\x43\x61\x70\x69\x32\x30");
              sig_req(rplci,ASSIGN,DSIG_ID);
              send_req(rplci);
            }
            else
            {
              PUT_DWORD(&SSstruct[6], MASK_TERMINAL_PORTABILITY);
              SSparms = (byte *)SSstruct;
              break;
            }
            rplci->internal_command = GETSERV_REQ_PEND;
            rplci->number = Number;
            rplci->appl = appl;
            sig_req(rplci,S_SUPPORTED,0);
            send_req(rplci);
            return FALSE;
            break;

          case S_LISTEN:
            if(parms->length==7)
            {
              if(api_parse(&parms->info[1],(word)parms->length,"wbd",ss_parms))
              {
                dbug(1,dprintf("format wrong"));
                Info = _WRONG_MESSAGE_FORMAT;
                break;
              }
            }
            else
            {
              Info = _WRONG_MESSAGE_FORMAT;
              break;
            }
            a->Notification_Mask[appl->Id-1] = GET_DWORD(ss_parms[2].info);
            if(a->Notification_Mask[appl->Id-1] & SMASK_MWI) /* MWI active? */
            {
              if((i=get_plci(a)))
              {
                rplci = &a->plci[i-1];
                rplci->appl = appl;
                add_p(rplci,CAI,"\x01\x80");
                add_p(rplci,UID,"\x06\x43\x61\x70\x69\x32\x30");
                sig_req(rplci,ASSIGN,DSIG_ID);
                send_req(rplci);
              }
              else
              {
                break;
              }
              rplci->internal_command = GET_MWI_STATE;
              rplci->number = Number;
              sig_req(rplci,MWI_POLL,0);
              send_req(rplci);
            }
            break;

          case S_HOLD:
            api_parse(&parms->info[1],(word)parms->length,"ws",ss_parms);
            if(plci && plci->State && plci->SuppState==IDLE)
            {
              plci->SuppState = HOLD_REQUEST;
              plci->command = C_HOLD_REQ;
              add_s(plci,CAI,&ss_parms[1]);
              sig_req(plci,CALL_HOLD,0);
              send_req(plci);
              return FALSE;
            }
            else Info = 0x3010;                    /* wrong state           */
            break;
          case S_RETRIEVE:
            if(plci && plci->State && plci->SuppState==CALL_HELD)
            {
              if(Id & EXT_CONTROLLER)
              {
                if(AdvCodecSupport(a, plci, appl, 0))
                {
                  Info = 0x3010;                    /* wrong state           */
                  break;
                }
              }
              else plci->tel = 0;

              plci->SuppState = RETRIEVE_REQUEST;
              plci->command = C_RETRIEVE_REQ;
              if(plci->spoofed_msg==SPOOFING_REQUIRED)
              {
                plci->spoofed_msg = CALL_RETRIEVE;
                plci->internal_command = BLOCK_PLCI;
                plci->command = 0;
                dbug(1,dprintf("Spoof"));
                return FALSE;
              }
              else
              {
                sig_req(plci,CALL_RETRIEVE,0);
                send_req(plci);
                return FALSE;
              }
            }
            else Info = 0x3010;                    /* wrong state           */
            break;
          case S_SUSPEND:
            if(parms->length)
            {
              if(api_parse(&parms->info[1],(word)parms->length,"wbs",ss_parms))
              {
                dbug(1,dprintf("format wrong"));
                Info = _WRONG_MESSAGE_FORMAT;
                break;
              }
            }
            if(plci && plci->State)
            {
              add_s(plci,CAI,&ss_parms[2]);
              plci->command = SUSPEND_REQ;
              sig_req(plci,SUSPEND,0);
              plci->State = SUSPENDING;
              send_req(plci);
            }
            else Info = 0x3010;                    /* wrong state           */
            break;

          case S_RESUME:
            if(!(i=get_plci(a)) )
            {
              Info = _OUT_OF_PLCI;
              break;
            }
            rplci = &a->plci[i-1];
            rplci->appl = appl;
            rplci->number = Number;
            rplci->tel = 0;
            rplci->call_dir = CALL_DIR_OUT | CALL_DIR_ORIGINATE;
            /* check 'external controller' bit for codec support */
            if(Id & EXT_CONTROLLER)
            {
              if(AdvCodecSupport(a, rplci, appl, 0) )
              {
                rplci->Id = 0;
                Info = 0x300A;
                break;
              }
            }
            if(parms->length)
            {
              if(api_parse(&parms->info[1],(word)parms->length,"wbs",ss_parms))
              {
                dbug(1,dprintf("format wrong"));
                rplci->Id = 0;
                Info = _WRONG_MESSAGE_FORMAT;
                break;
              }
            }
            dummy.length = 0;
            dummy.info = "\x00";
            add_b1(rplci, &dummy, 0, 0);
            if (a->Info_Mask[appl->Id-1] & 0x200)
            {
              /* early B3 connect (CIP mask bit 9) no release after a disc */
              add_p(rplci,LLI,"\x01\x01");
            }
            add_p(rplci,UID,"\x06\x43\x61\x70\x69\x32\x30");
            sig_req(rplci,ASSIGN,DSIG_ID);
            send_req(rplci);
            add_s(rplci,CAI,&ss_parms[2]);
            rplci->command = RESUME_REQ;
            sig_req(rplci,RESUME,0);
            rplci->State = RESUMING;
            send_req(rplci);
            break;

          case S_CONF_BEGIN: /* Request */
          case S_CONF_DROP:
          case S_CONF_ISOLATE:
          case S_CONF_REATTACH:
            if(api_parse(&parms->info[1],(word)parms->length,"wbd",ss_parms))
            {
              dbug(1,dprintf("format wrong"));
              Info = _WRONG_MESSAGE_FORMAT;
              break;
            }
            if(plci && plci->State && ((plci->SuppState==IDLE)||(plci->SuppState==CALL_HELD)))
            {
              d = GET_DWORD(ss_parms[2].info);     
              if(d>=0x80)
              {
                dbug(1,dprintf("format wrong"));
                Info = _WRONG_MESSAGE_FORMAT;
                break;
              }
              plci->ptyState = (byte)SSreq;
              plci->command = 0;
              cai[0] = 2;
              switch(SSreq)
              {
              case S_CONF_BEGIN:
                  cai[1] = CONF_BEGIN;
                  plci->internal_command = CONF_BEGIN_REQ_PEND;
                  break;
              case S_CONF_DROP:
                  cai[1] = CONF_DROP;
                  plci->internal_command = CONF_DROP_REQ_PEND;
                  break;
              case S_CONF_ISOLATE:
                  cai[1] = CONF_ISOLATE;
                  plci->internal_command = CONF_ISOLATE_REQ_PEND;
                  break;
              case S_CONF_REATTACH:
                  cai[1] = CONF_REATTACH;
                  plci->internal_command = CONF_REATTACH_REQ_PEND;
                  break;
              }
              cai[2] = (byte)d; /* Conference Size resp. PartyId */
              add_p(plci,CAI,cai);
              sig_req(plci,S_SERVICE,0);
              send_req(plci);
              return FALSE;
            }
            else Info = 0x3010;                    /* wrong state           */
            break;

          case S_ECT:
          case S_3PTY_BEGIN:
          case S_3PTY_END:
          case S_CONF_ADD:
            if(parms->length==7)
            {
              if(api_parse(&parms->info[1],(word)parms->length,"wbd",ss_parms))
              {
                dbug(1,dprintf("format wrong"));
                Info = _WRONG_MESSAGE_FORMAT;
                break;
              }
            }
            else if(parms->length==8) /* workaround for the T-View-S */
            {
              if(api_parse(&parms->info[1],(word)parms->length,"wbdb",ss_parms))
              {
                dbug(1,dprintf("format wrong"));
                Info = _WRONG_MESSAGE_FORMAT;
                break;
              }
            }
            else
            {
              Info = _WRONG_MESSAGE_FORMAT;
              break;
            }
            if(!msg[1].length)
            {
              Info = _WRONG_MESSAGE_FORMAT;
              break;
            }
            if (!plci)
            {
              Info = _WRONG_IDENTIFIER;
              break;
            }
            relatedPLCIvalue = GET_DWORD(ss_parms[2].info);
            relatedPLCIvalue &= 0x0000FFFF;
            dbug(1,dprintf("PTY/ECT/addCONF,relPLCI=%lx",relatedPLCIvalue));
            /* controller starts with 0 up to (max_adapter - 1) */
            if (((relatedPLCIvalue & 0x7f) == 0)
             || (MapController ((byte)(relatedPLCIvalue & 0x7f)) == 0)
             || (MapController ((byte)(relatedPLCIvalue & 0x7f)) > max_adapter))
            {
              if(SSreq==S_3PTY_END)
              {
                dbug(1, dprintf("wrong Controller use 2nd PLCI=PLCI"));
                rplci = plci;
              }
              else
              {
                Info = 0x3010;                    /* wrong state           */
                break;
              }
            }
            else
            {  
              relatedadapter = &adapter[MapController ((byte)(relatedPLCIvalue & 0x7f))-1];
              relatedPLCIvalue >>=8;
              /* find PLCI PTR*/
              for(i=0,rplci=NULL;i<relatedadapter->max_plci;i++)
              {
                if(relatedadapter->plci[i].Id == (byte)relatedPLCIvalue)
                {
                  rplci = &relatedadapter->plci[i];
                }
              }
              if(!rplci || !relatedPLCIvalue)
              {
                if(SSreq==S_3PTY_END)
                {
                  dbug(1, dprintf("use 2nd PLCI=PLCI"));
                  rplci = plci;
                }
                else
                {
                  Info = 0x3010;                    /* wrong state           */
                  break;
                }
              }
            }
/*
            dbug(1,dprintf("rplci:%x",rplci));
            dbug(1,dprintf("plci:%x",plci));
            dbug(1,dprintf("rplci->ptyState:%x",rplci->ptyState));
            dbug(1,dprintf("plci->ptyState:%x",plci->ptyState));
            dbug(1,dprintf("SSreq:%x",SSreq));
            dbug(1,dprintf("rplci->internal_command:%x",rplci->internal_command));
            dbug(1,dprintf("rplci->appl:%x",rplci->appl));
            dbug(1,dprintf("rplci->Id:%x",rplci->Id));
*/
            /* send PTY/ECT req, cannot check all states because of US stuff */
            if( !rplci->internal_command && rplci->appl )
            {
              plci->command = 0;
              rplci->relatedPTYPLCI = plci;
              plci->relatedPTYPLCI = rplci;
              rplci->ptyState = (byte)SSreq;
              if(SSreq==S_ECT)
              {
                rplci->internal_command = ECT_REQ_PEND;
                cai[1] = ECT_EXECUTE;

                rplci->vswitchstate=0;
                rplci->vsprot=0;
                rplci->vsprotdialect=0;
                plci->vswitchstate=0;
                plci->vsprot=0;
                plci->vsprotdialect=0;

              }
              else if(SSreq==S_CONF_ADD)
              {
                rplci->internal_command = CONF_ADD_REQ_PEND;
                cai[1] = CONF_ADD;
              }
              else
              {
                rplci->internal_command = PTY_REQ_PEND;
                cai[1] = (byte)(SSreq-3);
              }
              rplci->number = Number;
              if(plci!=rplci) /* explicit invocation */
              {
                cai[0] = 2;
                cai[2] = plci->Sig.Id;
                dbug(1,dprintf("explicit invocation"));
              }
              else
              {
                dbug(1,dprintf("implicit invocation"));
                cai[0] = 1;
              }
              add_p(rplci,CAI,cai);
              sig_req(rplci,S_SERVICE,0);
              send_req(rplci);
              return FALSE;
            }
            else
            {
              dbug(0,dprintf("Wrong line"));
              Info = 0x3010;                    /* wrong state           */
              break;
            }
            break;

          case S_CALL_DEFLECTION:
            if(api_parse(&parms->info[1],(word)parms->length,"wbwss",ss_parms))
            {
              dbug(1,dprintf("format wrong"));
              Info = _WRONG_MESSAGE_FORMAT;
              break;
            }
            if (!plci)
            {
              Info = _WRONG_IDENTIFIER;
              break;
            }
            /* reuse unused screening indicator */
            ss_parms[3].info[3] = (byte)GET_WORD(&(ss_parms[2].info[0]));
            plci->command = 0;
            plci->internal_command = CD_REQ_PEND;
            appl->CDEnable = TRUE;
            cai[0] = 1;
            cai[1] = CALL_DEFLECTION;
            add_p(plci,CAI,cai);
            add_p(plci,CPN,ss_parms[3].info);
            sig_req(plci,S_SERVICE,0);
            send_req(plci);
            return FALSE;
            break;

          case S_CALL_FORWARDING_START:
            if(api_parse(&parms->info[1],(word)parms->length,"wbdwwsss",ss_parms))
            {
              dbug(1,dprintf("format wrong"));
              Info = _WRONG_MESSAGE_FORMAT;
              break;
            }

            if((i=get_plci(a)))
            {
              rplci = &a->plci[i-1];
              rplci->appl = appl;
              add_p(rplci,CAI,"\x01\x80");
              add_p(rplci,UID,"\x06\x43\x61\x70\x69\x32\x30");
              sig_req(rplci,ASSIGN,DSIG_ID);
              send_req(rplci);
            }
            else
            {
              Info = _OUT_OF_PLCI;
              break;
            }

            /* reuse unused screening indicator */
            rplci->internal_command = CF_START_PEND;
            rplci->appl = appl;
            rplci->number = Number;
            appl->S_Handle = GET_DWORD(&(ss_parms[2].info[0]));
            cai[0] = 2;
            cai[1] = 0x70|(byte)GET_WORD(&(ss_parms[3].info[0])); /* Function */
            cai[2] = (byte)GET_WORD(&(ss_parms[4].info[0])); /* Basic Service */
            add_p(rplci,CAI,cai);
            add_p(rplci,OAD,ss_parms[5].info);
            add_p(rplci,CPN,ss_parms[6].info);
            sig_req(rplci,S_SERVICE,0);
            send_req(rplci);
            return FALSE;
            break;

          case S_INTERROGATE_DIVERSION:
          case S_INTERROGATE_NUMBERS:
          case S_CALL_FORWARDING_STOP:
          case S_CCBS_REQUEST:
          case S_CCBS_DEACTIVATE:
          case S_CCBS_INTERROGATE:
            switch(SSreq)
            {
            case S_INTERROGATE_NUMBERS:
                if(api_parse(&parms->info[1],(word)parms->length,"wbd",ss_parms))
                {
                  dbug(0,dprintf("format wrong"));
                  Info = _WRONG_MESSAGE_FORMAT;
                }
                break;
            case S_CCBS_REQUEST:
            case S_CCBS_DEACTIVATE:
                if(api_parse(&parms->info[1],(word)parms->length,"wbdw",ss_parms))
                {
                  dbug(0,dprintf("format wrong"));
                  Info = _WRONG_MESSAGE_FORMAT;
                }
                break;
            case S_CCBS_INTERROGATE:
                if(api_parse(&parms->info[1],(word)parms->length,"wbdws",ss_parms))
                {
                  dbug(0,dprintf("format wrong"));
                  Info = _WRONG_MESSAGE_FORMAT;
                }
                break;
            default:
            if(api_parse(&parms->info[1],(word)parms->length,"wbdwws",ss_parms))
            {
              dbug(0,dprintf("format wrong"));
              Info = _WRONG_MESSAGE_FORMAT;
              break;
            }
                break;
            }

            if(Info) break;
            if((i=get_plci(a)))
            {
              rplci = &a->plci[i-1];
              switch(SSreq)
              {
                case S_INTERROGATE_DIVERSION: /* use cai with S_SERVICE below */
                  cai[1] = 0x60|(byte)GET_WORD(&(ss_parms[3].info[0])); /* Function */
                  rplci->internal_command = INTERR_DIVERSION_REQ_PEND; /* move to rplci if assigned */
                  break;
                case S_INTERROGATE_NUMBERS: /* use cai with S_SERVICE below */
                  cai[1] = DIVERSION_INTERROGATE_NUM; /* Function */
                  rplci->internal_command = INTERR_NUMBERS_REQ_PEND; /* move to rplci if assigned */
                  break;
                case S_CALL_FORWARDING_STOP:
                  rplci->internal_command = CF_STOP_PEND;
                  cai[1] = 0x80|(byte)GET_WORD(&(ss_parms[3].info[0])); /* Function */
                  break;
                case S_CCBS_REQUEST:
                  cai[1] = CCBS_REQUEST;
                  rplci->internal_command = CCBS_REQUEST_REQ_PEND;
                  break;
                case S_CCBS_DEACTIVATE:
                  cai[1] = CCBS_DEACTIVATE;
                  rplci->internal_command = CCBS_DEACTIVATE_REQ_PEND;
                  break;
                case S_CCBS_INTERROGATE:
                  cai[1] = CCBS_INTERROGATE;
                  rplci->internal_command = CCBS_INTERROGATE_REQ_PEND;
                  break;
                default:
                  cai[1] = 0;
                break;
              }
              rplci->appl = appl;
              rplci->number = Number;
              add_p(rplci,CAI,"\x01\x80");
              add_p(rplci,UID,"\x06\x43\x61\x70\x69\x32\x30");
              sig_req(rplci,ASSIGN,DSIG_ID);
              send_req(rplci);
            }
            else
            {
              Info = _OUT_OF_PLCI;
              break;
            }

            appl->S_Handle = GET_DWORD(&(ss_parms[2].info[0]));
            switch(SSreq)
            {
            case S_INTERROGATE_NUMBERS:
                cai[0] = 1;
                add_p(rplci,CAI,cai);
                break;
            case S_CCBS_REQUEST:
            case S_CCBS_DEACTIVATE:
                cai[0] = 3;
                PUT_WORD(&cai[2],GET_WORD(&(ss_parms[3].info[0])));
                add_p(rplci,CAI,cai);
                break;
            case S_CCBS_INTERROGATE:
                cai[0] = 3;
                PUT_WORD(&cai[2],GET_WORD(&(ss_parms[3].info[0])));
                add_p(rplci,CAI,cai);
                add_p(rplci,OAD,ss_parms[4].info);
                break;
            default:
            cai[0] = 2;
            cai[2] = (byte)GET_WORD(&(ss_parms[4].info[0])); /* Basic Service */
            add_p(rplci,CAI,cai);
            add_p(rplci,OAD,ss_parms[5].info);
                break;
            }
                        
            sig_req(rplci,S_SERVICE,0);
            send_req(rplci);
            return FALSE;
            break;

          case S_MWI_ACTIVATE:
            if(api_parse(&parms->info[1],(word)parms->length,"wbwdwwwssss",ss_parms))
            {
              dbug(1,dprintf("format wrong"));
              Info = _WRONG_MESSAGE_FORMAT;
              break;
            }
            if(!plci)
            {                               
              if((i=get_plci(a)))
              {
                rplci = &a->plci[i-1];
                rplci->appl = appl;
                rplci->cr_enquiry=TRUE;
                add_p(rplci,CAI,"\x01\x80");
                add_p(rplci,UID,"\x06\x43\x61\x70\x69\x32\x30");
                sig_req(rplci,ASSIGN,DSIG_ID);
                send_req(rplci);
              }
              else
              {
                Info = _OUT_OF_PLCI;
                break;
              }
            }
            else
            {
              rplci = plci;
              rplci->cr_enquiry=FALSE;
            }

            rplci->command = 0;
            rplci->internal_command = MWI_ACTIVATE_REQ_PEND;
            rplci->appl = appl;
            rplci->number = Number;

            cai[0] = 13;
            cai[1] = ACTIVATION_MWI; /* Function */
            PUT_WORD(&cai[2],GET_WORD(&(ss_parms[2].info[0]))); /* Basic Service */
            PUT_DWORD(&cai[4],GET_DWORD(&(ss_parms[3].info[0]))); /* Number of Messages */
            PUT_WORD(&cai[8],GET_WORD(&(ss_parms[4].info[0]))); /* Message Status */
            PUT_WORD(&cai[10],GET_WORD(&(ss_parms[5].info[0]))); /* Message Reference */
            PUT_WORD(&cai[12],GET_WORD(&(ss_parms[6].info[0]))); /* Invocation Mode */
            add_p(rplci,CAI,cai);
            add_p(rplci,CPN,ss_parms[7].info); /* Receiving User Number */
            add_p(rplci,OAD,ss_parms[8].info); /* Controlling User Number */
            add_p(rplci,OSA,ss_parms[9].info); /* Controlling User Provided Number */
            add_p(rplci,UID,ss_parms[10].info); /* Time */
            sig_req(rplci,S_SERVICE,0);
            send_req(rplci);
            return FALSE;

          case S_MWI_DEACTIVATE:
            if(api_parse(&parms->info[1],(word)parms->length,"wbwwss",ss_parms))
            {
              dbug(1,dprintf("format wrong"));
              Info = _WRONG_MESSAGE_FORMAT;
              break;
            }
            if(!plci)
            {                               
              if((i=get_plci(a)))
              {
                rplci = &a->plci[i-1];
                rplci->appl = appl;
                rplci->cr_enquiry=TRUE;
                add_p(rplci,CAI,"\x01\x80");
                add_p(rplci,UID,"\x06\x43\x61\x70\x69\x32\x30");
                sig_req(rplci,ASSIGN,DSIG_ID);
                send_req(rplci);
              }
              else
              {
                Info = _OUT_OF_PLCI;
                break;
              }
            }
            else
            {
              rplci = plci;
              rplci->cr_enquiry=FALSE;
            }

            rplci->command = 0;
            rplci->internal_command = MWI_DEACTIVATE_REQ_PEND;
            rplci->appl = appl;
            rplci->number = Number;

            cai[0] = 5;
            cai[1] = DEACTIVATION_MWI; /* Function */
            PUT_WORD(&cai[2],GET_WORD(&(ss_parms[2].info[0]))); /* Basic Service */
            PUT_WORD(&cai[4],GET_WORD(&(ss_parms[3].info[0]))); /* Invocation Mode */
            add_p(rplci,CAI,cai);
            add_p(rplci,CPN,ss_parms[4].info); /* Receiving User Number */
            add_p(rplci,OAD,ss_parms[5].info); /* Controlling User Number */
            sig_req(rplci,S_SERVICE,0);
            send_req(rplci);
            return FALSE;

          default:
            Info = 0x300E;  /* not supported */
            break;
        }
        break; /* case SELECTOR_SU_SERV: end */


      case SELECTOR_DTMF:
        return (dtmf_request (Id, Number, a, plci, appl, msg));



      case SELECTOR_LINE_INTERCONNECT:
        return (mixer_request (Id, Number, a, plci, appl, msg));



      case PRIV_SELECTOR_ECHO_CANCELLER:
        appl->appl_flags |= APPL_FLAG_PRIV_EC_SPEC;
        return (ec_request (Id, Number, a, plci, appl, msg));

      case SELECTOR_ECHO_CANCELLER:
        appl->appl_flags &= ~APPL_FLAG_PRIV_EC_SPEC;
        return (ec_request (Id, Number, a, plci, appl, msg));


      case SELECTOR_V42BIS:
      default:
        Info = _FACILITY_NOT_SUPPORTED;
        break;
    } /* end of switch(selector) */
  }

  dbug(1,dprintf("SendFacRc"));
  sendf(appl,
        _FACILITY_R|CONFIRM,
        Id,
        Number,
        "wws",Info,selector,SSparms);
  return FALSE;
}

byte facility_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * msg)
{
  dbug(1,dprintf("facility_res"));
  return FALSE;
}

byte connect_b3_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word Info = 0;
  byte req;
  byte len;
  word w;
  word fax_control_bits, fax_feature_bits, fax_info_change;
  API_PARSE * ncpi;
    byte pvc[2];

    API_PARSE fax_parms[9];
  word i;


  dbug(1,dprintf("connect_b3_req"));
  if(plci)
  {
    if ((plci->State == IDLE) || (plci->State == OUTG_DIS_PENDING)
     || (plci->State == INC_DIS_PENDING) || (plci->SuppState != IDLE))
    {
      Info = _WRONG_STATE;
    }
    else
    {
      /* local reply if assign unsuccessfull
         or B3 protocol allows only one layer 3 connection
           and already connected
             or B2 protocol not any LAPD
               and connect_b3_req contradicts originate/answer direction */
      if (!plci->NL.Id
       || (((plci->B3_prot != B3_T90NL) && (plci->B3_prot != B3_ISO8208) && (plci->B3_prot != B3_X25_DCE))
        && ((plci->channels != 0)
         || (((plci->B2_prot != B2_SDLC) && (plci->B2_prot != B2_LAPD) && (plci->B2_prot != B2_LAPD_FREE_SAPI_SEL))
          && ((plci->call_dir & CALL_DIR_ANSWER) && !(plci->call_dir & CALL_DIR_FORCE_OUTG_NL))))))
      {
        dbug(1,dprintf("B3 already connected=%d or no NL.Id=0x%x, dir=%d sstate=0x%x",
                       plci->channels,plci->NL.Id,plci->call_dir,plci->SuppState));
        Info = _WRONG_STATE;
        sendf(appl,                                                        
              _CONNECT_B3_R|CONFIRM,
              Id,
              Number,
              "w",Info);
        return FALSE;
      }
      plci->requested_options_conn = 0;

      req = N_CONNECT;
      ncpi = &parms[0];
      if(plci->B3_prot==2 || plci->B3_prot==3)
      {
        if(ncpi->length>2)
        {
          /* check for PVC */
          if(ncpi->info[2] || ncpi->info[3])
          {
            pvc[0] = ncpi->info[3];
            pvc[1] = ncpi->info[2];
            add_d(plci,2,pvc);
            req = N_RESET;
          }
          else
          {
            if(ncpi->info[1] &1) req = N_CONNECT | N_D_BIT;
            add_d(plci,(word)(ncpi->length-3),&ncpi->info[4]);
          }
        }
      }
      else if(plci->B3_prot==5)
      {
        if (plci->NL.Id && !plci->nl_remove_id)
        {
          fax_control_bits = GET_WORD(&((T30_INFO   *)plci->fax_connect_info_buffer)->control_bits_low);
          fax_feature_bits = GET_WORD(&((T30_INFO   *)plci->fax_connect_info_buffer)->feature_bits_low);
          if (!(fax_control_bits & T30_CONTROL_BIT_MORE_DOCUMENTS)
           || (fax_feature_bits & T30_FEATURE_BIT_MORE_DOCUMENTS))
          {
            len = (byte)(&(((T30_INFO *) 0)->universal_6));
            fax_info_change = FALSE;
            if (ncpi->length >= 4)
            {
              w = GET_WORD(&ncpi->info[3]);
              if ((w & 0x0001) != ((word)(((T30_INFO   *)(plci->fax_connect_info_buffer))->resolution & 0x0001)))
              {
                ((T30_INFO   *)(plci->fax_connect_info_buffer))->resolution =
                  (byte)((((T30_INFO   *)(plci->fax_connect_info_buffer))->resolution & ~T30_RESOLUTION_R8_0770_OR_200) |
                  ((w & 0x0001) ? T30_RESOLUTION_R8_0770_OR_200 : 0));
                fax_info_change = TRUE;
              }
              fax_control_bits &= ~(T30_CONTROL_BIT_REQUEST_POLLING | T30_CONTROL_BIT_MORE_DOCUMENTS);
              if (w & 0x0002)  /* Fax-polling request */
                fax_control_bits |= T30_CONTROL_BIT_REQUEST_POLLING;
              if ((w & 0x0004) /* Request to send / poll another document */
               && (a->manufacturer_features & MANUFACTURER_FEATURE_FAX_MORE_DOCUMENTS))
              {
                fax_control_bits |= T30_CONTROL_BIT_MORE_DOCUMENTS;
              }
              if (ncpi->length >= 6)
              {
                w = GET_WORD(&ncpi->info[5]);
                if (((byte) w) != ((T30_INFO   *)(plci->fax_connect_info_buffer))->data_format)
                {
                  ((T30_INFO   *)(plci->fax_connect_info_buffer))->data_format = (byte) w;
                  fax_info_change = TRUE;
                }

                if ((a->man_profile.private_options & (1L << PRIVATE_FAX_SUB_SEP_PWD))
                 && (GET_WORD(&ncpi->info[5]) & 0x8000)) /* Private SEP/SUB/PWD enable */
                {
                  plci->requested_options_conn |= (1L << PRIVATE_FAX_SUB_SEP_PWD);
                }
                if ((a->man_profile.private_options & (1L << PRIVATE_FAX_NONSTANDARD))
                 && (GET_WORD(&ncpi->info[5]) & 0x4000)) /* Private non-standard facilities enable */
                {
                  plci->requested_options_conn |= (1L << PRIVATE_FAX_NONSTANDARD);
                }
                fax_control_bits &= ~(T30_CONTROL_BIT_ACCEPT_SUBADDRESS | T30_CONTROL_BIT_ACCEPT_SEL_POLLING |
                  T30_CONTROL_BIT_ACCEPT_PASSWORD);
                if ((plci->requested_options_conn | plci->requested_options | a->requested_options_table[appl->Id-1])
                  & ((1L << PRIVATE_FAX_SUB_SEP_PWD) | (1L << PRIVATE_FAX_NONSTANDARD)))
                {
                  if (api_parse (&ncpi->info[1], ncpi->length, "wwwwsss", fax_parms))
                    Info = _WRONG_MESSAGE_FORMAT;
                  else
                  {
                    if ((plci->requested_options_conn | plci->requested_options | a->requested_options_table[appl->Id-1])
                      & (1L << PRIVATE_FAX_SUB_SEP_PWD))
      {
                    fax_control_bits |= T30_CONTROL_BIT_ACCEPT_SUBADDRESS | T30_CONTROL_BIT_ACCEPT_PASSWORD;
                    if (fax_control_bits & T30_CONTROL_BIT_ACCEPT_POLLING)
                      fax_control_bits |= T30_CONTROL_BIT_ACCEPT_SEL_POLLING;
      }
                    w = fax_parms[4].length;
                    if (w > 20)
                      w = 20;
                    ((T30_INFO   *)(plci->fax_connect_info_buffer))->station_id_len = (byte) w;
                    for (i = 0; i < w; i++)
                      ((T30_INFO   *)(plci->fax_connect_info_buffer))->station_id[i] = fax_parms[4].info[1+i];
                    ((T30_INFO   *)(plci->fax_connect_info_buffer))->head_line_len = 0;
                    len = (byte)(((T30_INFO *) 0)->station_id + 20);
                    w = fax_parms[5].length;
                    if (w > 20)
                      w = 20;
                    plci->fax_connect_info_buffer[len++] = (byte) w;
                    for (i = 0; i < w; i++)
                      plci->fax_connect_info_buffer[len++] = fax_parms[5].info[1+i];
                    w = fax_parms[6].length;
                    if (w > 20)
                      w = 20;
                    plci->fax_connect_info_buffer[len++] = (byte) w;
                    for (i = 0; i < w; i++)
                      plci->fax_connect_info_buffer[len++] = fax_parms[6].info[1+i];
                    if ((plci->requested_options_conn | plci->requested_options | a->requested_options_table[appl->Id-1])
                      & (1L << PRIVATE_FAX_NONSTANDARD))
      {
                      if (api_parse (&ncpi->info[1], ncpi->length, "wwwwssss", fax_parms))
        {
                        dbug(1,dprintf("non-standard facilities info missing or wrong format"));
                        plci->fax_connect_info_buffer[len++] = 0;
        }
                      else
                      {
          if ((fax_parms[7].length >= 3) && (fax_parms[7].info[1] >= 2))
            plci->nsf_control_bits = GET_WORD(&fax_parms[7].info[2]);
   plci->fax_connect_info_buffer[len++] = (byte)(fax_parms[7].length);
          for (i = 0; i < fax_parms[7].length; i++)
     plci->fax_connect_info_buffer[len++] = fax_parms[7].info[1+i];
                      }
                    }
                  }
                }
                else
                {
                  len = (byte)(&(((T30_INFO *) 0)->universal_6));
                }
                fax_info_change = TRUE;

              }
              if (fax_control_bits != GET_WORD(&((T30_INFO   *)plci->fax_connect_info_buffer)->control_bits_low))
              {
                PUT_WORD (&((T30_INFO   *)plci->fax_connect_info_buffer)->control_bits_low, fax_control_bits);
                fax_info_change = TRUE;
              }
            }
            if (Info == GOOD)
            {
              plci->fax_connect_info_length = len;
              if (fax_info_change)
              {
                if (fax_feature_bits & T30_FEATURE_BIT_MORE_DOCUMENTS)
                {
                  start_internal_command (Id, plci, fax_connect_info_command);
                  return FALSE;
                }
                else
                {
                  start_internal_command (Id, plci, fax_adjust_b23_command);
                  return FALSE;
                }
              }
            }
          }
          else  Info = _WRONG_STATE;
        }
        else  Info = _WRONG_STATE;
      }

      else if (plci->B3_prot == B3_RTP)
      {
        plci->internal_req_buffer[0] = ncpi->length + 1;
        plci->internal_req_buffer[1] = UDATA_REQUEST_RTP_RECONFIGURE;
        for (w = 0; w < ncpi->length; w++)
          plci->internal_req_buffer[2+w] = ncpi->info[1+w];
        start_internal_command (Id, plci, rtp_connect_b3_req_command);
        return FALSE;
      }

      if(!Info)
      {
        nl_req_ncci(plci,req,0);
        return 1;
      }
    }
  }
  else Info = _WRONG_IDENTIFIER;

  sendf(appl,
        _CONNECT_B3_R|CONFIRM,
        Id,
        Number,
        "w",Info);
  return FALSE;
}

byte connect_b3_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word ncci;
  API_PARSE * ncpi;
  byte req;

  word w;


    API_PARSE fax_parms[9];
  word i;
  byte len;


  dbug(1,dprintf("connect_b3_res"));

  ncci = (word)(Id>>16);
  if(plci && ncci) {
    if(a->ncci_state[ncci]==INC_CON_PENDING) {
      if (GET_WORD (&parms[0].info[0]) != 0)
      {
        a->ncci_state[ncci] = OUTG_REJ_PENDING;
        channel_request_xon (plci, a->ncci_ch[ncci]);
        channel_xmit_xon (plci);
        cleanup_ncci_data (plci, ncci);
        nl_req_ncci(plci,N_DISC,(byte)ncci);
        return 1;
      }
      a->ncci_state[ncci] = INC_ACT_PENDING;

      req = N_CONNECT_ACK;
      ncpi = &parms[1];
      if ((plci->B3_prot == 4) || (plci->B3_prot == 5) || (plci->B3_prot == 7))
      {

        if ((plci->requested_options_conn | plci->requested_options | a->requested_options_table[plci->appl->Id-1])
          & (1L << PRIVATE_FAX_NONSTANDARD))
 {
   if (((plci->B3_prot == 4) || (plci->B3_prot == 5))
    && (plci->nsf_control_bits & T30_NSF_CONTROL_BIT_ENABLE_NSF)
    && (plci->nsf_control_bits & T30_NSF_CONTROL_BIT_NEGOTIATE_RESP))
   {
            len = ((byte)(((T30_INFO *) 0)->station_id + 20));
            if (plci->fax_connect_info_length < len)
            {
              ((T30_INFO *)(plci->fax_connect_info_buffer))->station_id_len = 0;
              ((T30_INFO *)(plci->fax_connect_info_buffer))->head_line_len = 0;
            }
            if (api_parse (&ncpi->info[1], ncpi->length, "wwwwssss", fax_parms))
            {
              dbug(1,dprintf("non-standard facilities info missing or wrong format"));
            }
            else
            {
              if (plci->fax_connect_info_length <= len)
                plci->fax_connect_info_buffer[len] = 0;
              len += 1 + plci->fax_connect_info_buffer[len];
              if (plci->fax_connect_info_length <= len)
                plci->fax_connect_info_buffer[len] = 0;
              len += 1 + plci->fax_connect_info_buffer[len];
              if ((fax_parms[7].length >= 3) && (fax_parms[7].info[1] >= 2))
                plci->nsf_control_bits = GET_WORD(&fax_parms[7].info[2]);
              plci->fax_connect_info_buffer[len++] = (byte)(fax_parms[7].length);
              for (i = 0; i < fax_parms[7].length; i++)
                plci->fax_connect_info_buffer[len++] = fax_parms[7].info[1+i];
            }
            plci->fax_connect_info_length = len;
            ((T30_INFO *)(plci->fax_connect_info_buffer))->code = 0;
            start_internal_command (Id, plci, fax_connect_ack_command);
     return FALSE;
          }
        }

        nl_req_ncci(plci,req,(byte)ncci);
        if ((plci->ncpi_state & NCPI_VALID_CONNECT_B3_ACT)
         && !(plci->ncpi_state & NCPI_CONNECT_B3_ACT_SENT))
        {
          if (plci->B3_prot == 4)
            sendf(appl,_CONNECT_B3_ACTIVE_I,Id,0,"s","");
          else
            sendf(appl,_CONNECT_B3_ACTIVE_I,Id,0,"S",plci->ncpi_buffer);
          plci->ncpi_state |= NCPI_CONNECT_B3_ACT_SENT;
        }
      }

      else if (plci->B3_prot == B3_RTP)
      {
        plci->internal_req_buffer[0] = ncpi->length + 1;
        plci->internal_req_buffer[1] = UDATA_REQUEST_RTP_RECONFIGURE;
        for (w = 0; w < ncpi->length; w++)
          plci->internal_req_buffer[2+w] = ncpi->info[1+w];
        start_internal_command (Id, plci, rtp_connect_b3_res_command);
        return FALSE;
      }

      else
      {
        if(ncpi->length>2) {
          if(ncpi->info[1] &1) req = N_CONNECT_ACK | N_D_BIT;
          add_d(plci,(word)(ncpi->length-3),&ncpi->info[4]);
        }
        nl_req_ncci(plci,req,(byte)ncci);
        sendf(appl,_CONNECT_B3_ACTIVE_I,Id,0,"s","");
        if (plci->adjust_b_restore)
        {
          plci->adjust_b_restore = FALSE;
          start_internal_command (Id, plci, adjust_b_restore);
        }
      }
      return 1;
    }
  }
  return FALSE;
}

byte connect_b3_a_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word ncci;

  ncci = (word)(Id>>16);
  dbug(1,dprintf("connect_b3_a_res(ncci=0x%x)",ncci));

  if (plci && ncci && (plci->State != IDLE) && (plci->State != INC_DIS_PENDING)
   && (plci->State != OUTG_DIS_PENDING))
  {
    if(a->ncci_state[ncci]==INC_ACT_PENDING) {
      a->ncci_state[ncci] = CONNECTED;
      if(plci->State!=INC_CON_CONNECTED_ALERT) plci->State = CONNECTED;
      channel_request_xon (plci, a->ncci_ch[ncci]);
      channel_xmit_xon (plci);
    }
  }
  return FALSE;
}

byte disconnect_b3_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word Info;
  word ncci;
  API_PARSE * ncpi;

  dbug(1,dprintf("disconnect_b3_req"));

  Info = _WRONG_IDENTIFIER;
  ncci = (word)(Id>>16);
  if (plci && ncci)
  {
    Info = _WRONG_STATE;
    if ((a->ncci_state[ncci] == CONNECTED)
     || (a->ncci_state[ncci] == OUTG_CON_PENDING)
     || (a->ncci_state[ncci] == INC_CON_PENDING)
     || (a->ncci_state[ncci] == INC_ACT_PENDING))
    {
      a->ncci_state[ncci] = OUTG_DIS_PENDING;
      channel_request_xon (plci, a->ncci_ch[ncci]);
      channel_xmit_xon (plci);

      if (a->ncci[ncci].data_pending
       && ((plci->B3_prot == B3_TRANSPARENT)
        || (plci->B3_prot == B3_T30)
        || (plci->B3_prot == B3_T30_WITH_EXTENSIONS)))
      {
        plci->send_disc = (byte)ncci;
        plci->command = 0;
        return FALSE;
      }
      else
      {
        cleanup_ncci_data (plci, ncci);

        if(plci->B3_prot==2 || plci->B3_prot==3)
        {
          ncpi = &parms[0];
          if(ncpi->length>3)
          {
            add_d(plci, (word)(ncpi->length - 3) ,(byte   *)&(ncpi->info[4]));
          }
        }
        nl_req_ncci(plci,N_DISC,(byte)ncci);
      }
      return 1;
    }
  }
  sendf(appl,
        _DISCONNECT_B3_R|CONFIRM,
        Id,
        Number,
        "w",Info);
  return FALSE;
}

byte disconnect_b3_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word ncci;
  word i;

  ncci = (word)(Id>>16);
  dbug(1,dprintf("disconnect_b3_res(ncci=0x%x",ncci));
  if(plci && ncci) {
    plci->requested_options_conn = 0;
    plci->fax_connect_info_length = 0;
    plci->ncpi_state = 0x00;
    if (((plci->B3_prot != B3_T90NL) && (plci->B3_prot != B3_ISO8208) && (plci->B3_prot != B3_X25_DCE))
      && ((plci->B2_prot != B2_LAPD) && (plci->B2_prot != B2_LAPD_FREE_SAPI_SEL)))
    {
      plci->call_dir |= CALL_DIR_FORCE_OUTG_NL;
    }
    for(i=0; i<MAX_CHANNELS_PER_PLCI && plci->inc_dis_ncci_table[i]!=(byte)ncci; i++);
    if(i<MAX_CHANNELS_PER_PLCI) {
      if(plci->channels)plci->channels--;
      for(; i<MAX_CHANNELS_PER_PLCI-1; i++) plci->inc_dis_ncci_table[i] = plci->inc_dis_ncci_table[i+1];
      plci->inc_dis_ncci_table[MAX_CHANNELS_PER_PLCI-1] = 0;

      ncci_free_receive_buffers (plci, ncci);

      if((plci->State==IDLE || plci->State==SUSPENDING) && !plci->channels){
        if(plci->State == SUSPENDING){
          sendf(plci->appl,
                _FACILITY_I,
                Id & 0xffffL,
                0,
                "ws", (word)3, "\x03\x04\x00\x00");
          sendf(plci->appl, _DISCONNECT_I, Id & 0xffffL, 0, "w", 0);
        }
        plci_remove(plci);
        plci->State=IDLE;
      }
    }
    else
    {
      if ((a->manufacturer_features & MANUFACTURER_FEATURE_FAX_PAPER_FORMATS)
       && ((plci->B3_prot == 4) || (plci->B3_prot == 5))
       && (a->ncci_state[ncci] == INC_DIS_PENDING))
      {
        ncci_free_receive_buffers (plci, ncci);

        nl_req_ncci(plci,N_EDATA,(byte)ncci);

        plci->adapter->ncci_state[ncci] = IDLE;
        start_internal_command (Id, plci, fax_disconnect_command);
        return 1;
      }
    }
  }
  return FALSE;
}

byte data_b3_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  NCCI   *ncci_ptr;
  DATA_B3_DESC   *data;
  word Info;
  word ncci;
  word i;

  dbug(1,dprintf("data_b3_req"));

  Info = _WRONG_IDENTIFIER;
  ncci = (word)(Id>>16);
  dbug(1,dprintf("ncci=0x%x, plci=0x%x",ncci,plci));

  if (plci && ncci)
  {
    Info = _WRONG_STATE;
    if ((a->ncci_state[ncci] == CONNECTED)
     || (a->ncci_state[ncci] == INC_ACT_PENDING))
    {
        /* queue data */
      ncci_ptr = &(a->ncci[ncci]);
      i = ncci_ptr->data_out + ncci_ptr->data_pending;
      if (i >= MAX_DATA_B3)
        i -= MAX_DATA_B3;
      data = &(ncci_ptr->DBuffer[i]);
      data->Number = Number;
      if ((((byte   *)(parms[0].info)) >= ((byte   *)(plci->msg_in_queue)))
       && (((byte   *)(parms[0].info)) < ((byte   *)(plci->msg_in_queue)) + sizeof(plci->msg_in_queue)))
      {

        data->P = (byte   *)(*((dword   *)(parms[0].info)));

      }
      else
        data->P = TransmitBufferSet(appl,*(dword *)parms[0].info);
      data->Length = GET_WORD(parms[1].info);
      data->Handle = GET_WORD(parms[2].info);
      data->Flags = GET_WORD(parms[3].info);
      (ncci_ptr->data_pending)++;

        /* check for delivery confirmation */
      if (data->Flags & 0x0004)
      {
        i = ncci_ptr->data_ack_out + ncci_ptr->data_ack_pending;
        if (i >= MAX_DATA_ACK)
          i -= MAX_DATA_ACK;
        ncci_ptr->DataAck[i].Number = data->Number;
        ncci_ptr->DataAck[i].Handle = data->Handle;
        (ncci_ptr->data_ack_pending)++;
      }

      send_data(plci);
      return FALSE;
    }
  }
  if (appl)
  {
    if (plci)
    {
      if ((((byte   *)(parms[0].info)) >= ((byte   *)(plci->msg_in_queue)))
       && (((byte   *)(parms[0].info)) < ((byte   *)(plci->msg_in_queue)) + sizeof(plci->msg_in_queue)))
      {

        TransmitBufferFree (appl, (byte   *)(*((dword   *)(parms[0].info))));

      }
    }
    sendf(appl,
          _DATA_B3_R|CONFIRM,
          Id,
          Number,
          "ww",GET_WORD(parms[2].info),Info);
  }
  return FALSE;
}

byte data_b3_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word n;
  word ncci;
  word NCCIcode;

  dbug(1,dprintf("data_b3_res"));

  ncci = (word)(Id>>16);
  if(plci && ncci) {
    n = GET_WORD(parms[0].info);
    dbug(1,dprintf("free(%d)",n));
    NCCIcode = ncci | (((word) a->Id) << 8);
    if(n<appl->MaxBuffer &&
       appl->DataNCCI[n]==NCCIcode &&
       (byte)(appl->DataFlags[n]>>8)==plci->Id) {
      dbug(1,dprintf("found"));
      appl->DataNCCI[n] = 0;

      if (channel_can_xon (plci, a->ncci_ch[ncci])) {
        channel_request_xon (plci, a->ncci_ch[ncci]);
      }
      channel_xmit_xon (plci);

      if(appl->DataFlags[n] &4) {
        nl_req_ncci(plci,N_DATA_ACK,(byte)ncci);
        return 1;
      }
    }
  }
  return FALSE;
}

byte reset_b3_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word Info;
  word ncci;

  dbug(1,dprintf("reset_b3_req"));

  Info = _WRONG_IDENTIFIER;
  ncci = (word)(Id>>16);
  if(plci && ncci)
  {
    Info = _WRONG_STATE;
    switch (plci->B3_prot)
    {
    case B3_ISO8208:
    case B3_X25_DCE:
      if(a->ncci_state[ncci]==CONNECTED)
      {
        nl_req_ncci(plci,N_RESET,(byte)ncci);
        send_req(plci);
        Info = GOOD;
      }
      break;
    case B3_TRANSPARENT:
      if(a->ncci_state[ncci]==CONNECTED)
      {
        start_internal_command (Id, plci, reset_b3_command);
        Info = GOOD;
      }
      break;
    }
  }
  /* reset_b3 must result in a reset_b3_con & reset_b3_Ind */
  sendf(appl,
        _RESET_B3_R|CONFIRM,
        Id,
        Number,
        "w",Info);
  return FALSE;
}

byte reset_b3_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word ncci;

  dbug(1,dprintf("reset_b3_res"));

  ncci = (word)(Id>>16);
  if(plci && ncci) {
    switch (plci->B3_prot)
    {
    case B3_ISO8208:
    case B3_X25_DCE:
      if(a->ncci_state[ncci]==INC_RES_PENDING)
      {
        a->ncci_state[ncci] = CONNECTED;
        nl_req_ncci(plci,N_RESET_ACK,(byte)ncci);
        return TRUE;
      }
    break;
    }
  }
  return FALSE;
}

byte connect_b3_t90_a_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word ncci;
  API_PARSE * ncpi;
  byte req;

  dbug(1,dprintf("connect_b3_t90_a_res"));

  ncci = (word)(Id>>16);
  if(plci && ncci) {
    if(a->ncci_state[ncci]==INC_ACT_PENDING) {
      a->ncci_state[ncci] = CONNECTED;
    }
    else if(a->ncci_state[ncci]==INC_CON_PENDING) {
      a->ncci_state[ncci] = CONNECTED;

      req = N_CONNECT_ACK;

        /* parms[0]==0 for CAPI original message definition! */
      if(parms[0].info) {
        ncpi = &parms[1];
        if(ncpi->length>2) {
          if(ncpi->info[1] &1) req = N_CONNECT_ACK | N_D_BIT;
          add_d(plci,(word)(ncpi->length-3),&ncpi->info[4]);
        }
      }
      nl_req_ncci(plci,req,(byte)ncci);
      return 1;
    }
  }
  return FALSE;
}


byte select_b_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * msg)
{
  word Info=0;
  word i;
  byte tel;
    API_PARSE bp_parms[7];

  if(!plci || !msg)
  {
    Info = _WRONG_IDENTIFIER;
  }
  else
  {
    dbug(1,dprintf("select_b_req[%d],PLCI=0x%x,Tel=0x%x,NL=0x%x,appl=0x%x,sstate=0x%x",
                   msg->length,plci->Id,plci->tel,plci->NL.Id,plci->appl,plci->SuppState));
    dbug(1,dprintf("PlciState=0x%x",plci->State));
    for(i=0;i<7;i++) bp_parms[i].length = 0;

    /* check if no channel is open, no B3 connected only */
    if((plci->State == IDLE) || (plci->State == OUTG_DIS_PENDING) || (plci->State == INC_DIS_PENDING)
     || (plci->SuppState != IDLE) || plci->channels || plci->nl_remove_id)
    {
      Info = _WRONG_STATE;
    }
    /* check message format and fill bp_parms pointer */
    else if(msg->length && api_parse(&msg->info[1], (word)msg->length, "wwwsss", bp_parms))
    {
      Info = _WRONG_MESSAGE_FORMAT;
    }
    else
    {
      if((plci->State==INC_CON_PENDING) || (plci->State==INC_CON_ALERT)) /* send alert tone inband to the network, */
      {                                                                  /* e.g. Qsig or RBS or Cornet-N or xess PRI */
        if(Id & EXT_CONTROLLER)
        {
          sendf(appl, _SELECT_B_REQ|CONFIRM, Id, Number, "w", 0x2002); /* wrong controller */
          return 0;
        }
        plci->State=INC_CON_CONNECTED_ALERT;
        plci->appl = appl;
        clear_c_ind_mask_bit (plci, (word)(appl->Id-1));
        dump_c_ind_mask (plci);
        for(i=0; i<max_appl; i++) /* disconnect the other appls */
        {                         /* its quasi a connect        */
          if(test_c_ind_mask_bit (plci, i))
            sendf(&application[i], _DISCONNECT_I, Id, 0, "w", _OTHER_APPL_CONNECTED);
        }
      }

      api_save_msg(msg, "s", &plci->saved_msg);
      tel = plci->tel;
      if(Id & EXT_CONTROLLER)
      {
        if(tel) /* external controller in use by this PLCI */
        {
          if(a->AdvSignalAppl && a->AdvSignalAppl!=appl)
          {
            dbug(1,dprintf("Ext_Ctrl in use 1"));
            Info = _WRONG_STATE;
          }
        }
        else  /* external controller NOT in use by this PLCI ? */
        {
          if(a->AdvSignalPLCI)
          {
            dbug(1,dprintf("Ext_Ctrl in use 2"));
            Info = _WRONG_STATE;
          }
          else /* activate the codec */
          {
            dbug(1,dprintf("Ext_Ctrl start"));
            if(AdvCodecSupport(a, plci, appl, 0) )
            {
              dbug(1,dprintf("Error in codec procedures"));
              Info = _WRONG_STATE;
            }
            else if(plci->spoofed_msg==SPOOFING_REQUIRED) /* wait until codec is active */
            {
              plci->spoofed_msg = AWAITING_SELECT_B;
              plci->internal_command = BLOCK_PLCI; /* lock other commands */
              plci->command = 0;
              dbug(1,dprintf("continue if codec loaded"));
              return FALSE;
            }
          }
        }
      }
      else /* external controller bit is OFF */
      {
        if(tel) /* external controller in use, need to switch off */
        {
          if(a->AdvSignalAppl==appl)
          {
            CodecIdCheck(a, plci);
            plci->tel = 0;
            plci->adv_nl = 0;
            dbug(1,dprintf("Ext_Ctrl disable"));
          }
          else
          {
            dbug(1,dprintf("Ext_Ctrl not requested"));
          }
        }
      }
      if (!Info)
      {
        if (plci->call_dir & CALL_DIR_OUT)
          plci->call_dir = CALL_DIR_OUT | CALL_DIR_ORIGINATE;
        else if (plci->call_dir & CALL_DIR_IN)
          plci->call_dir = CALL_DIR_IN | CALL_DIR_ANSWER;
        start_internal_command (Id, plci, select_b_command);
        return FALSE;
      }
    }
  }
  sendf(appl, _SELECT_B_REQ|CONFIRM, Id, Number, "w", Info);
  return FALSE;
}

byte manufacturer_req(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * parms)
{
  word command;
  word i;
  word ncci;
  API_PARSE * m;
    API_PARSE m_parms[5];
  word codec;
  byte req;
  byte ch;
  byte dir;
  static byte chi[2] = {0x01,0x00};
  static byte lli[2] = {0x01,0x00};
  static byte codec_cai[2] = {0x01,0x01};
  static byte null_msg = {0};
  static API_PARSE null_parms = { 0, &null_msg };
  PLCI   * v_plci;
  word Info=0;

  dbug(1,dprintf("manufacturer_req"));
  for(i=0;i<5;i++) m_parms[i].length = 0;

  if(GET_DWORD(parms[0].info)!=_DI_MANU_ID) {
    Info = _WRONG_MESSAGE_FORMAT;
  }
  command = GET_WORD(parms[1].info);
  m = &parms[2];
  if (!Info)
  {
    switch(command) {
    case _DI_ASSIGN_PLCI:
      if(api_parse(&m->info[1],(word)m->length,"wbbs",m_parms)) {
        Info = _WRONG_MESSAGE_FORMAT;
        break;
      }
      codec = GET_WORD(m_parms[0].info);
      ch = m_parms[1].info[0];
      dir = m_parms[2].info[0];
      if((i=get_plci(a))) {
        plci = &a->plci[i-1];
        plci->appl = appl;
        plci->command = _MANUFACTURER_R;
        plci->m_command = command;
        plci->number = Number;
        plci->State = LOCAL_CONNECT;
        Id = ( ((word)plci->Id<<8)|plci->adapter->Id|0x80);
        dbug(1,dprintf("ManCMD,plci=0x%x",Id));

        if((ch==1 || ch==2) && (dir<=2)) {
          chi[1] = (byte)(0x80|ch);
          lli[1] = 0;
          plci->call_dir = CALL_DIR_OUT | CALL_DIR_ORIGINATE;
          switch(codec)
          {
          case 0:
            Info = add_b1(plci,&m_parms[3],0,0);
            break;
          case 1:
            add_p(plci,CAI,codec_cai);
            break;
          /* manual 'swich on' to the codec support without signalling */
          /* first 'assign plci' with this function, then use */
          case 2:
            if(AdvCodecSupport(a, plci, appl, 0) ) {
              Info = _RESOURCE_ERROR;
            }
            else {
              Info = add_b1(plci,&null_parms,0,B1_FACILITY_LOCAL);
              lli[1] = 0x10; /* local call codec stream */
            }
            break;
          }

          plci->State = LOCAL_CONNECT;
          plci->manufacturer = TRUE;
          plci->command = _MANUFACTURER_R;
          plci->m_command = command;
          plci->number = Number;

          if(!Info)
          {
            add_p(plci,LLI,lli);
            add_p(plci,CHI,chi);
            add_p(plci,UID,"\x06\x43\x61\x70\x69\x32\x30");
            sig_req(plci,ASSIGN,DSIG_ID);

            if(!codec)
            {
              Info = add_b23(plci,&m_parms[3]);
              if(!Info)
              {
                nl_req_ncci(plci,ASSIGN,0);
                send_req(plci);
              }
            }
            if(!Info)
            {
              dbug(1,dprintf("dir=0x%x,spoof=0x%x",dir,plci->spoofed_msg));
              if (plci->spoofed_msg==SPOOFING_REQUIRED)
              {
                api_save_msg (m_parms, "wbbs", &plci->saved_msg);
                plci->spoofed_msg = AWAITING_MANUF_CON;
                plci->internal_command = BLOCK_PLCI; /* reject other req meanwhile */
                plci->command = 0;
                send_req(plci);
                return FALSE;
              }
              if(dir==1) {
                sig_req(plci,CALL_REQ,0);
              }
              else if(!dir){
                sig_req(plci,LISTEN_REQ,0);
              }
              send_req(plci);
            }
            else
            {
              sendf(appl,
                    _MANUFACTURER_R|CONFIRM,
                    Id,
                    Number,
                    "dww",_DI_MANU_ID,command,Info);
              return 2;
            }
          }
        }
      }
      else  Info = _OUT_OF_PLCI;
      break;

    case _DI_IDI_CTRL:
      if(!plci)
      {
        Info = _WRONG_IDENTIFIER;
        break;
      }
      if(api_parse(&m->info[1],(word)m->length,"bs",m_parms)) {
        Info = _WRONG_MESSAGE_FORMAT;
        break;
      }
      req = m_parms[0].info[0];
      plci->command = _MANUFACTURER_R;
      plci->m_command = command;
      plci->number = Number;
      if(req==CALL_REQ)
      {
        plci->b_channel = getChannel(&m_parms[1]);
        mixer_set_bchannel_id_esc (plci, plci->b_channel);
        if(plci->spoofed_msg==SPOOFING_REQUIRED)
        {
          plci->spoofed_msg = CALL_REQ | AWAITING_MANUF_CON;
          plci->internal_command = BLOCK_PLCI; /* reject other req meanwhile */
          plci->command = 0;
          break;
        }
      }
      else if(req==LAW_REQ)
      {
        plci->cr_enquiry = TRUE;
      }
      add_ss(plci,FTY,&m_parms[1]);
      sig_req(plci,req,0);
      send_req(plci);
      if(req==HANGUP)
      {      
        if (plci->NL.Id && !plci->nl_remove_id)
        {
          if (plci->channels)
          {
            for (ncci = 1; ncci < MAX_NCCI+1; ncci++)
            {
              if ((a->ncci_plci[ncci] == plci->Id) && (a->ncci_state[ncci] == CONNECTED))
              {
                a->ncci_state[ncci] = OUTG_DIS_PENDING;
                cleanup_ncci_data (plci, ncci);
                nl_req_ncci(plci,N_DISC,(byte)ncci);
              }
            }
          }
          mixer_remove (plci);
          nl_req_ncci(plci,REMOVE,0);
          send_req(plci);
        }  
      }
      break;

    case _DI_SIG_CTRL:
    /* signalling control for loop activation B-channel */
      if(!plci)
      {
        Info = _WRONG_IDENTIFIER;
        break;
      }
      if(m->length){
        plci->command = _MANUFACTURER_R;
        plci->number = Number;
        add_ss(plci,FTY,m);
        sig_req(plci,SIG_CTRL,0);
        send_req(plci);
      }
      else Info = _WRONG_MESSAGE_FORMAT;
      break;

    case _DI_RXT_CTRL:
    /* activation control for receiver/transmitter B-channel */
      if(!plci)
      {
        Info = _WRONG_IDENTIFIER;
        break;
      }
      if(m->length){
        plci->command = _MANUFACTURER_R;
        plci->number = Number;
        add_ss(plci,FTY,m);
        sig_req(plci,DSP_CTRL,0);
        send_req(plci);
      }
      else Info = _WRONG_MESSAGE_FORMAT;
      break;

    case _DI_ADV_CODEC:
    case _DI_DSP_CTRL:
      /* TEL_CTRL commands to support non standard adjustments: */
      /* Ring on/off, Handset micro volume, external micro vol. */
      /* handset+external speaker volume, receiver+transm. gain,*/
      /* handsfree on (hookinfo off), set mixer command         */

      if(command == _DI_ADV_CODEC)
      {
        if(!a->AdvCodecPLCI) {
          Info = _WRONG_STATE;
          break;
        }
        v_plci = a->AdvCodecPLCI;
      }
      else
      {
        if (plci
         && (m->length >= 3)
         && (m->info[1] == 0x1c)
         && (m->info[2] >= 1))
        {
          if (m->info[3] == DSP_CTRL_OLD_SET_MIXER_COEFFICIENTS)
          {
            if ((plci->tel != ADV_VOICE) || (plci != a->AdvSignalPLCI))
            {
              Info = _WRONG_STATE;
              break;
            }
            a->adv_voice_coef_length = m->info[2] - 1;
            if (a->adv_voice_coef_length > m->length - 3)
              a->adv_voice_coef_length = (byte)(m->length - 3);
            if (a->adv_voice_coef_length > ADV_VOICE_COEF_BUFFER_SIZE)
              a->adv_voice_coef_length = ADV_VOICE_COEF_BUFFER_SIZE;
            for (i = 0; i < a->adv_voice_coef_length; i++)
              a->adv_voice_coef_buffer[i] = m->info[4 + i];
            if (plci->B1_facilities & B1_FACILITY_VOICE)
              adv_voice_write_coefs (plci, ADV_VOICE_WRITE_UPDATE);
            break;
          }
          else if (m->info[3] == DSP_CTRL_SET_DTMF_PARAMETERS)
          {
            if (!(a->manufacturer_features & MANUFACTURER_FEATURE_DTMF_PARAMETERS))
            {
              Info = _FACILITY_NOT_SUPPORTED;
              break;
            }

            plci->dtmf_parameter_length = m->info[2] - 1;
            if (plci->dtmf_parameter_length > m->length - 3)
              plci->dtmf_parameter_length = (byte)(m->length - 3);
            if (plci->dtmf_parameter_length > DTMF_PARAMETER_BUFFER_SIZE)
              plci->dtmf_parameter_length = DTMF_PARAMETER_BUFFER_SIZE;
            for (i = 0; i < plci->dtmf_parameter_length; i++)
              plci->dtmf_parameter_buffer[i] = m->info[4+i];
            if (plci->B1_facilities & B1_FACILITY_DTMFR)
              dtmf_parameter_write (plci);
            break;

          }
        }
        v_plci = plci;
      }

      if(!v_plci)
      {
        Info = _WRONG_IDENTIFIER;
        break;
      }
      if(m->length){
        add_ss(v_plci,FTY,m);
        sig_req(v_plci,TEL_CTRL,0);
        send_req(v_plci);
      }
      else Info = _WRONG_MESSAGE_FORMAT;

      break;

    case _DI_OPTIONS_REQUEST:
      if(api_parse(&m->info[1],(word)m->length,"d",m_parms)) {
        Info = _WRONG_MESSAGE_FORMAT;
        break;
      }
      if (GET_DWORD (m_parms[0].info) & ~a->man_profile.private_options)
      {
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
      a->requested_options_table[appl->Id-1] = GET_DWORD (m_parms[0].info);
      break;



    default:
      Info = _WRONG_MESSAGE_FORMAT;
      break;
    }
  }

  sendf(appl,
        _MANUFACTURER_R|CONFIRM,
        Id,
        Number,
        "dww",_DI_MANU_ID,command,Info);
  return FALSE;
}


byte manufacturer_res(dword Id, word Number, DIVA_CAPI_ADAPTER   * a, PLCI   * plci, APPL   * appl, API_PARSE * msg)
{
  word indication;

    API_PARSE m_parms[3];
  API_PARSE *ncpi;
    API_PARSE fax_parms[9];
  word i;
  byte len;


  dbug(1,dprintf("manufacturer_res"));

  if ((msg[0].length == 0)
   || (msg[1].length == 0)
   || (GET_DWORD(msg[0].info)!=_DI_MANU_ID))
  {
    return FALSE;
  }
  indication = GET_WORD(msg[1].info);
  switch (indication)
  {

  case _DI_NEGOTIATE_B3:
    if(!plci)
      break;
    if (((plci->B3_prot != 4) && (plci->B3_prot != 5))
     || !(plci->ncpi_state & NCPI_NEGOTIATE_B3_SENT))
    {
      dbug(1,dprintf("wrong state for NEGOTIATE_B3 parameters"));
      break;
    }
    if (api_parse (&msg[2].info[1], msg[2].length, "ws", m_parms))
    {
      dbug(1,dprintf("wrong format in NEGOTIATE_B3 parameters"));
      break;
    }
    ncpi = &m_parms[1];
    len = ((byte)(((T30_INFO *) 0)->station_id + 20));
    if (plci->fax_connect_info_length < len)
    {
      ((T30_INFO *)(plci->fax_connect_info_buffer))->station_id_len = 0;
      ((T30_INFO *)(plci->fax_connect_info_buffer))->head_line_len = 0;
    }
    if (api_parse (&ncpi->info[1], ncpi->length, "wwwwssss", fax_parms))
    {
      dbug(1,dprintf("non-standard facilities info missing or wrong format"));
    }
    else
    {
      if (plci->fax_connect_info_length <= len)
        plci->fax_connect_info_buffer[len] = 0;
      len += 1 + plci->fax_connect_info_buffer[len];
      if (plci->fax_connect_info_length <= len)
        plci->fax_connect_info_buffer[len] = 0;
      len += 1 + plci->fax_connect_info_buffer[len];
      if ((fax_parms[7].length >= 3) && (fax_parms[7].info[1] >= 2))
        plci->nsf_control_bits = GET_WORD(&fax_parms[7].info[2]);
      plci->fax_connect_info_buffer[len++] = (byte)(fax_parms[7].length);
      for (i = 0; i < fax_parms[7].length; i++)
        plci->fax_connect_info_buffer[len++] = fax_parms[7].info[1+i];
    }
    plci->fax_connect_info_length = len;
    plci->fax_edata_ack_length = plci->fax_connect_info_length;
    start_internal_command (Id, plci, fax_edata_ack_command);
    break;

  }
  return FALSE;
}

/*------------------------------------------------------------------*/
/* IDI callback function                                            */
/*------------------------------------------------------------------*/

void   callback(ENTITY   * e)
{
  DIVA_CAPI_ADAPTER   * a;
  APPL   * appl;
  PLCI   * plci;
  CAPI_MSG   *m;
  word i, j;
  byte rc;
  byte ch;
  byte req;
  byte global_req;
  int no_cancel_rc;

  dbug(1,dprintf("%x:CB(%x:Req=%x,Rc=%x,Ind=%x)",
                 (e->user[0]+1)&0x7fff,e->Id,e->Req,e->Rc,e->Ind));

  a = &(adapter[(byte)e->user[0]]);
  plci = &(a->plci[e->user[1]]);
  no_cancel_rc = DIVA_CAPI_SUPPORTS_NO_CANCEL(a);

  /*
     If new protocol code and new XDI is used then CAPI should work
     fully in accordance with IDI cpec an look on callback field instead
     of Rc field for return codes.
   */
  if (((e->complete == 0xff) && no_cancel_rc) ||
      (e->Rc && !no_cancel_rc)) {
    rc = e->Rc;
    ch = e->RcCh;
    req = e->Req;
    e->Rc = 0;

    if (e->user[0] & 0x8000)
    {
      /*
         If REMOVE request was sent then we have to wait until
         return code with Id set to zero arrives.
         All other return codes should be ignored.
         */
      if (req == REMOVE)
      {
        if (e->Id)
        {
          dbug(1,dprintf("cancel RC in REMOVE state"));
          return;
        }
        channel_flow_control_remove (plci);
        for (i = 0; i < 256; i++)
        {
          if (a->FlowControlIdTable[i] == plci->nl_remove_id)
            a->FlowControlIdTable[i] = 0;
        }
        plci->nl_remove_id = 0;
        if (plci->rx_dma_descriptor > 0) {
          diva_free_dma_descriptor (plci, plci->rx_dma_descriptor - 1);
          plci->rx_dma_descriptor = 0;
        }
      }
      if (rc == OK_FC)
      {
        a->FlowControlIdTable[ch] = e->Id;
        a->FlowControlSkipTable[ch] = 0;

        a->ch_flow_control[ch] |= N_OK_FC_PENDING;
        a->ch_flow_plci[ch] = plci->Id;
        plci->nl_req = 0;
      }
      else
      {
        /*
          Cancel return codes self, if feature was requested
          */
        if (no_cancel_rc && (a->FlowControlIdTable[ch] == e->Id) && e->Id) {
          a->FlowControlIdTable[ch] = 0;
          if ((rc == OK) && a->FlowControlSkipTable[ch]) {
            dbug(3,dprintf ("XDI CAPI: RC cancelled Id:0x02, Ch:%02x",                              e->Id, ch));
            return;
          }
        }

        if (a->ch_flow_control[ch] & N_OK_FC_PENDING)
        {
          a->ch_flow_control[ch] &= ~N_OK_FC_PENDING;
          if (ch == e->ReqCh)
            plci->nl_req = 0;
        }
        else
          plci->nl_req = 0;
      }
      if (plci->nl_req)
        control_rc (plci, 0, rc, ch, 0, TRUE);
      else
      {
        if (req == N_XON)
        {
          channel_x_on (plci, ch);
          if (plci->internal_command)
            control_rc (plci, req, rc, ch, 0, TRUE);
        }
        else
        {
          if (plci->nl_global_req)
          {
            global_req = plci->nl_global_req;
            plci->nl_global_req = 0;
            if (rc != ASSIGN_OK) {
              e->Id = 0;
              if (plci->rx_dma_descriptor > 0) {
                diva_free_dma_descriptor (plci, plci->rx_dma_descriptor - 1);
                plci->rx_dma_descriptor = 0;
              }
            }
            channel_xmit_xon (plci);
            control_rc (plci, 0, rc, ch, global_req, TRUE);
          }
          else if (plci->data_sent)
          {
            channel_xmit_xon (plci);
            plci->data_sent = FALSE;
            plci->NL.XNum = 1;
            data_rc (plci, ch);
            if (plci->internal_command)
              control_rc (plci, req, rc, ch, 0, TRUE);
          }
          else
          {
            channel_xmit_xon (plci);
            control_rc (plci, req, rc, ch, 0, TRUE);
          }
        }
      }
    }
    else
    {
      /*
         If REMOVE request was sent then we have to wait until
         return code with Id set to zero arrives.
         All other return codes should be ignored.
         */
      if (req == REMOVE)
      {
        if (e->Id)
        {
          dbug(1,dprintf("cancel RC in REMOVE state"));
          return;
        }
        plci->sig_remove_id = 0;
      }
      plci->sig_req = 0;
      if (plci->sig_global_req)
      {
        global_req = plci->sig_global_req;
        plci->sig_global_req = 0;
        if (rc != ASSIGN_OK)
          e->Id = 0;
        channel_xmit_xon (plci);
        control_rc (plci, 0, rc, ch, global_req, FALSE);
      }
      else
      {
        channel_xmit_xon (plci);
        control_rc (plci, req, rc, ch, 0, FALSE);
      }
    }
    /*
      Again: in accordance with IDI spec Rc and Ind can't be delivered in the
      same callback. Also if new XDI and protocol code used then jump
      direct to finish.
      */
    if (no_cancel_rc) {
      channel_xmit_xon(plci);
      goto capi_callback_suffix;
    }
  }

  channel_xmit_xon(plci);

  if (e->Ind) {
    if (e->user[0] &0x8000) {
      byte Ind = e->Ind & 0x0f;
      byte Ch = e->IndCh;
      if (((Ind==N_DISC) || (Ind==N_DISC_ACK)) &&
          (a->ch_flow_plci[Ch] == plci->Id)) {
        if (a->ch_flow_control[Ch] & N_RX_FLOW_CONTROL_MASK) {
          dbug(3,dprintf ("XDI CAPI: I: pending N-XON Ch:%02x", Ch));
        }
        a->ch_flow_control[Ch] &= ~N_RX_FLOW_CONTROL_MASK;
      }
      nl_ind(plci);
      if ((e->RNR != 1) &&
          (a->ch_flow_plci[Ch] == plci->Id) &&
          (a->ch_flow_control[Ch] & N_RX_FLOW_CONTROL_MASK)) {
        a->ch_flow_control[Ch] &= ~N_RX_FLOW_CONTROL_MASK;
        dbug(3,dprintf ("XDI CAPI: I: remove faked N-XON Ch:%02x", Ch));
      }
    } else {
      sig_ind(plci);
    }
    e->Ind = 0;
  }

capi_callback_suffix:

  while (!plci->req_in
   && !plci->internal_command
   && (plci->msg_in_write_pos != plci->msg_in_read_pos))
  {
    j = (plci->msg_in_read_pos == plci->msg_in_wrap_pos) ? 0 : plci->msg_in_read_pos;

    i = (((CAPI_MSG   *)(&((byte   *)(plci->msg_in_queue))[j]))->header.length + 3) & 0xfffc;

    m = (CAPI_MSG   *)(&((byte   *)(plci->msg_in_queue))[j]);
    appl = *((APPL   *   *)(&((byte   *)(plci->msg_in_queue))[j+i]));
    dbug(1,dprintf("dequeue msg(0x%04x) - write=%d read=%d wrap=%d",
      m->header.command, plci->msg_in_write_pos, plci->msg_in_read_pos, plci->msg_in_wrap_pos));
    if (plci->msg_in_read_pos == plci->msg_in_wrap_pos)
    {
      plci->msg_in_wrap_pos = MSG_IN_QUEUE_SIZE;
      plci->msg_in_read_pos = i + MSG_IN_OVERHEAD;
    }
    else
    {
      plci->msg_in_read_pos = j + i + MSG_IN_OVERHEAD;
    }
    if (plci->msg_in_read_pos == plci->msg_in_write_pos)
    {
      plci->msg_in_write_pos = MSG_IN_QUEUE_SIZE;
      plci->msg_in_read_pos = MSG_IN_QUEUE_SIZE;
    }
    else if (plci->msg_in_read_pos == plci->msg_in_wrap_pos)
    {
      plci->msg_in_read_pos = MSG_IN_QUEUE_SIZE;
      plci->msg_in_wrap_pos = MSG_IN_QUEUE_SIZE;
    }
    i = api_put (appl, m);
    if (i != 0)
    {
      if (m->header.command == _DATA_B3_R)

        TransmitBufferFree (appl, (byte   *)(m->info.data_b3_req.Data));

      dbug(1,dprintf("Error 0x%04x from msg(0x%04x)", i, m->header.command));
      break;
    }

    if (plci->li_notify_update)
    {
      plci->li_notify_update = FALSE;
      mixer_notify_update (plci, FALSE);
    }

  }
  send_data(plci);
  send_req(plci);
}


void control_rc(PLCI   * plci, byte req, byte rc, byte ch, byte global_req, byte nl_rc)
{
  dword Id;
  dword rId;
  word Number;
  word Info=0;
  word i;
  word ncci;
  DIVA_CAPI_ADAPTER   * a;
  APPL   * appl;
  PLCI   * rplci;
    byte SSparms[]  = "\x05\x00\x00\x02\x00\x00";
    byte SSstruct[] = "\x09\x00\x00\x06\x00\x00\x00\x00\x00\x00";

  if (!plci) {
    dbug(0,dprintf("A: control_rc, no plci %02x:%02x:%02x:%02x:%02x", req, rc, ch, global_req, nl_rc));
    return;
  }
  dbug(1,dprintf("req0_in/out=%d/%d",plci->req_in,plci->req_out));
  if(plci->req_in!=plci->req_out)
  {
    if (nl_rc || (global_req != ASSIGN) || (rc == ASSIGN_OK))
    {
      dbug(1,dprintf("req_1return"));
      return;
    }
    /* cancel outstanding request on the PLCI after SIG ASSIGN failure */
  }
  plci->req_in = plci->req_in_start = plci->req_out = 0;
  dbug(1,dprintf("control_rc"));

  appl = plci->appl;
  a = plci->adapter;
  ncci = a->ch_ncci[ch];
  if(appl)
  {
    Id = (((dword)(ncci ? ncci : ch)) << 16) | ((word)plci->Id << 8) | a->Id;
    if(plci->tel && plci->SuppState!=CALL_HELD) Id|=EXT_CONTROLLER;
    Number = plci->number;
    dbug(1,dprintf("Contr_RC-Id=%08lx,plci=%x,tel=%x, entity=0x%x, command=0x%x, int_command=0x%x",Id,plci->Id,plci->tel,plci->Sig.Id,plci->command,plci->internal_command));
    dbug(1,dprintf("channels=0x%x",plci->channels));
    if (plci_remove_check(plci))
      return;
    if(req==REMOVE && rc==ASSIGN_OK)
    {
      sig_req(plci,HANGUP,0);
      sig_req(plci,REMOVE,0);
      send_req(plci);
    }
    if(plci->command)
    {
      switch(plci->command)
      {
      case C_HOLD_REQ:
        dbug(1,dprintf("HoldRC=0x%x",rc));
        SSparms[1] = (byte)S_HOLD;
        if(rc!=OK)
        {
          plci->SuppState = IDLE;
          Info = 0x2001;
        }
        sendf(appl,_FACILITY_R|CONFIRM,Id,Number,"wws",Info,3,SSparms);
        break;

      case C_RETRIEVE_REQ:
        dbug(1,dprintf("RetrieveRC=0x%x",rc));
        SSparms[1] = (byte)S_RETRIEVE;
        if(rc!=OK)
        {
          plci->SuppState = CALL_HELD;
          Info = 0x2001;
        }
        sendf(appl,_FACILITY_R|CONFIRM,Id,Number,"wws",Info,3,SSparms);
        break;

      case _INFO_R:
        dbug(1,dprintf("InfoRC=0x%x",rc));
        if(rc!=OK) Info=_WRONG_STATE;
        sendf(appl,_INFO_R|CONFIRM,Id,Number,"w",Info);
        break;

      case _CONNECT_R:
        dbug(1,dprintf("Connect_R=0x%x/0x%x/0x%x/0x%x",req,rc,global_req,nl_rc));
        if (plci->State == INC_DIS_PENDING)
          break;
        if(plci->Sig.Id!=0xff)
        {
          if (((global_req == ASSIGN) && (rc != ASSIGN_OK))
           || (!nl_rc && (req == CALL_REQ) && (rc != OK)))
          {
            dbug(1,dprintf("No more IDs/Call_Req failed"));
            sendf(appl,_CONNECT_R|CONFIRM,Id&0xffL,Number,"w",_OUT_OF_PLCI);
            plci_remove(plci);
            plci->State = IDLE;
            break;
          }
          if(plci->State!=LOCAL_CONNECT)plci->State = OUTG_CON_PENDING;
          sendf(appl,_CONNECT_R|CONFIRM,Id,Number,"w",0);
        }
        else /* D-ch activation */
        {
          if (rc != ASSIGN_OK)
          {
            dbug(1,dprintf("No more IDs/X.25 Call_Req failed"));
            sendf(appl,_CONNECT_R|CONFIRM,Id&0xffL,Number,"w",_OUT_OF_PLCI);
            plci_remove(plci);
            plci->State = IDLE;
            break;
          }
          sendf(appl,_CONNECT_R|CONFIRM,Id,Number,"w",0);
          sendf(plci->appl,_CONNECT_ACTIVE_I,Id,0,"sss","","","");
          plci->State = INC_ACT_PENDING;
        }
        break;

      case _CONNECT_I|RESPONSE:
        if (plci->State != INC_DIS_PENDING)
          plci->State = INC_CON_ACCEPT;
        break;

      case _DISCONNECT_R:
        if (plci->State == INC_DIS_PENDING)
          break;
        if(plci->Sig.Id!=0xff)
        {
          plci->State = OUTG_DIS_PENDING;
          sendf(appl,_DISCONNECT_R|CONFIRM,Id,Number,"w",0);
        }
        break;

      case SUSPEND_REQ:
        break;

      case RESUME_REQ:
        break;

      case _CONNECT_B3_R:
        if(rc!=OK)
        {
          sendf(appl,_CONNECT_B3_R|CONFIRM,Id,Number,"w",_WRONG_IDENTIFIER);
          break;
        }
        ncci = get_ncci (plci, ch, 0);
        Id = (Id & 0xffff) | (((dword) ncci) << 16);
        plci->channels++;
        if(req==N_RESET)
        {
          a->ncci_state[ncci] = INC_ACT_PENDING;
          sendf(appl,_CONNECT_B3_R|CONFIRM,Id,Number,"w",0);
          sendf(appl,_CONNECT_B3_ACTIVE_I,Id,0,"s","");
        }
        else
        {
          a->ncci_state[ncci] = OUTG_CON_PENDING;
          sendf(appl,_CONNECT_B3_R|CONFIRM,Id,Number,"w",0);
        }
        break;

      case _CONNECT_B3_I|RESPONSE:
        break;

      case _RESET_B3_R:
/*        sendf(appl,_RESET_B3_R|CONFIRM,Id,Number,"w",0);*/
        break;

      case _DISCONNECT_B3_R:
        sendf(appl,_DISCONNECT_B3_R|CONFIRM,Id,Number,"w",0);
        break;

      case _MANUFACTURER_R:
        break;

      case PERM_LIST_REQ:
        if(rc!=OK)
        {
          Info = _WRONG_IDENTIFIER;
          sendf(plci->appl,_CONNECT_R|CONFIRM,Id,Number,"w",Info);
          plci_remove(plci);
        }
        else
          sendf(plci->appl,_CONNECT_R|CONFIRM,Id,Number,"w",Info);
        break;

      default:
        break;
      }
      plci->command = 0;
    }
    else if (plci->internal_command)
    {
      switch(plci->internal_command)
      {
      case BLOCK_PLCI:
        return;

      case GET_MWI_STATE:
        if(rc==OK) /* command supported, wait for indication */
        {
          return;
        }
        plci_remove(plci);
        break;

        /* Get Supported Services */
      case GETSERV_REQ_PEND:
        if(rc==OK) /* command supported, wait for indication */
        {
          break;
        }
        PUT_DWORD(&SSstruct[6], MASK_TERMINAL_PORTABILITY);
        sendf(appl, _FACILITY_R|CONFIRM, Id, Number, "wws",0,3,SSstruct);
        plci_remove(plci);
        break;

      case INTERR_DIVERSION_REQ_PEND:      /* Interrogate Parameters        */
      case INTERR_NUMBERS_REQ_PEND:
      case CF_START_PEND:                  /* Call Forwarding Start pending */
      case CF_STOP_PEND:                   /* Call Forwarding Stop pending  */
      case CCBS_REQUEST_REQ_PEND:
      case CCBS_DEACTIVATE_REQ_PEND:
      case CCBS_INTERROGATE_REQ_PEND:
        switch(plci->internal_command)
        {
          case INTERR_DIVERSION_REQ_PEND:
            SSparms[1] = S_INTERROGATE_DIVERSION;
            break;
          case INTERR_NUMBERS_REQ_PEND:
            SSparms[1] = S_INTERROGATE_NUMBERS;
            break;
          case CF_START_PEND:
            SSparms[1] = S_CALL_FORWARDING_START;
            break;
          case CF_STOP_PEND:
            SSparms[1] = S_CALL_FORWARDING_STOP;
            break;
          case CCBS_REQUEST_REQ_PEND:
            SSparms[1] = S_CCBS_REQUEST;
            break;
          case CCBS_DEACTIVATE_REQ_PEND:
            SSparms[1] = S_CCBS_DEACTIVATE;
            break;
          case CCBS_INTERROGATE_REQ_PEND:
            SSparms[1] = S_CCBS_INTERROGATE;
            break;
        }
        if(global_req==ASSIGN)
        {
          dbug(1,dprintf("AssignDiversion_RC=0x%x/0x%x",req,rc));
          return;
        }
        if(!plci->appl) break;
        if(rc==ISDN_GUARD_REJ)
        {
          Info = _CAPI_GUARD_ERROR;
        }
        else if(rc!=OK)
        {
          Info = _SUPPLEMENTARY_SERVICE_NOT_SUPPORTED;
        }
        sendf(plci->appl,_FACILITY_R|CONFIRM,Id&0x7,
              plci->number,"wws",Info,(word)3,SSparms);
        if(Info) plci_remove(plci);
        break;

        /* 3pty conference pending */
      case PTY_REQ_PEND:
        if(!plci->relatedPTYPLCI) break;
        rplci = plci->relatedPTYPLCI;
        SSparms[1] = plci->ptyState;
        rId = ((word)rplci->Id<<8)|rplci->adapter->Id;
        if(rplci->tel) rId|=EXT_CONTROLLER;
        if(rc!=OK)
        {
          Info = 0x300E; /* not supported */
          plci->relatedPTYPLCI = NULL;
          plci->ptyState = 0;
        }
        sendf(rplci->appl,
              _FACILITY_R|CONFIRM,
              rId,
              plci->number,
              "wws",Info,(word)3,SSparms);
        break;

        /* Explicit Call Transfer pending */
      case ECT_REQ_PEND:
        dbug(1,dprintf("ECT_RC=0x%x/0x%x",req,rc));
        if(!plci->relatedPTYPLCI) break;
        rplci = plci->relatedPTYPLCI;
        SSparms[1] = S_ECT;
        rId = ((word)rplci->Id<<8)|rplci->adapter->Id;
        if(rplci->tel) rId|=EXT_CONTROLLER;
        if(rc!=OK)
        {
          Info = 0x300E; /* not supported */
          plci->relatedPTYPLCI = NULL;
          plci->ptyState = 0;
        }
        sendf(rplci->appl,
              _FACILITY_R|CONFIRM,
              rId,
              plci->number,
              "wws",Info,(word)3,SSparms);
        break;

      case _MANUFACTURER_R:
        dbug(1,dprintf("_Manufacturer_R=0x%x/0x%x",req,rc));
        if ((global_req == ASSIGN) && (rc != ASSIGN_OK))
        {
          dbug(1,dprintf("No more IDs"));
          sendf(appl,_MANUFACTURER_R|CONFIRM,Id,Number,"dww",_DI_MANU_ID,_MANUFACTURER_R,_OUT_OF_PLCI);
          plci_remove(plci);  /* after codec init, internal codec commands pending */
        }
        break;

      case _CONNECT_R:
        dbug(1,dprintf("_Connect_R=0x%x/0x%x",req,rc));
        if ((global_req == ASSIGN) && (rc != ASSIGN_OK))
        {
          dbug(1,dprintf("No more IDs"));
          sendf(appl,_CONNECT_R|CONFIRM,Id&0xffL,Number,"w",_OUT_OF_PLCI);
          plci_remove(plci);  /* after codec init, internal codec commands pending */
        }
        break;

      case PERM_COD_HOOK:                     /* finished with Hook_Ind */
        return;

      case PERM_COD_CALL:
        dbug(1,dprintf("***Codec Connect_Pending A, Rc = 0x%x",rc));
        plci->internal_command = PERM_COD_CONN_PEND;
        return;

      case PERM_COD_ASSIGN:
        dbug(1,dprintf("***Codec Assign A, Rc = 0x%x",rc));
        if(rc!=ASSIGN_OK) break;
        sig_req(plci,CALL_REQ,0);
        send_req(plci);
        plci->internal_command = PERM_COD_CALL;
        return;

        /* Null Call Reference Request pending */
      case C_NCR_FAC_REQ:
        dbug(1,dprintf("NCR_FAC=0x%x/0x%x",req,rc));
        if(global_req==ASSIGN)
        {
          if(rc==ASSIGN_OK)
          {
            return;
          }
          else
          {
            sendf(appl,_INFO_R|CONFIRM,Id&0xf,Number,"w",_WRONG_STATE);
            appl->NullCREnable = FALSE;
            plci_remove(plci);
          }
        }
        else if(req==NCR_FACILITY)
        {
          if(rc==OK)
          {
            sendf(appl,_INFO_R|CONFIRM,Id&0xf,Number,"w",0);
          }
          else
          {
            sendf(appl,_INFO_R|CONFIRM,Id&0xf,Number,"w",_WRONG_STATE);
            appl->NullCREnable = FALSE;
          }
          plci_remove(plci);
        }
        break;

      case HOOK_ON_REQ:
        if(plci->channels)
        {
          if(a->ncci_state[ncci]==CONNECTED)
          {
            a->ncci_state[ncci] = OUTG_DIS_PENDING;
            cleanup_ncci_data (plci, ncci);
            nl_req_ncci(plci,N_DISC,(byte)ncci);
          }
          break;
        }
        break;

      case HOOK_OFF_REQ:
        if (plci->State == INC_DIS_PENDING)
          break;
        sig_req(plci,CALL_REQ,0);
        send_req(plci);
        plci->State=OUTG_CON_PENDING;
        break;


      case MWI_ACTIVATE_REQ_PEND:
      case MWI_DEACTIVATE_REQ_PEND:
        if(global_req == ASSIGN && rc==ASSIGN_OK)
        {
          dbug(1,dprintf("MWI_REQ assigned"));
          return;
        }
        else if(rc!=OK)
        {                 
          if(rc==WRONG_IE)
          {
            Info = 0x2007; /* Illegal message parameter coding */
            dbug(1,dprintf("MWI_REQ invalid parameter"));
          }
          else
          {
            Info = 0x300B; /* not supported */                      
            dbug(1,dprintf("MWI_REQ not supported"));
          }
          /* 0x3010: Request not allowed in this state */
          PUT_WORD(&SSparms[4],0x300E); /* SS not supported */
                    
        }
        if(plci->internal_command==MWI_ACTIVATE_REQ_PEND)
        {
          PUT_WORD(&SSparms[1],S_MWI_ACTIVATE);
        }
        else PUT_WORD(&SSparms[1],S_MWI_DEACTIVATE);

        if(plci->cr_enquiry)
        {
          sendf(plci->appl,
                _FACILITY_R|CONFIRM,
                Id&0xf,
                plci->number,
                "wws",Info,(word)3,SSparms);
          if(rc!=OK) plci_remove(plci);
        }
        else
        {
          sendf(plci->appl,
                _FACILITY_R|CONFIRM,
                Id,
                plci->number,
                "wws",Info,(word)3,SSparms);
        }
        break;

      case CONF_BEGIN_REQ_PEND:
      case CONF_ADD_REQ_PEND:
      case CONF_SPLIT_REQ_PEND:
      case CONF_DROP_REQ_PEND:
      case CONF_ISOLATE_REQ_PEND:
      case CONF_REATTACH_REQ_PEND:
        dbug(1,dprintf("CONF_RC=0x%x/0x%x",req,rc));
        if((plci->internal_command==CONF_ADD_REQ_PEND)&&(!plci->relatedPTYPLCI)) break;
        rplci = plci;
        rId = Id;
        switch(plci->internal_command)
        {
          case CONF_BEGIN_REQ_PEND:
            SSparms[1] = S_CONF_BEGIN;
            break;
          case CONF_ADD_REQ_PEND:
            SSparms[1] = S_CONF_ADD;
            rplci = plci->relatedPTYPLCI;
            rId = ((word)rplci->Id<<8)|rplci->adapter->Id;
            break;
          case CONF_SPLIT_REQ_PEND:
            SSparms[1] = S_CONF_SPLIT;
            break;
          case CONF_DROP_REQ_PEND:
            SSparms[1] = S_CONF_DROP;
            break;
          case CONF_ISOLATE_REQ_PEND:
            SSparms[1] = S_CONF_ISOLATE;
            break;
          case CONF_REATTACH_REQ_PEND:
            SSparms[1] = S_CONF_REATTACH;
            break;
        }
        
        if(rc!=OK)
        {
          Info = 0x300E; /* not supported */
          plci->relatedPTYPLCI = NULL;
          plci->ptyState = 0;
        }
        sendf(rplci->appl,
              _FACILITY_R|CONFIRM,
              rId,
              plci->number,
              "wws",Info,(word)3,SSparms);
        break;

      case VSWITCH_REQ_PEND:
        if(rc!=OK)
        {
          if(plci->relatedPTYPLCI)
          {
            plci->relatedPTYPLCI->vswitchstate=0;
            plci->relatedPTYPLCI->vsprot=0;
            plci->relatedPTYPLCI->vsprotdialect=0;    
          }
          plci->vswitchstate=0;
          plci->vsprot=0;
          plci->vsprotdialect=0;
        }
        else
        {
          if(plci->relatedPTYPLCI &&
             plci->vswitchstate==1 &&
             plci->relatedPTYPLCI->vswitchstate==3) /* join complete */
            plci->vswitchstate=3;
        }
        break;

  /* Call Deflection Request pending (SSCT) */
      case CD_REQ_PEND:
        SSparms[1] = S_CALL_DEFLECTION;
        if(rc!=OK)
        {
          Info = 0x300E; /* not supported */
          plci->appl->CDEnable = 0;
        }  
        sendf(plci->appl,_FACILITY_R|CONFIRM,Id,
          plci->number,"wws",Info,(word)3,SSparms);
        break;

      case RTP_CONNECT_B3_REQ_COMMAND_2:
        if (rc == OK)
        {
          ncci = get_ncci (plci, ch, 0);
          Id = (Id & 0xffff) | (((dword) ncci) << 16);
          plci->channels++;
          a->ncci_state[ncci] = OUTG_CON_PENDING;
        }

      default:
        if (plci->internal_command_queue[0])
        {
          (*(plci->internal_command_queue[0]))(Id, plci, rc);
          if (plci->internal_command)
            return;
        }
        break;
      }
      next_internal_command (Id, plci);
    }
  }
  else /* appl==0 */
  {
    Id = ((word)plci->Id<<8)|plci->adapter->Id;
    if(plci->tel) Id|=EXT_CONTROLLER;

    switch(plci->internal_command)
    {
    case BLOCK_PLCI:
      return;

    case START_L1_SIG_ASSIGN_PEND:
    case REM_L1_SIG_ASSIGN_PEND:
      if(global_req == ASSIGN)
      {
        break;
      }
      else
      {
        dbug(1,dprintf("***L1 Req rem PLCI"));
        plci->internal_command = 0;
        sig_req(plci,REMOVE,0);
        send_req(plci);
      }
      break;

      /* Call Deflection Request pending, just no appl ptr assigned */
    case CD_REQ_PEND:
      SSparms[1] = S_CALL_DEFLECTION;
      if(rc!=OK)
      {
        Info = 0x300E; /* not supported */
      }
      for(i=0; i<max_appl; i++)
      {
        if(application[i].CDEnable)
        {
          if(!application[i].Id) application[i].CDEnable = 0;
          else
          {
            sendf(&application[i],_FACILITY_R|CONFIRM,Id,
                  plci->number,"wws",Info,(word)3,SSparms);
            if(Info) application[i].CDEnable = 0;
          }
        }
      }
      plci->internal_command = 0;
      break;

    case PERM_COD_HOOK:                   /* finished with Hook_Ind */
      return;

    case PERM_COD_CALL:
      plci->internal_command = PERM_COD_CONN_PEND;
      dbug(1,dprintf("***Codec Connect_Pending, Rc = 0x%x",rc));
      return;

    case PERM_COD_ASSIGN:
      dbug(1,dprintf("***Codec Assign, Rc = 0x%x",rc));
      plci->internal_command = 0;
      if(rc!=ASSIGN_OK) break;
      plci->internal_command = PERM_COD_CALL;
      sig_req(plci,CALL_REQ,0);
      send_req(plci);
      return;

    case LISTEN_SIG_ASSIGN_PEND:
      if(rc == ASSIGN_OK)
      {
        plci->internal_command = 0;
        dbug(1,dprintf("ListenCheck, new SIG_ID = 0x%x",plci->Sig.Id));
        add_p(plci,ESC,"\x02\x18\x00");             /* support call waiting */
        sig_req(plci,INDICATE_REQ,0);
        send_req(plci);
      }
      else
      {
        dbug(1,dprintf("ListenCheck failed (assignRc=0x%x)",rc));
        a->listen_active--;
        plci_remove(plci);
        plci->State = IDLE;
      }
      break;

    case USELAW_REQ:
      if(global_req == ASSIGN)
      {
        if (rc==ASSIGN_OK)
      {
        sig_req(plci,LAW_REQ,0);
        send_req(plci);
        dbug(1,dprintf("Auto-Law assigned"));
        }
        else
        {
          dbug(1,dprintf("Auto-Law assign failed"));
          a->automatic_law = 3;
          plci->internal_command = 0;
          a->automatic_lawPLCI = NULL;
        }
        break;
      }
      else if(req == LAW_REQ && rc==OK)
      {
        dbug(1,dprintf("Auto-Law initiated"));
        a->automatic_law = 2;
        plci->internal_command = 0;
      }
      else
      {
        dbug(1,dprintf("Auto-Law not supported"));
        a->automatic_law = 3;
        plci->internal_command = 0;
        sig_req(plci,REMOVE,0);
        send_req(plci);
        a->automatic_lawPLCI = NULL;
      }
      break;
    }
    plci_remove_check(plci);
  }
}

void data_rc(PLCI   * plci, byte ch)
{
  dword Id;
  DIVA_CAPI_ADAPTER   * a;
  NCCI   *ncci_ptr;
  DATA_B3_DESC   *data;
  word ncci;

  if (plci->appl)
  {
    TransmitBufferFree (plci->appl, plci->data_sent_ptr);
    a = plci->adapter;
    ncci = a->ch_ncci[ch];
    if (ncci && (a->ncci_plci[ncci] == plci->Id))
    {
      ncci_ptr = &(a->ncci[ncci]);
      dbug(1,dprintf("data_out=%d, data_pending=%d",ncci_ptr->data_out,ncci_ptr->data_pending));
      if (ncci_ptr->data_pending)
      {
        data = &(ncci_ptr->DBuffer[ncci_ptr->data_out]);
        if (!(data->Flags &4) && a->ncci_state[ncci])
        {
          Id = (((dword)ncci)<<16)|((word)plci->Id<<8)|a->Id;
          if(plci->tel) Id|=EXT_CONTROLLER;
          sendf(plci->appl,_DATA_B3_R|CONFIRM,Id,data->Number,
                "ww",data->Handle,0);
        }
        (ncci_ptr->data_out)++;
        if (ncci_ptr->data_out == MAX_DATA_B3)
          ncci_ptr->data_out = 0;
        (ncci_ptr->data_pending)--;
      }
    }
  }
}

void data_ack(PLCI   * plci, byte ch)
{
  dword Id;
  DIVA_CAPI_ADAPTER   * a;
  NCCI   *ncci_ptr;
  word ncci;

  a = plci->adapter;
  ncci = a->ch_ncci[ch];
  ncci_ptr = &(a->ncci[ncci]);
  if (ncci_ptr->data_ack_pending)
  {
    if (a->ncci_state[ncci] && (a->ncci_plci[ncci] == plci->Id))
    {
      Id = (((dword)ncci)<<16)|((word)plci->Id<<8)|a->Id;
      if(plci->tel) Id|=EXT_CONTROLLER;
      sendf(plci->appl,_DATA_B3_R|CONFIRM,Id,ncci_ptr->DataAck[ncci_ptr->data_ack_out].Number,
            "ww",ncci_ptr->DataAck[ncci_ptr->data_ack_out].Handle,0);
    }
    (ncci_ptr->data_ack_out)++;
    if (ncci_ptr->data_ack_out == MAX_DATA_ACK)
      ncci_ptr->data_ack_out = 0;
    (ncci_ptr->data_ack_pending)--;
  }
}

void sig_ind(PLCI   * plci)
{
  dword x_Id;
  dword Id;
  dword rId;
  word Number = 0;
  word i;
  word cip;
  dword cip_mask;
  byte   *ie;
  DIVA_CAPI_ADAPTER   * a;
    API_PARSE saved_parms[MAX_MSG_PARMS+1];
#define MAXPARMSIDS 31
    byte   * parms[MAXPARMSIDS];
    byte   * add_i[4];
    byte   * multi_fac_parms[MAX_MULTI_IE];
    byte   * multi_pi_parms [MAX_MULTI_IE];
    byte   * multi_ssext_parms [MAX_MULTI_IE];
    byte   * multi_CiPN_parms [MAX_MULTI_IE];

    byte   * multi_vswitch_parms [MAX_MULTI_IE];

  byte ai_len;
    byte   *esc_chi = "";
    byte   *esc_law = "";
    byte   *pty_cai = "";
    byte   *esc_cr  = "";
    byte   *esc_profile = "";

    byte facility[256];
  PLCI   * tplci = NULL;
  byte chi[] = "\x02\x18\x01";
  byte voice_cai[]  = "\x06\x14\x00\x00\x00\x00\x08";
    byte resume_cau[] = "\x05\x05\x00\x02\x00\x00";
  /* ESC_MSGTYPE must be the last but one message, a new IE has to be */
  /* included before the ESC_MSGTYPE and MAXPARMSIDS has to be incremented */
  /* SMSG is situated at the end because its 0 (for compatibility reasons */
  /* (see Info_Mask Bit 4, first IE. then the message type)           */
    word parms_id[] =
         {MAXPARMSIDS, CPN, 0xff, DSA, OSA, BC, LLC, HLC, ESC_CAUSE, DSP, DT, CHA,
          UUI, CONG_RR, CONG_RNR, ESC_CHI, KEY, CHI, CAU, ESC_LAW,
          RDN, RDX, CONN_NR, RIN, NI, CAI, ESC_CR,
          CST, ESC_PROFILE, 0xff, ESC_MSGTYPE, SMSG};
          /* 14 FTY repl by ESC_CHI */
          /* 18 PI  repl by ESC_LAW */
         /* removed OAD changed to 0xff for future use, OAD is multiIE now */
     word multi_fac_id[] = {1, FTY};
     word multi_pi_id[]  = {1, PI};
     word multi_CiPN_id[]  = {1, OAD};
     word multi_ssext_id[]  = {1, ESC_SSEXT};

     word multi_vswitch_id[]  = {1, ESC_VSWITCH};

  byte   * cau;
  word ncci;
    byte SS_Ind[] = "\x05\x02\x00\x02\x00\x00"; /* Hold_Ind struct*/
    byte CF_Ind[] = "\x09\x02\x00\x06\x00\x00\x00\x00\x00\x00";
    byte Interr_Err_Ind[] = "\x0a\x02\x00\x07\x00\x00\x00\x00\x00\x00\x00\x00\x00\x00";
    byte CONF_Ind[] = "\x09\x16\x00\x06\x00\x00\0x00\0x00\0x00\0x00";
  byte force_mt_info = FALSE;
  byte dir;
  dword d;
  word w;

  a = plci->adapter;
  Id = ((word)plci->Id<<8)|a->Id;
  PUT_WORD(&SS_Ind[4],0x0000);

  if (plci->sig_remove_id)
  {
    plci->Sig.RNR = 2; /* discard */
    dbug(1,dprintf("SIG discard while remove pending"));
    return;
  }
  if(plci->tel && plci->SuppState!=CALL_HELD) Id|=EXT_CONTROLLER;
  dbug(1,dprintf("SigInd-Id=%08lx,plci=%x,tel=%x,state=0x%x,channels=%d,Discflowcl=%d",
    Id,plci->Id,plci->tel,plci->State,plci->channels,plci->hangup_flow_ctrl_timer));
  if(plci->Sig.Ind==CALL_HOLD_ACK && plci->channels)
  {
    plci->Sig.RNR = 1;
    return;
  }
  if(plci->Sig.Ind==HANGUP && plci->channels)
  {
    plci->Sig.RNR = 1;
    plci->hangup_flow_ctrl_timer++;
    /* recover the network layer after timeout */
    if(plci->hangup_flow_ctrl_timer==100)
    {
      dbug(1,dprintf("Exceptional disc"));
      plci->Sig.RNR = 0;
      plci->hangup_flow_ctrl_timer = 0;
      for (ncci = 1; ncci < MAX_NCCI+1; ncci++)
      {
        if (a->ncci_plci[ncci] == plci->Id)
        {
          cleanup_ncci_data (plci, ncci);
          if(plci->channels)plci->channels--;
          if (plci->appl)
            sendf(plci->appl,_DISCONNECT_B3_I, (((dword) ncci) << 16) | Id,0,"ws",0,"");
        }
      }
      if (plci->appl)
        sendf(plci->appl, _DISCONNECT_I, Id, 0, "w", 0);
      plci_remove(plci);
      plci->State=IDLE;
    }
    return;
  }

  /* do first parse the info with no OAD in, because OAD will be converted */
  /* first the multiple facility IE, then mult. progress ind.              */
  /* then the parameters for the info_ind + conn_ind                       */
  IndParse(plci,multi_fac_id,multi_fac_parms,MAX_MULTI_IE);
  IndParse(plci,multi_pi_id,multi_pi_parms,MAX_MULTI_IE);
  IndParse(plci,multi_ssext_id,multi_ssext_parms,MAX_MULTI_IE);

  IndParse(plci,multi_vswitch_id,multi_vswitch_parms,MAX_MULTI_IE);

  IndParse(plci,parms_id,parms,0);
  IndParse(plci,multi_CiPN_id,multi_CiPN_parms,MAX_MULTI_IE);
  esc_chi  = parms[14];
  esc_law  = parms[18];
  pty_cai  = parms[24];
  esc_cr   = parms[25];
  esc_profile = parms[27];
  if(esc_cr[0] && plci)
  {
    if(plci->cr_enquiry && plci->appl)
    {
      plci->cr_enquiry = FALSE;
      /* d = MANU_ID            */
      /* w = m_command          */
      /* b = total length       */
      /* b = indication type    */
      /* b = length of all IEs  */
      /* b = IE1                */
      /* S = IE1 length + cont. */
      /* b = IE2                */
      /* S = IE2 lenght + cont. */
      sendf(plci->appl,
        _MANUFACTURER_I,
        Id,
        0,
        "dwbbbbSbS",_DI_MANU_ID,plci->m_command,
        2+1+1+esc_cr[0]+1+1+esc_law[0],plci->Sig.Ind,1+1+esc_cr[0]+1+1+esc_law[0],ESC,esc_cr,ESC,esc_law);
    }
  }
  /* create the additional info structure                                  */
  add_i[1] = parms[15]; /* KEY of additional info */
  add_i[2] = parms[11]; /* UUI of additional info */
  ai_len = AddInfo(add_i,multi_fac_parms, esc_chi, facility);

  /* the ESC_LAW indicates if u-Law or a-Law is actually used by the card  */
  /* indication returns by the card if requested by the function           */
  /* AutomaticLaw() after driver init                                      */
  if (a->automatic_law<4)
  {
    if(esc_law[0]){
      if(esc_law[2]){
        dbug(0,dprintf("u-Law selected"));
        a->u_law = 1;
      }
      else {
        dbug(0,dprintf("a-Law selected"));
        a->u_law = 0;
      }
      a->automatic_law = 4;
      if(plci==a->automatic_lawPLCI) {
        plci->internal_command = 0;
        sig_req(plci,REMOVE,0);
        send_req(plci);
        a->automatic_lawPLCI = NULL;
      }
    }
    if (esc_profile[0])
    {
      dbug (1, dprintf ("[%06x] CardProfile: %lx %lx %lx %lx %lx",
        UnMapController (a->Id), GET_DWORD (&esc_profile[6]),
        GET_DWORD (&esc_profile[10]), GET_DWORD (&esc_profile[14]),
        GET_DWORD (&esc_profile[18]), GET_DWORD (&esc_profile[46])));

      a->profile.Global_Options &= 0x000000ffL;
      a->profile.B1_Protocols &= 0x000003ffL;
      a->profile.B2_Protocols &= 0x00001fdfL;
      a->profile.B3_Protocols &= 0x000000b7L;

      a->profile.Global_Options &= GET_DWORD (&esc_profile[6]) |
        GL_BCHANNEL_OPERATION_SUPPORTED;
      a->profile.B1_Protocols &= GET_DWORD (&esc_profile[10]);
      a->profile.B2_Protocols &= GET_DWORD (&esc_profile[14]);
      a->profile.B3_Protocols &= GET_DWORD (&esc_profile[18]);
      a->manufacturer_features = GET_DWORD (&esc_profile[46]);
      a->man_profile.private_options = 0;

      if (a->manufacturer_features & MANUFACTURER_FEATURE_ECHO_CANCELLER)
      {
        a->man_profile.private_options |= 1L << PRIVATE_ECHO_CANCELLER;
        a->profile.Global_Options |= GL_ECHO_CANCELLER_SUPPORTED;
      }


      if (a->manufacturer_features & MANUFACTURER_FEATURE_RTP)
        a->man_profile.private_options |= 1L << PRIVATE_RTP;
      a->man_profile.rtp_primary_payloads = GET_DWORD (&esc_profile[50]);
      a->man_profile.rtp_additional_payloads = GET_DWORD (&esc_profile[54]);


      if (a->manufacturer_features & MANUFACTURER_FEATURE_T38)
        a->man_profile.private_options |= 1L << PRIVATE_T38;


      if (a->manufacturer_features & MANUFACTURER_FEATURE_FAX_SUB_SEP_PWD)
        a->man_profile.private_options |= 1L << PRIVATE_FAX_SUB_SEP_PWD;


      if (a->manufacturer_features & MANUFACTURER_FEATURE_V18)
        a->man_profile.private_options |= 1L << PRIVATE_V18;


      if (a->manufacturer_features & MANUFACTURER_FEATURE_DTMF_TONE)
        a->man_profile.private_options |= 1L << PRIVATE_DTMF_TONE;


      if (a->manufacturer_features & MANUFACTURER_FEATURE_PIAFS)
        a->man_profile.private_options |= 1L << PRIVATE_PIAFS;


      if (a->manufacturer_features & MANUFACTURER_FEATURE_FAX_PAPER_FORMATS)
        a->man_profile.private_options |= 1L << PRIVATE_FAX_PAPER_FORMATS;


      if (a->manufacturer_features & MANUFACTURER_FEATURE_VOWN)
        a->man_profile.private_options |= 1L << PRIVATE_VOWN;


      if (a->manufacturer_features & MANUFACTURER_FEATURE_FAX_NONSTANDARD)
        a->man_profile.private_options |= 1L << PRIVATE_FAX_NONSTANDARD;

    }
    else
    {
      a->profile.Global_Options &= 0x0000007fL;
      a->profile.B1_Protocols &= 0x000003dfL;
      a->profile.B2_Protocols &= 0x00001adfL;
      a->profile.B3_Protocols &= 0x000000b7L;
      a->manufacturer_features &= MANUFACTURER_FEATURE_HARDDTMF;
    }
    if (a->manufacturer_features & (MANUFACTURER_FEATURE_HARDDTMF |
      MANUFACTURER_FEATURE_SOFTDTMF_SEND | MANUFACTURER_FEATURE_SOFTDTMF_RECEIVE))
    {
      a->profile.Global_Options |= GL_DTMF_SUPPORTED;
    }
    a->manufacturer_features &= ~MANUFACTURER_FEATURE_OOB_CHANNEL;
    dbug (1, dprintf ("[%06x] Profile: %lx %lx %lx %lx %lx",
      UnMapController (a->Id), a->profile.Global_Options,
      a->profile.B1_Protocols, a->profile.B2_Protocols,
      a->profile.B3_Protocols, a->manufacturer_features));
  }
  /* codec plci for the handset/hook state support is just an internal id  */
  if(plci!=a->AdvCodecPLCI)
  {
    force_mt_info =  SendMultiIE(plci,Id,multi_fac_parms, FTY, 0x20, 0);
    force_mt_info |= SendMultiIE(plci,Id,multi_pi_parms, PI, 0x210, 0);
    SendSSExtInd(NULL,plci,Id,multi_ssext_parms);
    SendInfo(plci,Id, parms, force_mt_info);

    VSwitchReqInd(plci,Id,multi_vswitch_parms);

  }

  /* switch the codec to the b-channel                                     */
  if(esc_chi[0] && plci && !plci->SuppState){
    plci->b_channel = esc_chi[esc_chi[0]]&0x1f;
    mixer_set_bchannel_id_esc (plci, plci->b_channel);
    dbug(1,dprintf("storeChannel=0x%x",plci->b_channel));
    if(plci->tel==ADV_VOICE && plci->appl) {
      SetVoiceChannel(a->AdvCodecPLCI, esc_chi, a);
    }
  }

  if(plci->appl) Number = plci->appl->Number++;

  switch(plci->Sig.Ind) {
  /* Response to Get_Supported_Services request */
  case S_SUPPORTED:
    dbug(1,dprintf("S_Supported"));
    if(!plci->appl) break;
    if(pty_cai[0]==4)
    {
      PUT_DWORD(&CF_Ind[6],GET_DWORD(&pty_cai[1]) );
    }
    else
    {
      PUT_DWORD(&CF_Ind[6],MASK_TERMINAL_PORTABILITY | MASK_HOLD_RETRIEVE);
    }
    PUT_WORD (&CF_Ind[1], 0);
    PUT_WORD (&CF_Ind[4], 0);
    sendf(plci->appl,_FACILITY_R|CONFIRM,Id&0x7,plci->number, "wws",0,3,CF_Ind);
    plci_remove(plci);
    break;
                    
  /* Supplementary Service rejected */
  case S_SERVICE_REJ:
    dbug(1,dprintf("S_Reject=0x%x",pty_cai[5]));
    if(!pty_cai[0]) break;
    switch (pty_cai[5])
    {
    case ECT_EXECUTE:
    case THREE_PTY_END:
    case THREE_PTY_BEGIN:
      if(!plci->relatedPTYPLCI) break;
      tplci = plci->relatedPTYPLCI;
      rId = ( (word)tplci->Id<<8)|tplci->adapter->Id;
      if(tplci->tel) rId|=EXT_CONTROLLER;
      if(pty_cai[5]==ECT_EXECUTE)
      {
        PUT_WORD(&SS_Ind[1],S_ECT);

        plci->vswitchstate=0;
        plci->relatedPTYPLCI->vswitchstate=0;

      }
      else
      {
        PUT_WORD(&SS_Ind[1],pty_cai[5]+3);
      }
      if(pty_cai[2]!=0xff)
      {
        PUT_WORD(&SS_Ind[4],0x3600|(word)pty_cai[2]);
      }
      else
      {
        PUT_WORD(&SS_Ind[4],0x300E);
      }
      plci->relatedPTYPLCI = NULL;
      plci->ptyState = 0;
      sendf(tplci->appl,_FACILITY_I,rId,0,"ws",3, SS_Ind);
      break;

    case CALL_DEFLECTION:
      if(pty_cai[2]!=0xff)
      {
        PUT_WORD(&SS_Ind[4],0x3600|(word)pty_cai[2]);
      }
      else
      {
        PUT_WORD(&SS_Ind[4],0x300E);
      }
      PUT_WORD(&SS_Ind[1],pty_cai[5]);
      for(i=0; i<max_appl; i++)
      {
        if(application[i].CDEnable)
        {
          if(application[i].Id) sendf(&application[i],_FACILITY_I,Id,0,"ws",3, SS_Ind);
          application[i].CDEnable = FALSE;
        }
      }
      break;

    case DEACTIVATION_DIVERSION:
    case ACTIVATION_DIVERSION:
    case DIVERSION_INTERROGATE_CFU:
    case DIVERSION_INTERROGATE_CFB:
    case DIVERSION_INTERROGATE_CFNR:
    case DIVERSION_INTERROGATE_NUM:
    case CCBS_REQUEST:
    case CCBS_DEACTIVATE:
    case CCBS_INTERROGATE:
      if(!plci->appl) break;
      if(pty_cai[2]!=0xff)
      {
        PUT_WORD(&Interr_Err_Ind[4],0x3600|(word)pty_cai[2]);
      }
      else
      {
        PUT_WORD(&Interr_Err_Ind[4],0x300E);
      }
      switch (pty_cai[5])
      {
        case DEACTIVATION_DIVERSION:
          dbug(1,dprintf("Deact_Div"));
          Interr_Err_Ind[0]=0x9;
          Interr_Err_Ind[3]=0x6;
          PUT_WORD(&Interr_Err_Ind[1],S_CALL_FORWARDING_STOP);
          break;
        case ACTIVATION_DIVERSION:
          dbug(1,dprintf("Act_Div"));
          Interr_Err_Ind[0]=0x9;
          Interr_Err_Ind[3]=0x6;
          PUT_WORD(&Interr_Err_Ind[1],S_CALL_FORWARDING_START);
          break;
        case DIVERSION_INTERROGATE_CFU:
        case DIVERSION_INTERROGATE_CFB:
        case DIVERSION_INTERROGATE_CFNR:
          dbug(1,dprintf("Interr_Div"));
          Interr_Err_Ind[0]=0xa;
          Interr_Err_Ind[3]=0x7;
          PUT_WORD(&Interr_Err_Ind[1],S_INTERROGATE_DIVERSION);
          break;
        case DIVERSION_INTERROGATE_NUM:
          dbug(1,dprintf("Interr_Num"));
          Interr_Err_Ind[0]=0xa;
          Interr_Err_Ind[3]=0x7;
          PUT_WORD(&Interr_Err_Ind[1],S_INTERROGATE_NUMBERS);
          break;
        case CCBS_REQUEST:
          dbug(1,dprintf("CCBS Request"));
          Interr_Err_Ind[0]=0xd;
          Interr_Err_Ind[3]=0xa;
          PUT_WORD(&Interr_Err_Ind[1],S_CCBS_REQUEST);
          break;
        case CCBS_DEACTIVATE:
          dbug(1,dprintf("CCBS Deactivate"));
          Interr_Err_Ind[0]=0x9;
          Interr_Err_Ind[3]=0x6;
          PUT_WORD(&Interr_Err_Ind[1],S_CCBS_DEACTIVATE);
          break;
        case CCBS_INTERROGATE:
          dbug(1,dprintf("CCBS Interrogate"));
          Interr_Err_Ind[0]=0xb;
          Interr_Err_Ind[3]=0x8;
          PUT_WORD(&Interr_Err_Ind[1],S_CCBS_INTERROGATE);
          break;
      }
      PUT_DWORD(&Interr_Err_Ind[6],plci->appl->S_Handle);
      sendf(plci->appl,_FACILITY_I,Id&0x7,0,"ws",3, Interr_Err_Ind);
      plci_remove(plci);
      break;
    case ACTIVATION_MWI:      
    case DEACTIVATION_MWI:
      if(pty_cai[5]==ACTIVATION_MWI)
      {
        PUT_WORD(&SS_Ind[1],S_MWI_ACTIVATE);
      }
      else PUT_WORD(&SS_Ind[1],S_MWI_DEACTIVATE);
      
      if(pty_cai[2]!=0xff)
      {
        PUT_WORD(&SS_Ind[4],0x3600|(word)pty_cai[2]);
      }
      else
      {
        PUT_WORD(&SS_Ind[4],0x300E);
      }

      if(plci->cr_enquiry)
      {
        sendf(plci->appl,_FACILITY_I,Id&0xf,0,"ws",3, SS_Ind);
        plci_remove(plci);
      }
      else
      {
        sendf(plci->appl,_FACILITY_I,Id,0,"ws",3, SS_Ind);
      }
      break;
    case CONF_ADD: /* ERROR */
    case CONF_BEGIN:
    case CONF_DROP:
    case CONF_ISOLATE:
    case CONF_REATTACH:
      CONF_Ind[0]=9;
      CONF_Ind[3]=6;   
      switch(pty_cai[5])
      {
      case CONF_BEGIN:
          PUT_WORD(&CONF_Ind[1],S_CONF_BEGIN);
          plci->ptyState = 0;
          break;
      case CONF_DROP:
          CONF_Ind[0]=5;
          CONF_Ind[3]=2;
          PUT_WORD(&CONF_Ind[1],S_CONF_DROP);
          plci->ptyState = CONNECTED;
          break;
      case CONF_ISOLATE:
          CONF_Ind[0]=5;
          CONF_Ind[3]=2;
          PUT_WORD(&CONF_Ind[1],S_CONF_ISOLATE);
          plci->ptyState = CONNECTED;
          break;
      case CONF_REATTACH:
          CONF_Ind[0]=5;
          CONF_Ind[3]=2;
          PUT_WORD(&CONF_Ind[1],S_CONF_REATTACH);
          plci->ptyState = CONNECTED;
          break;
      case CONF_ADD:
          PUT_WORD(&CONF_Ind[1],S_CONF_ADD);
          plci->relatedPTYPLCI = NULL;
          tplci=plci->relatedPTYPLCI;
          if(tplci) tplci->ptyState = CONNECTED;
          plci->ptyState = CONNECTED;
          break;
      }
          
      if(pty_cai[2]!=0xff)
      {
        PUT_WORD(&CONF_Ind[4],0x3600|(word)pty_cai[2]);
      }
      else
      {
        PUT_WORD(&CONF_Ind[4],0x3303); /* Time-out: network did not respond
                                            within the required time */
      }

      PUT_DWORD(&CONF_Ind[6],0x0);
      sendf(plci->appl,_FACILITY_I,Id,0,"ws",3, CONF_Ind);
      break;
    }
    break;

  /* Supplementary Service indicates success */
  case S_SERVICE:
    dbug(1,dprintf("Service_Ind"));
    PUT_WORD (&CF_Ind[4], 0);
    switch (pty_cai[5])
    {
    case THREE_PTY_END:
    case THREE_PTY_BEGIN:
    case ECT_EXECUTE:
      if(!plci->relatedPTYPLCI) break;
      tplci = plci->relatedPTYPLCI;
      rId = ( (word)tplci->Id<<8)|tplci->adapter->Id;
      if(tplci->tel) rId|=EXT_CONTROLLER;
      if(pty_cai[5]==ECT_EXECUTE)
      {
        PUT_WORD(&SS_Ind[1],S_ECT);

        if(plci->vswitchstate!=3)
        {

        plci->ptyState = IDLE;
        plci->relatedPTYPLCI = NULL;
        plci->ptyState = 0;

        }

        dbug(1,dprintf("ECT OK"));
        sendf(tplci->appl,_FACILITY_I,rId,0,"ws",3, SS_Ind);



      }
      else
      {
        switch (plci->ptyState)
        {
        case S_3PTY_BEGIN:
          plci->ptyState = CONNECTED;
          dbug(1,dprintf("3PTY ON"));
          break;

        case S_3PTY_END:
          plci->ptyState = IDLE;
          plci->relatedPTYPLCI = NULL;
          plci->ptyState = 0;
          dbug(1,dprintf("3PTY OFF"));
          break;
        }
        PUT_WORD(&SS_Ind[1],pty_cai[5]+3);
        sendf(tplci->appl,_FACILITY_I,rId,0,"ws",3, SS_Ind);
      }
      break;

    case CALL_DEFLECTION:
      PUT_WORD(&SS_Ind[1],pty_cai[5]);
      for(i=0; i<max_appl; i++)
      {
        if(application[i].CDEnable)
        {
          if(application[i].Id) sendf(&application[i],_FACILITY_I,Id,0,"ws",3, SS_Ind);
          application[i].CDEnable = FALSE;
        }
      }
      break;

    case DEACTIVATION_DIVERSION:
    case ACTIVATION_DIVERSION:
      if(!plci->appl) break;
      PUT_WORD(&CF_Ind[1],pty_cai[5]+2);
      PUT_DWORD(&CF_Ind[6],plci->appl->S_Handle);
      sendf(plci->appl,_FACILITY_I,Id&0x7,0,"ws",3, CF_Ind);
      plci_remove(plci);
      break;

    case DIVERSION_INTERROGATE_CFU:
    case DIVERSION_INTERROGATE_CFB:
    case DIVERSION_INTERROGATE_CFNR:
    case DIVERSION_INTERROGATE_NUM:
    case CCBS_REQUEST:
    case CCBS_DEACTIVATE:
    case CCBS_INTERROGATE:
      if(!plci->appl) break;
      switch (pty_cai[5])
      {
        case DIVERSION_INTERROGATE_CFU:
        case DIVERSION_INTERROGATE_CFB:
        case DIVERSION_INTERROGATE_CFNR:
          dbug(1,dprintf("Interr_Div"));
          PUT_WORD(&pty_cai[1],S_INTERROGATE_DIVERSION);
          pty_cai[3]=pty_cai[0]-3; /* Supplementary Service-specific parameter len */
          break;
        case DIVERSION_INTERROGATE_NUM:
          dbug(1,dprintf("Interr_Num"));
          PUT_WORD(&pty_cai[1],S_INTERROGATE_NUMBERS);
          pty_cai[3]=pty_cai[0]-3; /* Supplementary Service-specific parameter len */
          break;
        case CCBS_REQUEST:
          dbug(1,dprintf("CCBS Request"));
          PUT_WORD(&pty_cai[1],S_CCBS_REQUEST);
          pty_cai[3]=pty_cai[0]-3; /* Supplementary Service-specific parameter len */
          break;
        case CCBS_DEACTIVATE:
          dbug(1,dprintf("CCBS Deactivate"));
          PUT_WORD(&pty_cai[1],S_CCBS_DEACTIVATE);
          pty_cai[3]=pty_cai[0]-3; /* Supplementary Service-specific parameter len */
          break;
        case CCBS_INTERROGATE:
          dbug(1,dprintf("CCBS Interrogate"));
          PUT_WORD(&pty_cai[1],S_CCBS_INTERROGATE);
          pty_cai[3]=pty_cai[0]-3; /* Supplementary Service-specific parameter len */
          break;
      }
      PUT_WORD(&pty_cai[4],0); /* Supplementary Service Reason */
      PUT_DWORD(&pty_cai[6],plci->appl->S_Handle);
      sendf(plci->appl,_FACILITY_I,Id&0x7,0,"wS",3, pty_cai);
      plci_remove(plci);
      break;

    case ACTIVATION_MWI:
    case DEACTIVATION_MWI:
      if(pty_cai[5]==ACTIVATION_MWI)
      {
        PUT_WORD(&SS_Ind[1],S_MWI_ACTIVATE);
      }
      else PUT_WORD(&SS_Ind[1],S_MWI_DEACTIVATE);
      if(plci->cr_enquiry)
      {
        sendf(plci->appl,_FACILITY_I,Id&0xf,0,"ws",3, SS_Ind);
        plci_remove(plci);
      }
      else
      {
        sendf(plci->appl,_FACILITY_I,Id,0,"ws",3, SS_Ind);
      }
      break;
    case MWI_INDICATION:
      if(pty_cai[0]>=0x12)
      {
        PUT_WORD(&pty_cai[3],S_MWI_INDICATE);
        pty_cai[2]=pty_cai[0]-2; /* len Parameter */
        pty_cai[5]=pty_cai[0]-5; /* Supplementary Service-specific parameter len */
        if(plci->appl && (a->Notification_Mask[plci->appl->Id-1]&SMASK_MWI))
        {
          if(plci->internal_command==GET_MWI_STATE) /* result on Message Waiting Listen */
          {
            sendf(plci->appl,_FACILITY_I,Id&0xf,0,"wS",3, &pty_cai[2]);
            plci_remove(plci);
            return;
          }
          else  sendf(plci->appl,_FACILITY_I,Id,0,"wS",3, &pty_cai[2]);
          pty_cai[0]=0;
        }
        else
        {
          for(i=0; i<max_appl; i++)
          {                     
            if(a->Notification_Mask[i]&SMASK_MWI)
            {
              sendf(&application[i],_FACILITY_I,Id&0x7,0,"wS",3, &pty_cai[2]);
              pty_cai[0]=0;
            }
          }
        }

        if(!pty_cai[0])
        { /* acknowledge */
          facility[2]= 0; /* returncode */
        }
        else facility[2]= 0xff;
      }
      else
      {
        /* reject */
        facility[2]= 0xff; /* returncode */
      }
      facility[0]= 2;
      facility[1]= MWI_RESPONSE; /* Function */
      add_p(plci,CAI,facility);
      add_p(plci,ESC,multi_ssext_parms[0]); /* remembered parameter -> only one possible */
      sig_req(plci,S_SERVICE,0);
      send_req(plci);
      plci->command = 0;
      next_internal_command (Id, plci);
      break;
    case CONF_ADD: /* OK */
    case CONF_BEGIN:
    case CONF_DROP:
    case CONF_ISOLATE:
    case CONF_REATTACH:
    case CONF_PARTYDISC:
      CONF_Ind[0]=9;
      CONF_Ind[3]=6;
      switch(pty_cai[5])
      {
      case CONF_BEGIN:
          PUT_WORD(&CONF_Ind[1],S_CONF_BEGIN);
          if(pty_cai[0]==6)
          {
              d=pty_cai[6];
              PUT_DWORD(&CONF_Ind[6],d); /* PartyID */
          }
          else
          {
              PUT_DWORD(&CONF_Ind[6],0x0);
          }
          break;
      case CONF_ISOLATE:
          PUT_WORD(&CONF_Ind[1],S_CONF_ISOLATE);
          CONF_Ind[0]=5;
          CONF_Ind[3]=2;
          break;
      case CONF_REATTACH:
          PUT_WORD(&CONF_Ind[1],S_CONF_REATTACH);
          CONF_Ind[0]=5;
          CONF_Ind[3]=2;
          break;
      case CONF_DROP:
          PUT_WORD(&CONF_Ind[1],S_CONF_DROP);
          CONF_Ind[0]=5;
          CONF_Ind[3]=2;
          break;
      case CONF_ADD:
          PUT_WORD(&CONF_Ind[1],S_CONF_ADD);
          d=pty_cai[6];
          PUT_DWORD(&CONF_Ind[6],d); /* PartyID */
          tplci=plci->relatedPTYPLCI;
          if(tplci) tplci->ptyState = CONNECTED;
          break;
      case CONF_PARTYDISC:
          CONF_Ind[0]=7;
          CONF_Ind[3]=4;          
          PUT_WORD(&CONF_Ind[1],S_CONF_PARTYDISC);
          d=pty_cai[6];
          PUT_DWORD(&CONF_Ind[4],d); /* PartyID */
          break;
      }
      plci->ptyState = CONNECTED;
      sendf(plci->appl,_FACILITY_I,Id,0,"ws",3, CONF_Ind);
      break;
    case CCBS_INFO_RETAIN:
    case CCBS_ERASECALLLINKAGEID:
    case CCBS_STOP_ALERTING:
      CONF_Ind[0]=5;
      CONF_Ind[3]=2;
      switch(pty_cai[5])
      {
      case CCBS_INFO_RETAIN:
        PUT_WORD(&CONF_Ind[1],S_CCBS_INFO_RETAIN);
        break;
      case CCBS_STOP_ALERTING:
        PUT_WORD(&CONF_Ind[1],S_CCBS_STOP_ALERTING);
    break;
      case CCBS_ERASECALLLINKAGEID:
        PUT_WORD(&CONF_Ind[1],S_CCBS_ERASECALLLINKAGEID);
        CONF_Ind[0]=7;
        CONF_Ind[3]=4;
        CONF_Ind[6]=0;
        CONF_Ind[7]=0;
        break;
      }      
      w=pty_cai[6];
      PUT_WORD(&CONF_Ind[4],w); /* PartyID */

      if(plci->appl && (a->Notification_Mask[plci->appl->Id-1]&SMASK_CCBS))
      {
        sendf(plci->appl,_FACILITY_I,Id,0,"ws",3, CONF_Ind);
      }
      else
      {
        for(i=0; i<max_appl; i++)
            if(a->Notification_Mask[i]&SMASK_CCBS)
                sendf(&application[i],_FACILITY_I,Id&0x7,0,"ws",3, CONF_Ind);
      }
      break;
    }
    break;
  case CALL_HOLD_REJ:
    cau = parms[7];
    if(cau)
    {
      i = _L3_CAUSE | cau[2];
      if(cau[2]==0) i = 0x3603;
    }
    else
    {
      i = 0x3603;
    }
    PUT_WORD(&SS_Ind[1],S_HOLD);
    PUT_WORD(&SS_Ind[4],i);
    if(plci->SuppState == HOLD_REQUEST)
    {
      plci->SuppState = IDLE;
      sendf(plci->appl,_FACILITY_I,Id,0,"ws",3, SS_Ind);
    }
    break;

  case CALL_HOLD_ACK:
    if(plci->SuppState == HOLD_REQUEST)
    {
      plci->SuppState = CALL_HELD;
      CodecIdCheck(a, plci);
      start_internal_command (Id, plci, hold_save_command);
    }
    break;

  case CALL_RETRIEVE_REJ:
    cau = parms[7];
    if(cau)
    {
      i = _L3_CAUSE | cau[2];
      if(cau[2]==0) i = 0x3603;
    }
    else
    {
      i = 0x3603;
    }
    PUT_WORD(&SS_Ind[1],S_RETRIEVE);
    PUT_WORD(&SS_Ind[4],i);
    if(plci->SuppState == RETRIEVE_REQUEST)
    {
      plci->SuppState = CALL_HELD;
      CodecIdCheck(a, plci);
      sendf(plci->appl,_FACILITY_I,Id,0,"ws",3, SS_Ind);
    }
    break;

  case CALL_RETRIEVE_ACK:
    PUT_WORD(&SS_Ind[1],S_RETRIEVE);
    if(plci->SuppState == RETRIEVE_REQUEST)
    {
      plci->SuppState = IDLE;
      plci->call_dir |= CALL_DIR_FORCE_OUTG_NL;
      plci->b_channel = esc_chi[esc_chi[0]]&0x1f;
      if(plci->tel)
      {
        mixer_set_bchannel_id_esc (plci, plci->b_channel);
        dbug(1,dprintf("RetrChannel=0x%x",plci->b_channel));
        SetVoiceChannel(a->AdvCodecPLCI, esc_chi, a);
        if(plci->B2_prot==B2_TRANSPARENT && plci->B3_prot==B3_TRANSPARENT)
        {
          dbug(1,dprintf("Get B-ch"));
          start_internal_command (Id, plci, retrieve_restore_command);
        }
        else
          sendf(plci->appl,_FACILITY_I,Id,0,"ws",3, SS_Ind);
      }
      else
        start_internal_command (Id, plci, retrieve_restore_command);
    }
    break;

  case INDICATE_IND:
    if(plci->State != LISTENING) {
      sig_req(plci,HANGUP,0);
      send_req(plci);
      break;
    }
    cip = find_cip(a,parms[4],parms[6]);
    cip_mask = 1L<<cip;
    dbug(1,dprintf("cip=%d,cip_mask=%lx",cip,cip_mask));
    clear_c_ind_mask (plci);
    if (!remove_started && !a->adapter_disabled)
    {
      set_c_ind_mask_bit (plci, MAX_APPL);
      group_optimization(a, plci);
      for(i=0; i<max_appl; i++) {
        if(application[i].Id
        && (a->CIP_Mask[i]&1 || a->CIP_Mask[i]&cip_mask)
        && CPN_filter_ok(parms[0],a,i)
        && test_group_ind_mask_bit (plci, i) ) {
          dbug(1,dprintf("storedcip_mask[%d]=0x%lx",i,a->CIP_Mask[i] ));
          set_c_ind_mask_bit (plci, i);
          dump_c_ind_mask (plci);
          plci->State = INC_CON_PENDING;
          plci->call_dir = (plci->call_dir & ~(CALL_DIR_OUT | CALL_DIR_ORIGINATE)) |
            CALL_DIR_IN | CALL_DIR_ANSWER;
          if(esc_chi[0]) {
            plci->b_channel = esc_chi[esc_chi[0]]&0x1f;
            mixer_set_bchannel_id_esc (plci, plci->b_channel);
          }
          /* if a listen on the ext controller is done, check if hook states */
          /* are supported or if just a on board codec must be activated     */
          if(a->codec_listen[i] && !a->AdvSignalPLCI) {
            if(a->profile.Global_Options & HANDSET)
              plci->tel = ADV_VOICE;
            else if(a->profile.Global_Options & ON_BOARD_CODEC)
              plci->tel = CODEC;
            if(plci->tel) Id|=EXT_CONTROLLER;
            a->codec_listen[i] = plci;
          }

          sendf(&application[i],_CONNECT_I,Id,0,
                "wSSSSSSSbSSSSS", cip,    /* CIP                 */
                             parms[0],    /* CalledPartyNumber   */
                             multi_CiPN_parms[0],    /* CallingPartyNumber  */
                             parms[2],    /* CalledPartySubad    */
                             parms[3],    /* CallingPartySubad   */
                             parms[4],    /* BearerCapability    */
                             parms[5],    /* LowLC               */
                             parms[6],    /* HighLC              */
                             ai_len,      /* nested struct add_i */
                             add_i[0],    /* B channel info    */
                             add_i[1],    /* keypad facility   */
                             add_i[2],    /* user user data    */
                             add_i[3],    /* nested facility   */
                             multi_CiPN_parms[1]    /* second CiPN(SCR)   */
                             );
          SendSSExtInd(&application[i],
                        plci,
                        Id,
                        multi_ssext_parms);
          SendSetupInfo(&application[i],
                        plci,
                        Id,
                        parms,
                        SendMultiIE(plci,Id,multi_pi_parms, PI, 0x210, TRUE));
        }
      }
      clear_c_ind_mask_bit (plci, MAX_APPL);
      dump_c_ind_mask (plci);
    }
    if(c_ind_mask_empty (plci)) {
      sig_req(plci,HANGUP,0);
      send_req(plci);
      plci->State = IDLE;
    }
    plci->notifiedcall = 0;
    a->listen_active--;
    listen_check(a);
    break;

  case CALL_PEND_NOTIFY:
    plci->notifiedcall = 1;
    listen_check(a);
    break;

  case CALL_IND:
  case CALL_CON:
    if(plci->State==ADVANCED_VOICE_SIG || plci->State==ADVANCED_VOICE_NOSIG)
    {
      if(plci->internal_command==PERM_COD_CONN_PEND)
      {
        if(plci->State==ADVANCED_VOICE_NOSIG)
        {
          dbug(1,dprintf("***Codec OK"));
          if(a->AdvSignalPLCI)
          {
            tplci = a->AdvSignalPLCI;
            if(tplci->spoofed_msg)
            {
              dbug(1,dprintf("***Spoofed Msg(0x%x)",tplci->spoofed_msg));
              tplci->command = 0;
              tplci->internal_command = 0;
              x_Id = ((word)tplci->Id<<8)|tplci->adapter->Id | 0x80;
              switch (tplci->spoofed_msg)
              {
              case CALL_RES:
                tplci->command = _CONNECT_I|RESPONSE;
                api_load_msg (&tplci->saved_msg, saved_parms);
                add_b1(tplci,&saved_parms[1],0,tplci->B1_facilities);
                if (tplci->adapter->Info_Mask[tplci->appl->Id-1] & 0x200)
                {
                  /* early B3 connect (CIP mask bit 9) no release after a disc */
                  add_p(tplci,LLI,"\x01\x01");
                }
                add_s(tplci, CONN_NR, &saved_parms[2]);
                add_s(tplci, LLC, &saved_parms[4]);
                add_ai(tplci, &saved_parms[5]);
                tplci->State = INC_CON_ACCEPT;
                sig_req(tplci, CALL_RES,0);
                send_req(tplci);
                break;

              case AWAITING_SELECT_B:
                dbug(1,dprintf("Select_B continue"));
                start_internal_command (x_Id, tplci, select_b_command);
                break;

              case AWAITING_MANUF_CON: /* Get_Plci per Manufacturer_Req to ext controller */
                if(!tplci->Sig.Id)
                {
                  dbug(1,dprintf("No SigID!"));
                  sendf(tplci->appl, _MANUFACTURER_R|CONFIRM,x_Id,tplci->number, "dww",_DI_MANU_ID,_MANUFACTURER_R,_OUT_OF_PLCI);
                  plci_remove(tplci);
                  break;
                }
                tplci->command = _MANUFACTURER_R;
                api_load_msg (&tplci->saved_msg, saved_parms);
                dir = saved_parms[2].info[0];
                if(dir==1) {
                  sig_req(tplci,CALL_REQ,0);
                }
                else if(!dir){
                  sig_req(tplci,LISTEN_REQ,0);
                }
                send_req(tplci);
                sendf(tplci->appl, _MANUFACTURER_R|CONFIRM,x_Id,tplci->number, "dww",_DI_MANU_ID,_MANUFACTURER_R,0);
                break;

              case (CALL_REQ|AWAITING_MANUF_CON):
                sig_req(tplci,CALL_REQ,0);
                send_req(tplci);
                break;

              case CALL_REQ:
                if(!tplci->Sig.Id)
                {
                  dbug(1,dprintf("No SigID!"));
                  sendf(tplci->appl,_CONNECT_R|CONFIRM,tplci->adapter->Id,0,"w",_OUT_OF_PLCI);
                  plci_remove(tplci);
                  break;
                }
                tplci->command = _CONNECT_R;
                api_load_msg (&tplci->saved_msg, saved_parms);
                add_s(tplci,CPN,&saved_parms[1]);
                add_s(tplci,DSA,&saved_parms[3]);
                add_ai(tplci,&saved_parms[9]);
                sig_req(tplci,CALL_REQ,0);
                send_req(tplci);
                break;

              case CALL_RETRIEVE:
                tplci->command = C_RETRIEVE_REQ;
                sig_req(tplci,CALL_RETRIEVE,0);
                send_req(tplci);
                break;
              }
              tplci->spoofed_msg = 0;
              if (tplci->internal_command == 0)
                next_internal_command (x_Id, tplci);
            }
          }
          next_internal_command (Id, plci);
          break;
        }
        dbug(1,dprintf("***Codec Hook Init Req"));
        plci->internal_command = PERM_COD_HOOK;
        add_p(plci,FTY,"\x01\x09");             /* Get Hook State*/
        sig_req(plci,TEL_CTRL,0);
        send_req(plci);
      }
    }
    else if(plci->command != _MANUFACTURER_R  /* old style permanent connect */
    && plci->State!=INC_ACT_PENDING)
    {
      mixer_set_bchannel_id_esc (plci, plci->b_channel);
      if(plci->tel == ADV_VOICE && plci->SuppState == IDLE) /* with permanent codec switch on immediately */
      {
        chi[2] = plci->b_channel;
        SetVoiceChannel(a->AdvCodecPLCI, chi, a);
      }
      sendf(plci->appl,_CONNECT_ACTIVE_I,Id,0,"Sss",parms[21],"","");
      plci->State = INC_ACT_PENDING;
    }
    break;

  case TEL_CTRL:
    Number = 0;
    ie = multi_fac_parms[0]; /* inspect the facility hook indications */
    if(plci->State==ADVANCED_VOICE_SIG && ie[0]){
      switch (ie[1]&0x91) {
        case 0x80:   /* hook off */
        case 0x81:
          if(plci->internal_command==PERM_COD_HOOK)
          {
            dbug(1,dprintf("init:hook_off"));
            plci->hook_state = ie[1];
            next_internal_command (Id, plci);
            break;
          }
          else /* ignore doubled hook indications */
          {
            if( ((plci->hook_state)&0xf0)==0x80)
            {
              dbug(1,dprintf("ignore hook"));
              break;
            }
            plci->hook_state = ie[1]&0x91;
          }
          /* check for incoming call pending */
          /* and signal '+'.Appl must decide */
          /* with connect_res if call must   */
          /* accepted or not                 */
          for(i=0, tplci=NULL;i<max_appl;i++){
            if(a->codec_listen[i]
            && (a->codec_listen[i]->State==INC_CON_PENDING
              ||a->codec_listen[i]->State==INC_CON_ALERT) ){
              tplci = a->codec_listen[i];
              tplci->appl = &application[i];
            }
          }
          /* no incoming call, do outgoing call */
          /* and signal '+' if outg. setup   */
          if(!a->AdvSignalPLCI && !tplci){
            if((i=get_plci(a))) {
              a->AdvSignalPLCI = &a->plci[i-1];
              tplci = a->AdvSignalPLCI;
              tplci->tel  = ADV_VOICE;
              PUT_WORD(&voice_cai[5],a->AdvSignalAppl->MaxDataLength);
              if (a->Info_Mask[a->AdvSignalAppl->Id-1] & 0x200){
                /* early B3 connect (CIP mask bit 9) no release after a disc */
                add_p(tplci,LLI,"\x01\x01");
              }
              add_p(tplci, CAI, voice_cai);
              add_p(tplci, OAD, a->TelOAD);
              add_p(tplci, OSA, a->TelOSA);
              add_p(tplci,SHIFT|6,NULL);
              add_p(tplci,SIN,"\x02\x01\x00");
              add_p(tplci,UID,"\x06\x43\x61\x70\x69\x32\x30");
              sig_req(tplci,ASSIGN,DSIG_ID);
              a->AdvSignalPLCI->internal_command = HOOK_OFF_REQ;
              a->AdvSignalPLCI->command = 0;
              tplci->appl = a->AdvSignalAppl;
              tplci->call_dir = CALL_DIR_OUT | CALL_DIR_ORIGINATE;
              send_req(tplci);
            }

          }

          if(!tplci) break;
          Id = ((word)tplci->Id<<8)|a->Id;
          Id|=EXT_CONTROLLER;
          sendf(tplci->appl,
                _FACILITY_I,
                Id,
                0,
                "ws", (word)0, "\x01+");
          break;

        case 0x90:   /* hook on  */
        case 0x91:
          if(plci->internal_command==PERM_COD_HOOK)
          {
            dbug(1,dprintf("init:hook_on"));
            plci->hook_state = ie[1]&0x91;
            next_internal_command (Id, plci);
            break;
          }
          else /* ignore doubled hook indications */
          {
            if( ((plci->hook_state)&0xf0)==0x90) break;
            plci->hook_state = ie[1]&0x91;
          }
          /* hangup the adv. voice call and signal '-' to the appl */
          if(a->AdvSignalPLCI) {
            Id = ((word)a->AdvSignalPLCI->Id<<8)|a->Id;
            if(plci->tel) Id|=EXT_CONTROLLER;
            sendf(a->AdvSignalAppl,
                  _FACILITY_I,
                  Id,
                  0,
                  "ws", (word)0, "\x01-");
            a->AdvSignalPLCI->internal_command = HOOK_ON_REQ;
            a->AdvSignalPLCI->command = 0;
            sig_req(a->AdvSignalPLCI,HANGUP,0);
            send_req(a->AdvSignalPLCI);
          }
          break;
      }
    }
    break;

  case RESUME:
    clear_c_ind_mask_bit (plci, (word)(plci->appl->Id-1));
    PUT_WORD(&resume_cau[4],GOOD);
    sendf(plci->appl,_FACILITY_I,Id,0,"ws", (word)3, resume_cau);
    break;

  case SUSPEND:
    clear_c_ind_mask (plci);

    if (plci->NL.Id && !plci->nl_remove_id) {
      mixer_remove (plci);
      nl_req_ncci(plci,REMOVE,0);
    }
    if (!plci->sig_remove_id) {
      plci->internal_command = 0;
      sig_req(plci,REMOVE,0);
    }
    send_req(plci);
    if(!plci->channels) {
      sendf(plci->appl,_FACILITY_I,Id,0,"ws", (word)3, "\x05\x04\x00\x02\x00\x00");
      sendf(plci->appl, _DISCONNECT_I, Id, 0, "w", 0);
    }
    break;

  case SUSPEND_REJ:
    break;

  case HANGUP:
    plci->hangup_flow_ctrl_timer=0;
    if(plci->manufacturer && plci->State==LOCAL_CONNECT) break;
    cau = parms[7];
    if(cau) {
      i = _L3_CAUSE | cau[2];
      if(cau[2]==0) i = 0;
      else if(cau[2]==8) i = _L1_ERROR;
      else if(cau[2]==9 || cau[2]==10) i = _L2_ERROR;
      else if(cau[2]==5) i = _CAPI_GUARD_ERROR;
    }
    else {
      i = _L3_ERROR;
    }

    if(plci->State==INC_CON_PENDING || plci->State==INC_CON_ALERT)
    {
      for(i=0; i<max_appl; i++)
      {
        if(test_c_ind_mask_bit (plci, i))
          sendf(&application[i], _DISCONNECT_I, Id, 0, "w", 0);
      }
    }
    else
    {
      clear_c_ind_mask (plci);
    }
    if(!plci->appl)
    {
      if (plci->State == LISTENING)
      {
        plci->notifiedcall=0;
        a->listen_active--;
      }
      plci->State = INC_DIS_PENDING;
      if(c_ind_mask_empty (plci))
      {
        plci->State = IDLE;
        if (plci->NL.Id && !plci->nl_remove_id)
        {
          mixer_remove (plci);
          nl_req_ncci(plci,REMOVE,0);
        }
        if (!plci->sig_remove_id)
        {
          plci->internal_command = 0;
          sig_req(plci,REMOVE,0);
        }
        send_req(plci);
      }
    }
    else
    {
        /* collision of DISCONNECT or CONNECT_RES with HANGUP can   */
        /* result in a second HANGUP! Don't generate another        */
        /* DISCONNECT                                               */
      if(plci->State!=IDLE && plci->State!=INC_DIS_PENDING)
      {
        if(plci->State==RESUMING)
        {
          PUT_WORD(&resume_cau[4],i);
          sendf(plci->appl,_FACILITY_I,Id,0,"ws", (word)3, resume_cau);
        }
        plci->State = INC_DIS_PENDING;
        sendf(plci->appl,_DISCONNECT_I,Id,0,"w",i);
      }
    }
    break;

  case SSEXT_IND:
    SendSSExtInd(NULL,plci,Id,multi_ssext_parms);
    break;

  case VSWITCH_REQ:
    VSwitchReqInd(plci,Id,multi_vswitch_parms);
    break;
  case VSWITCH_IND:
 if(plci->relatedPTYPLCI &&
  plci->vswitchstate==3 &&
  plci->relatedPTYPLCI->vswitchstate==3 &&
  parms[MAXPARMSIDS-1][0])
 {
  add_p(plci->relatedPTYPLCI,SMSG,parms[MAXPARMSIDS-1]);
  sig_req(plci->relatedPTYPLCI,VSWITCH_REQ,0);
  send_req(plci->relatedPTYPLCI);
 }
    else VSwitchReqInd(plci,Id,multi_vswitch_parms);
    break;

  }
}


static void SendSetupInfo(APPL   * appl, PLCI   * plci, dword Id, byte   * * parms, byte Info_Sent_Flag)
{
  word i;
  byte   * ie;
  word Info_Number;
  byte   * Info_Element;
  word Info_Mask = 0;

  dbug(1,dprintf("SetupInfo"));

  for(i=0; i<MAXPARMSIDS; i++) {
    ie = parms[i];
    Info_Number = 0;
    Info_Element = ie;
    if(ie[0]) {
      switch(i) {
      case 0:
        dbug(1,dprintf("CPN "));
        Info_Number = 0x0070;
        Info_Mask   = 0x80;
        Info_Sent_Flag = TRUE;
        break;
      case 8:  /* display      */
        dbug(1,dprintf("display(%d)",i));
        Info_Number = 0x0028;
        Info_Mask = 0x04;
        Info_Sent_Flag = TRUE;
        break;
      case 16: /* Channel Id */
        dbug(1,dprintf("CHI"));
        Info_Number = 0x0018;
        Info_Mask = 0x100;
        Info_Sent_Flag = TRUE;
        mixer_set_bchannel_id (plci, Info_Element);
        break;
      case 19: /* Redirected Number */
        dbug(1,dprintf("RDN"));
        Info_Number = 0x0074;
        Info_Mask = 0x400;
        Info_Sent_Flag = TRUE;
        break;
      case 20: /* Redirected Number extended */
        dbug(1,dprintf("RDX"));
        Info_Number = 0x0073;
        Info_Mask = 0x400;
        Info_Sent_Flag = TRUE;
        break;
      case 22: /* Redirecing Number  */
        dbug(1,dprintf("RIN"));
        Info_Number = 0x0076;
        Info_Mask = 0x400;
        Info_Sent_Flag = TRUE;
        break;
      default:
        Info_Number = 0;
        break;
      }
    }

    if(i==MAXPARMSIDS-2){ /* to indicate the message type "Setup" */
      Info_Number = 0x8000 |5;
      Info_Mask = 0x10;
      Info_Element = "";
    }

    if(Info_Sent_Flag && Info_Number){
      if(plci->adapter->Info_Mask[appl->Id-1] & Info_Mask) {
        sendf(appl,_INFO_I,Id,0,"wS",Info_Number,Info_Element);
      }
    }
  }
}


void SendInfo(PLCI   * plci, dword Id, byte   * * parms, byte iesent)
{
  word i;
  word j;
  word k;
  byte   * ie;
  word Info_Number;
  byte   * Info_Element;
  word Info_Mask = 0;
  static byte charges[5] = {4,0,0,0,0};
  static byte cause[] = {0x02,0x80,0x00};
  APPL   *appl;

  dbug(1,dprintf("InfoParse "));

  if(
        !plci->appl
        && !plci->State
        && plci->Sig.Ind!=NCR_FACILITY
      )
  {
    dbug(1,dprintf("NoParse "));
    return;
  }
  cause[2] = 0;
  for(i=0; i<MAXPARMSIDS; i++) {
    ie = parms[i];
    Info_Number = 0;
    Info_Element = ie;
    if(ie[0]) {
      switch(i) {
      case 0:
        dbug(1,dprintf("CPN "));
        Info_Number = 0x0070;
        Info_Mask   = 0x80;
        break;
      case 7: /* ESC_CAU */
        dbug(1,dprintf("cau(0x%x)",ie[2]));
        Info_Number = 0x0008;
        Info_Mask = 0x00;
        cause[2] = ie[2];
        Info_Element = NULL;
        break;
      case 8:  /* display      */
        dbug(1,dprintf("display(%d)",i));
        Info_Number = 0x0028;
        Info_Mask = 0x04;
        break;
      case 9:  /* Date display */
        dbug(1,dprintf("date(%d)",i));
        Info_Number = 0x0029;
        Info_Mask = 0x02;
        break;
      case 10: /* charges */
        for(j=0;j<4;j++) charges[1+j] = 0;
        for(j=0; j<ie[0] && !(ie[1+j]&0x80); j++);
        for(k=1,j++; j<ie[0] && k<=4; j++,k++) charges[k] = ie[1+j];
        Info_Number = 0x4000;
        Info_Mask = 0x40;
        Info_Element = charges;
        break;
      case 11: /* user user info */
        dbug(1,dprintf("uui"));
        Info_Number = 0x007E;
        Info_Mask = 0x08;
        break;
      case 12: /* congestion receiver ready */
        dbug(1,dprintf("clRDY"));
        Info_Number = 0x00B0;
        Info_Mask = 0x08;
        Info_Element = "";
        break;
      case 13: /* congestion receiver not ready */
        dbug(1,dprintf("clNRDY"));
        Info_Number = 0x00BF;
        Info_Mask = 0x08;
        Info_Element = "";
        break;
      case 15: /* Keypad Facility */
        dbug(1,dprintf("KEY"));
        Info_Number = 0x002C;
        Info_Mask = 0x20;
        break;
      case 16: /* Channel Id */
        dbug(1,dprintf("CHI"));
        Info_Number = 0x0018;
        Info_Mask = 0x100;
        mixer_set_bchannel_id (plci, Info_Element);
        break;
      case 17: /* if no 1tr6 cause, send full cause, else esc_cause */
        dbug(1,dprintf("q9cau(0x%x)",ie[2]));
        if(!cause[2] || cause[2]<0x80) break;  /* eg. layer 1 error */
        Info_Number = 0x0008;
        Info_Mask = 0x01;
        if(cause[2] != ie[2]) Info_Element = cause;
        break;
      case 19: /* Redirected Number */
        dbug(1,dprintf("RDN"));
        Info_Number = 0x0074;
        Info_Mask = 0x400;
        break;
      case 22: /* Redirecing Number  */
        dbug(1,dprintf("RIN"));
        Info_Number = 0x0076;
        Info_Mask = 0x400;
        break;
      case 23: /* Notification Indicator  */
        dbug(1,dprintf("NI"));
        Info_Number = (word)NI;
        Info_Mask = 0x210;
        break;
      case 26: /* Call State  */
        dbug(1,dprintf("CST"));
        Info_Number = (word)CST;
        Info_Mask = 0x01; /* do with cause i.e. for now */
        break;
      case MAXPARMSIDS-2:  /* Escape Message Type, must be the last indication */
        dbug(1,dprintf("ESC/MT[0x%x]",ie[3]));
        Info_Number = 0x8000 |ie[3];
        if(iesent) Info_Mask = 0xffff;
        else  Info_Mask = 0x10;
        Info_Element = "";
        break;
      default:
        Info_Number  = 0;
        Info_Mask    = 0;
        Info_Element = "";
        break;
      }
    }

    if(plci->Sig.Ind==NCR_FACILITY)           /* check controller broadcast */
    {
      for(j=0; j<max_appl; j++)
      {
        appl = &application[j];
        if(Info_Number
        && appl->Id
        && plci->adapter->Info_Mask[appl->Id-1] &Info_Mask)
        {
          dbug(1,dprintf("NCR_Ind"));
          iesent=TRUE;
          sendf(&application[j],_INFO_I,Id&0x0f,0,"wS",Info_Number,Info_Element);
        }
      }
    }
    else if(!plci->appl)
    { /* overlap receiving broadcast */
      if(Info_Number==CPN
      || Info_Number==KEY
      || Info_Number==NI
      || Info_Number==DSP
      || Info_Number==UUI )
      {
        for(j=0; j<max_appl; j++)
        {
          if(test_c_ind_mask_bit (plci, j))
          {
            dbug(1,dprintf("Ovl_Ind"));
            iesent=TRUE;
            sendf(&application[j],_INFO_I,Id,0,"wS",Info_Number,Info_Element);
          }
        }
      }
    }               /* all other signalling states */
    else if(Info_Number
    && plci->adapter->Info_Mask[plci->appl->Id-1] &Info_Mask)
    {
      dbug(1,dprintf("Std_Ind"));
      iesent=TRUE;
      sendf(plci->appl,_INFO_I,Id,0,"wS",Info_Number,Info_Element);
    }
  }
}


byte SendMultiIE(PLCI   * plci, dword Id, byte   * * parms, byte ie_type, dword info_mask, byte setupParse)
{
  word i;
  word j;
  byte   * ie;
  word Info_Number;
  byte   * Info_Element;
  APPL   *appl;
  word Info_Mask = 0;
  byte iesent=0;

  if(
      !plci->appl
      && !plci->State
      && plci->Sig.Ind!=NCR_FACILITY
      && !setupParse
      )
  {
    dbug(1,dprintf("NoM-IEParse "));
    return 0;
  }
  dbug(1,dprintf("M-IEParse "));

  for(i=0; i<MAX_MULTI_IE; i++)
  {
    ie = parms[i];
    Info_Number = 0;
    Info_Element = ie;
    if(ie[0])
    {
      dbug(1,dprintf("[Ind0x%x]:IE=0x%x",plci->Sig.Ind,ie_type));
      Info_Number = (word)ie_type;
      Info_Mask = (word)info_mask;
    }

    if(plci->Sig.Ind==NCR_FACILITY)           /* check controller broadcast */
    {
      for(j=0; j<max_appl; j++)
      {
        appl = &application[j];
        if(Info_Number
        && appl->Id
        && plci->adapter->Info_Mask[appl->Id-1] &Info_Mask)
        {
          iesent = TRUE;
          dbug(1,dprintf("Mlt_NCR_Ind"));
          sendf(&application[j],_INFO_I,Id&0x0f,0,"wS",Info_Number,Info_Element);
        }
      }
    }
    else if(!plci->appl && Info_Number)
    {                                        /* overlap receiving broadcast */
      for(j=0; j<max_appl; j++)
      {
        if(test_c_ind_mask_bit (plci, j))
        {
          iesent = TRUE;
          dbug(1,dprintf("Mlt_Ovl_Ind"));
          sendf(&application[j],_INFO_I,Id,0,"wS",Info_Number,Info_Element);
        }
      }
    }                                        /* all other signalling states */
    else if(Info_Number
    && plci->adapter->Info_Mask[plci->appl->Id-1] &Info_Mask)
    {
      iesent = TRUE;
      dbug(1,dprintf("Mlt_Std_Ind"));
      sendf(plci->appl,_INFO_I,Id,0,"wS",Info_Number,Info_Element);
    }
  }
  return iesent;
}

static void SendSSExtInd(APPL   * appl, PLCI   * plci, dword Id, byte   * * parms)
{
  word i;
   /* Format of multi_ssext_parms[i][]:
   0 byte length
   1 byte SSEXTIE
   2 byte SSEXT_REQ/SSEXT_IND
   3 byte length
   4 word SSExtCommand
   6... Params
   */
  if(
   plci
   && plci->State
   && plci->Sig.Ind!=NCR_FACILITY
    )
 for(i=0;i<MAX_MULTI_IE;i++)
    {
      if(parms[i][0]<6) continue;
   if(parms[i][2]==SSEXT_REQ) continue;

   if(appl)
   {
    parms[i][0]=0; /* kill it */
    sendf(appl,_MANUFACTURER_I,
    Id,
    0,
    "dwS",
    _DI_MANU_ID,
    _DI_SSEXT_CTRL,
    &parms[i][3]);
   }
   else if(plci->appl)
   {
    parms[i][0]=0; /* kill it */
    sendf(plci->appl,_MANUFACTURER_I,
    Id,
    0,
    "dwS",
    _DI_MANU_ID,
    _DI_SSEXT_CTRL,
    &parms[i][3]);
   }
    }
};

void nl_ind(PLCI   * plci)
{
  byte ch;
  word ncci;
  dword Id;
  DIVA_CAPI_ADAPTER   * a;
  word NCCIcode;
  APPL   * APPLptr;
  word count;
  word Num;
  word i, ncpi_state;
  byte len, ncci_state;
  word msg;
  word info = 0;
  word fax_feature_bits;
  byte fax_send_edata_ack;
  static byte v120_header_buffer[2 + 3];
  static word fax_info[] = {
    0,                     /* T30_SUCCESS                        */
    _FAX_NO_CONNECTION,    /* T30_ERR_NO_DIS_RECEIVED            */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_TIMEOUT_NO_RESPONSE        */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_RESPONSE          */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_TOO_MANY_REPEATS           */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_UNEXPECTED_MESSAGE         */
    _FAX_REMOTE_ABORT,     /* T30_ERR_UNEXPECTED_DCN             */
    _FAX_LOCAL_ABORT,      /* T30_ERR_DTC_UNSUPPORTED            */
    _FAX_TRAINING_ERROR,   /* T30_ERR_ALL_RATES_FAILED           */
    _FAX_TRAINING_ERROR,   /* T30_ERR_TOO_MANY_TRAINS            */
    _FAX_PARAMETER_ERROR,  /* T30_ERR_RECEIVE_CORRUPTED          */
    _FAX_REMOTE_ABORT,     /* T30_ERR_UNEXPECTED_DISC            */
    _FAX_LOCAL_ABORT,      /* T30_ERR_APPLICATION_DISC           */
    _FAX_REMOTE_REJECT,    /* T30_ERR_INCOMPATIBLE_DIS           */
    _FAX_LOCAL_ABORT,      /* T30_ERR_INCOMPATIBLE_DCS           */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_TIMEOUT_NO_COMMAND         */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_COMMAND           */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_TIMEOUT_COMMAND_TOO_LONG   */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_TIMEOUT_RESPONSE_TOO_LONG  */
    _FAX_NO_CONNECTION,    /* T30_ERR_NOT_IDENTIFIED             */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_SUPERVISORY_TIMEOUT        */
    _FAX_PARAMETER_ERROR,  /* T30_ERR_TOO_LONG_SCAN_LINE         */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_PAGE_AFTER_MPS    */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_PAGE_AFTER_CFR    */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_DCS_AFTER_FTT     */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_DCS_AFTER_EOM     */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_DCS_AFTER_MPS     */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_DCN_AFTER_MCF     */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_DCN_AFTER_RTN     */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_CFR               */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_MCF_AFTER_EOP     */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_MCF_AFTER_EOM     */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_RETRY_NO_MCF_AFTER_MPS     */
    0x331d,                /* T30_ERR_SUB_SEP_UNSUPPORTED        */
    0x331e,                /* T30_ERR_PWD_UNSUPPORTED            */
    0x331f,                /* T30_ERR_SUB_SEP_PWD_UNSUPPORTED    */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_INVALID_COMMAND_FRAME      */
    _FAX_PARAMETER_ERROR,  /* T30_ERR_UNSUPPORTED_PAGE_CODING    */
    _FAX_PARAMETER_ERROR,  /* T30_ERR_INVALID_PAGE_CODING        */
    _FAX_REMOTE_REJECT,    /* T30_ERR_INCOMPATIBLE_PAGE_CONFIG   */
    _FAX_LOCAL_ABORT,      /* T30_ERR_TIMEOUT_FROM_APPLICATION   */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_V34FAX_NO_REACTION_ON_MARK */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_V34FAX_TRAINING_TIMEOUT    */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_V34FAX_UNEXPECTED_V21      */
    _FAX_PROTOCOL_ERROR,   /* T30_ERR_V34FAX_PRIMARY_CTS_ON      */
    _FAX_LOCAL_ABORT,      /* T30_ERR_V34FAX_TURNAROUND_POLLING  */
    _FAX_LOCAL_ABORT       /* T30_ERR_V34FAX_V8_INCOMPATIBILITY  */
  };

    byte dtmf_code_buffer[CAPIDTMF_RECV_DIGIT_BUFFER_SIZE + 1];


  static word rtp_info[] = {
    GOOD,                  /* RTP_SUCCESS                       */
    0x3600                 /* RTP_ERR_SSRC_OR_PAYLOAD_CHANGE    */
  };

  static dword udata_forwarding_table[0x100 / sizeof(dword)] =
  {
    0x0020301e, 0x00000000, 0x00000000, 0x00000000,
    0x00000000, 0x00000000, 0x00000000, 0x00000000
  };

  ch = plci->NL.IndCh;
  a = plci->adapter;
  ncci = a->ch_ncci[ch];
  Id = (((dword)(ncci ? ncci : ch)) << 16) | (((word) plci->Id) << 8) | a->Id;
  if(plci->tel) Id|=EXT_CONTROLLER;
  APPLptr = plci->appl;
  dbug(1,dprintf("NL_IND-Id(NL:0x%x)=0x%08lx,plci=%x,tel=%x,state=0x%x,ch=0x%x,chs=%d,Ind=%x",
    plci->NL.Id,Id,plci->Id,plci->tel,plci->State,ch,plci->channels,plci->NL.Ind &0x0f));

  /* in the case if no connect_active_Ind was sent to the appl we wait for */

  if (plci->nl_remove_id)
  {
    plci->NL.RNR = 2; /* discard */
    dbug(1,dprintf("NL discard while remove pending"));
    return;
  }
  if((plci->NL.Ind &0x0f)==N_CONNECT)
  {
    if(plci->State==INC_DIS_PENDING
    || plci->State==OUTG_DIS_PENDING
    || plci->State==IDLE)
    {
      plci->NL.RNR = 2; /* discard */
      dbug(1,dprintf("discard n_connect"));
      return;
    }
    if(plci->State < INC_ACT_PENDING)
    {
      plci->NL.RNR = 1; /* flow control */
      channel_x_off (plci, ch, N_XON_CONNECT_IND);
      return;
    }
  }

  if(!APPLptr)                         /* no application or invalid data */
  {                                    /* while reloading the DSP        */
    dbug(1,dprintf("discard1"));
    plci->NL.RNR = 2;
    return;
  }

  if (((plci->NL.Ind &0x0f) == N_UDATA)
     && (((plci->B2_prot != B2_SDLC) && ((plci->B1_resource == 17) || (plci->B1_resource == 18)))
        || (plci->B2_prot == 7)
        || (plci->B3_prot == 7)) )
  {
    plci->ncpi_buffer[0] = 0;

    ncpi_state = plci->ncpi_state;
    if (plci->NL.complete == 1)
    {
      byte  * data = &plci->NL.RBuffer->P[0];

      if ((plci->NL.RBuffer->length >= 12)
        &&( (*data == DSP_UDATA_INDICATION_DCD_ON)
          ||(*data == DSP_UDATA_INDICATION_CTS_ON)) )
      {
        word conn_opt, ncpi_opt = 0x00;
/*      HexDump ("MDM N_UDATA:", plci->NL.RBuffer->length, data); */

        if (*data == DSP_UDATA_INDICATION_DCD_ON)
          plci->ncpi_state |= NCPI_MDM_DCD_ON_RECEIVED;
        if (*data == DSP_UDATA_INDICATION_CTS_ON)
          plci->ncpi_state |= NCPI_MDM_CTS_ON_RECEIVED;

        data++;    /* indication code */
        data += 2; /* timestamp */
        if ((*data == DSP_CONNECTED_NORM_V18) || (*data == DSP_CONNECTED_NORM_VOWN))
          ncpi_state &= ~(NCPI_MDM_DCD_ON_RECEIVED | NCPI_MDM_CTS_ON_RECEIVED);
        data++;    /* connected norm */
        conn_opt = GET_WORD(data);
        data += 2; /* connected options */

        PUT_WORD (&(plci->ncpi_buffer[1]), (word)(GET_DWORD(data) & 0x0000FFFF));

        if (conn_opt & DSP_CONNECTED_OPTION_MASK_V42)
        {
          ncpi_opt |= MDM_NCPI_ECM_V42;
        }
        else if (conn_opt & DSP_CONNECTED_OPTION_MASK_MNP)
        {
          ncpi_opt |= MDM_NCPI_ECM_MNP;
        }
        else
        {
          ncpi_opt |= MDM_NCPI_TRANSPARENT;
        }
        if (conn_opt & DSP_CONNECTED_OPTION_MASK_COMPRESSION)
        {
          ncpi_opt |= MDM_NCPI_COMPRESSED;
        }
        PUT_WORD (&(plci->ncpi_buffer[3]), ncpi_opt);
        plci->ncpi_buffer[0] = 4;

        plci->ncpi_state |= NCPI_VALID_CONNECT_B3_IND | NCPI_VALID_CONNECT_B3_ACT | NCPI_VALID_DISC_B3_IND;
      }
    }
    if (plci->B3_prot == 7)
    {
      if (((a->ncci_state[ncci] == INC_ACT_PENDING) || (a->ncci_state[ncci] == OUTG_CON_PENDING))
       && (plci->ncpi_state & NCPI_VALID_CONNECT_B3_ACT)
       && !(plci->ncpi_state & NCPI_CONNECT_B3_ACT_SENT))
      {
        a->ncci_state[ncci] = INC_ACT_PENDING;
        sendf(plci->appl,_CONNECT_B3_ACTIVE_I,Id,0,"S",plci->ncpi_buffer);
        plci->ncpi_state |= NCPI_CONNECT_B3_ACT_SENT;
      }
    }

    if (!((plci->requested_options_conn | plci->requested_options | plci->adapter->requested_options_table[plci->appl->Id-1])
        & ((1L << PRIVATE_V18) | (1L << PRIVATE_VOWN)))
     || !(ncpi_state & NCPI_MDM_DCD_ON_RECEIVED)
     || !(ncpi_state & NCPI_MDM_CTS_ON_RECEIVED))

    {
      plci->NL.RNR = 2;
      return;
    }
  }

  if(plci->NL.complete == 2)
    {
    if (((plci->NL.Ind &0x0f) == N_UDATA)
     && !(udata_forwarding_table[plci->RData[0].P[0] >> 5] & (1L << (plci->RData[0].P[0] & 0x1f))))
    {
      switch(plci->RData[0].P[0])
      {

      case DTMF_UDATA_INDICATION_FAX_CALLING_TONE:
        if (plci->dtmf_rec_active & DTMF_LISTEN_ACTIVE_FLAG)
          sendf(plci->appl, _FACILITY_I, Id & 0xffffL, 0,"ws", SELECTOR_DTMF, "\x01X");
        break;
      case DTMF_UDATA_INDICATION_ANSWER_TONE:
        if (plci->dtmf_rec_active & DTMF_LISTEN_ACTIVE_FLAG)
          sendf(plci->appl, _FACILITY_I, Id & 0xffffL, 0,"ws", SELECTOR_DTMF, "\x01Y");
        break;
      case DTMF_UDATA_INDICATION_DIGITS_RECEIVED:
        dtmf_indication (Id, plci, plci->RData[0].P, plci->RData[0].PLength);
        break;
      case DTMF_UDATA_INDICATION_DIGITS_SENT:
        dtmf_confirmation (Id, plci);
        break;


      case UDATA_INDICATION_MIXER_TAP_DATA:
        capidtmf_recv_process_block (&(plci->capidtmf_state), plci->RData[0].P + 1, (word)(plci->RData[0].PLength - 1));
 i = capidtmf_indication (&(plci->capidtmf_state), dtmf_code_buffer + 1);
 if (i != 0)
 {
   dtmf_code_buffer[0] = DTMF_UDATA_INDICATION_DIGITS_RECEIVED;
          dtmf_indication (Id, plci, dtmf_code_buffer, (word)(i + 1));
 }
        break;


      case UDATA_INDICATION_MIXER_COEFS_SET:
        mixer_indication_coefs_set (Id, plci);
        break;
      case UDATA_INDICATION_XCONNECT_FROM:
        mixer_indication_xconnect_from (Id, plci, plci->RData[0].P, plci->RData[0].PLength);
        break;
      case UDATA_INDICATION_XCONNECT_TO:
        mixer_indication_xconnect_to (Id, plci, plci->RData[0].P, plci->RData[0].PLength);
        break;


      case LEC_UDATA_INDICATION_DISABLE_DETECT:
        ec_indication (Id, plci, plci->RData[0].P, plci->RData[0].PLength);
        break;



      default:
        break;
      }
    }
    else
  {
      if ((plci->RData[0].PLength != 0)
     && ((plci->B2_prot == B2_V120_ASYNC)
      || (plci->B2_prot == B2_V120_ASYNC_V42BIS)
      || (plci->B2_prot == B2_V120_BIT_TRANSPARENT)))
    {

      sendf(plci->appl,_DATA_B3_I,Id,0,
            "dwww",
            plci->RData[1].P,
              (plci->NL.RNum < 2) ? 0 : plci->RData[1].PLength,
            plci->RNum,
            plci->RFlags);

    }
    else
    {

      sendf(plci->appl,_DATA_B3_I,Id,0,
            "dwww",
            plci->RData[0].P,
            plci->RData[0].PLength,
            plci->RNum,
            plci->RFlags);

    }
    }
    return;
  }

  fax_feature_bits = 0;
  if((plci->NL.Ind &0x0f)==N_CONNECT ||
     (plci->NL.Ind &0x0f)==N_CONNECT_ACK ||
     (plci->NL.Ind &0x0f)==N_DISC ||
     (plci->NL.Ind &0x0f)==N_EDATA ||
     (plci->NL.Ind &0x0f)==N_DISC_ACK)
  {
    info = 0;
    plci->ncpi_buffer[0] = 0;
    switch (plci->B3_prot) {
    case  0: /*XPARENT*/
    case  1: /*T.90 NL*/
      break;    /* no network control protocol info - jfr */
    case  2: /*ISO8202*/
    case  3: /*X25 DCE*/
      for(i=0; i<plci->NL.RLength; i++) plci->ncpi_buffer[4+i] = plci->NL.RBuffer->P[i];
      plci->ncpi_buffer[0] = (byte)(i+3);
      plci->ncpi_buffer[1] = (byte)(plci->NL.Ind &N_D_BIT? 1:0);
      plci->ncpi_buffer[2] = 0;
      plci->ncpi_buffer[3] = 0;
      break;
    case  4: /*T.30 - FAX*/
    case  5: /*T.30 - FAX*/
      if(plci->NL.RLength>=sizeof(T30_INFO))
      {
        dbug(1,dprintf("FaxStatus %04x", ((T30_INFO   *)plci->NL.RBuffer->P)->code));
        len = 9;
        PUT_WORD(&(plci->ncpi_buffer[1]),((T30_INFO   *)plci->NL.RBuffer->P)->rate_div_2400 * 2400);
        fax_feature_bits = GET_WORD(&((T30_INFO   *)plci->NL.RBuffer->P)->feature_bits_low);
        i = (((T30_INFO   *)plci->NL.RBuffer->P)->resolution & T30_RESOLUTION_R8_0770_OR_200) ? 0x0001 : 0x0000;
        if (plci->B3_prot == 5)
        {
          if (!(fax_feature_bits & T30_FEATURE_BIT_ECM))
            i |= 0x8000; /* This is not an ECM connection */
          if (fax_feature_bits & T30_FEATURE_BIT_T6_CODING)
            i |= 0x4000; /* This is a connection with MMR compression */
          if (fax_feature_bits & T30_FEATURE_BIT_2D_CODING)
            i |= 0x2000; /* This is a connection with MR compression */
          if (fax_feature_bits & T30_FEATURE_BIT_MORE_DOCUMENTS)
            i |= 0x0004; /* More documents */
          if (fax_feature_bits & T30_FEATURE_BIT_POLLING)
            i |= 0x0002; /* Fax-polling indication */
        }
        dbug(1,dprintf("FAX Options %04x %04x",fax_feature_bits,i));
        PUT_WORD(&(plci->ncpi_buffer[3]),i);
        PUT_WORD(&(plci->ncpi_buffer[5]),((T30_INFO   *)plci->NL.RBuffer->P)->data_format);
        plci->ncpi_buffer[7] = ((T30_INFO   *)plci->NL.RBuffer->P)->pages_low;
        plci->ncpi_buffer[8] = ((T30_INFO   *)plci->NL.RBuffer->P)->pages_high;
        plci->ncpi_buffer[len] = 0;
        if(((T30_INFO   *)plci->NL.RBuffer->P)->station_id_len)
        {
          plci->ncpi_buffer[len] = 20;
          for (i = 0; i < 20; i++)
            plci->ncpi_buffer[++len] = ((T30_INFO   *)plci->NL.RBuffer->P)->station_id[i];
        }
        if (((plci->NL.Ind & 0x0f) == N_DISC) || ((plci->NL.Ind & 0x0f) == N_DISC_ACK))
        {
          if (((T30_INFO   *)plci->NL.RBuffer->P)->code < sizeof(fax_info) / sizeof(fax_info[0]))
            info = fax_info[((T30_INFO   *)plci->NL.RBuffer->P)->code];
          else
            info = _FAX_PROTOCOL_ERROR;
        }

        if ((plci->requested_options_conn | plci->requested_options | a->requested_options_table[plci->appl->Id-1])
          & ((1L << PRIVATE_FAX_SUB_SEP_PWD) | (1L << PRIVATE_FAX_NONSTANDARD)))
        {
          i = ((word)(((T30_INFO *) 0)->station_id + 20)) + ((T30_INFO   *)plci->NL.RBuffer->P)->head_line_len;
          while (i < plci->NL.RBuffer->length)
            plci->ncpi_buffer[++len] = plci->NL.RBuffer->P[i++];
        }

        plci->ncpi_buffer[0] = len;
        fax_feature_bits = GET_WORD(&((T30_INFO   *)plci->NL.RBuffer->P)->feature_bits_low);
        PUT_WORD(&((T30_INFO   *)plci->fax_connect_info_buffer)->feature_bits_low, fax_feature_bits);

        plci->ncpi_state |= NCPI_VALID_CONNECT_B3_IND;
 if (((plci->NL.Ind &0x0f) == N_CONNECT_ACK)
         || (((plci->NL.Ind &0x0f) == N_CONNECT)
          && (fax_feature_bits & T30_FEATURE_BIT_POLLING))
         || (((plci->NL.Ind &0x0f) == N_EDATA)
          && ((((T30_INFO   *)plci->NL.RBuffer->P)->code == EDATA_T30_TRAIN_OK)
           || (((T30_INFO   *)plci->NL.RBuffer->P)->code == EDATA_T30_DIS)
           || (((T30_INFO   *)plci->NL.RBuffer->P)->code == EDATA_T30_DTC))))
 {
          plci->ncpi_state |= NCPI_VALID_CONNECT_B3_ACT;
 }
 if (((plci->NL.Ind &0x0f) == N_DISC)
  || ((plci->NL.Ind &0x0f) == N_DISC_ACK)
  || (((plci->NL.Ind &0x0f) == N_EDATA)
   && (((T30_INFO   *)plci->NL.RBuffer->P)->code == EDATA_T30_EOP_CAPI)))
 {
          plci->ncpi_state |= NCPI_VALID_CONNECT_B3_ACT | NCPI_VALID_DISC_B3_IND;
 }
      }
      break;

    case B3_RTP:
      if (((plci->NL.Ind & 0x0f) == N_DISC) || ((plci->NL.Ind & 0x0f) == N_DISC_ACK))
      {
        if (plci->NL.RLength != 0)
        {
          info = rtp_info[plci->NL.RBuffer->P[0]];
          plci->ncpi_buffer[0] = plci->NL.RLength - 1;
          for (i = 1; i < plci->NL.RLength; i++)
            plci->ncpi_buffer[i] = plci->NL.RBuffer->P[i];
        }
      }
      break;

    }
    plci->NL.RNR = 2;
  }
  switch(plci->NL.Ind &0x0f) {
  case N_EDATA:
    if ((plci->B3_prot == 4) || (plci->B3_prot == 5))
    {
      dbug(1,dprintf("EDATA ncci=0x%x state=%d code=%02x", ncci, a->ncci_state[ncci],
        ((T30_INFO   *)plci->NL.RBuffer->P)->code));
      fax_send_edata_ack = (((T30_INFO   *)(plci->fax_connect_info_buffer))->operating_mode == T30_OPERATING_MODE_CAPI_NEG);

      if ((plci->nsf_control_bits & T30_NSF_CONTROL_BIT_ENABLE_NSF)
       && (plci->nsf_control_bits & (T30_NSF_CONTROL_BIT_NEGOTIATE_IND | T30_NSF_CONTROL_BIT_NEGOTIATE_RESP))
       && (((T30_INFO   *)plci->NL.RBuffer->P)->code == EDATA_T30_DIS)
       && (a->ncci_state[ncci] == OUTG_CON_PENDING)
       && (plci->ncpi_state & NCPI_VALID_CONNECT_B3_ACT)
       && !(plci->ncpi_state & NCPI_NEGOTIATE_B3_SENT))
      {
        ((T30_INFO   *)(plci->fax_connect_info_buffer))->code = ((T30_INFO   *)plci->NL.RBuffer->P)->code;
        sendf(plci->appl,_MANUFACTURER_I,Id,0,"dwbS",_DI_MANU_ID,_DI_NEGOTIATE_B3,
          (byte)(plci->ncpi_buffer[0] + 1), plci->ncpi_buffer);
        plci->ncpi_state |= NCPI_NEGOTIATE_B3_SENT;
 if (plci->nsf_control_bits & T30_NSF_CONTROL_BIT_NEGOTIATE_RESP)
   fax_send_edata_ack = FALSE;
      }

      if (a->manufacturer_features & MANUFACTURER_FEATURE_FAX_PAPER_FORMATS)
      {
        switch (((T30_INFO   *)plci->NL.RBuffer->P)->code)
        {
        case EDATA_T30_DIS:
          if ((a->ncci_state[ncci] == OUTG_CON_PENDING)
           && !(GET_WORD(&((T30_INFO   *)plci->fax_connect_info_buffer)->control_bits_low) & T30_CONTROL_BIT_REQUEST_POLLING)
           && (plci->ncpi_state & NCPI_VALID_CONNECT_B3_ACT)
           && !(plci->ncpi_state & NCPI_CONNECT_B3_ACT_SENT))
          {
            a->ncci_state[ncci] = INC_ACT_PENDING;
            if (plci->B3_prot == 4)
              sendf(plci->appl,_CONNECT_B3_ACTIVE_I,Id,0,"s","");
            else
              sendf(plci->appl,_CONNECT_B3_ACTIVE_I,Id,0,"S",plci->ncpi_buffer);
            plci->ncpi_state |= NCPI_CONNECT_B3_ACT_SENT;
          }
          break;

        case EDATA_T30_TRAIN_OK:
          if ((a->ncci_state[ncci] == INC_ACT_PENDING)
           && (plci->ncpi_state & NCPI_VALID_CONNECT_B3_ACT)
           && !(plci->ncpi_state & NCPI_CONNECT_B3_ACT_SENT))
          {
            if (plci->B3_prot == 4)
              sendf(plci->appl,_CONNECT_B3_ACTIVE_I,Id,0,"s","");
            else
              sendf(plci->appl,_CONNECT_B3_ACTIVE_I,Id,0,"S",plci->ncpi_buffer);
            plci->ncpi_state |= NCPI_CONNECT_B3_ACT_SENT;
          }
          break;

        case EDATA_T30_EOP_CAPI:
          if (a->ncci_state[ncci] == CONNECTED)
          {
            sendf(plci->appl,_DISCONNECT_B3_I,Id,0,"wS",GOOD,plci->ncpi_buffer);
            a->ncci_state[ncci] = INC_DIS_PENDING;
            plci->ncpi_state = 0;
     fax_send_edata_ack = FALSE;
          }
          break;
        }
      }
      else
      {
        switch (((T30_INFO   *)plci->NL.RBuffer->P)->code)
        {
        case EDATA_T30_TRAIN_OK:
          if ((a->ncci_state[ncci] == INC_ACT_PENDING)
           && (plci->ncpi_state & NCPI_VALID_CONNECT_B3_ACT)
           && !(plci->ncpi_state & NCPI_CONNECT_B3_ACT_SENT))
          {
            if (plci->B3_prot == 4)
              sendf(plci->appl,_CONNECT_B3_ACTIVE_I,Id,0,"s","");
            else
              sendf(plci->appl,_CONNECT_B3_ACTIVE_I,Id,0,"S",plci->ncpi_buffer);
            plci->ncpi_state |= NCPI_CONNECT_B3_ACT_SENT;
          }
          break;
        }
      }
      if (fax_send_edata_ack)
      {
        ((T30_INFO   *)(plci->fax_connect_info_buffer))->code = ((T30_INFO   *)plci->NL.RBuffer->P)->code;
 plci->fax_edata_ack_length = 1;
        start_internal_command (Id, plci, fax_edata_ack_command);
      }
    }
    else
    {
      dbug(1,dprintf("EDATA ncci=0x%x state=%d", ncci, a->ncci_state[ncci]));
    }
    break;
  case N_CONNECT:
    if (!a->ch_ncci[ch])
    {
      ncci = get_ncci (plci, ch, 0);
      Id = (Id & 0xffff) | (((dword) ncci) << 16);
    }
    dbug(1,dprintf("N_CONNECT: ch=%d state=%d plci=%lx plci_Id=%lx plci_State=%d",
      ch, a->ncci_state[ncci], a->ncci_plci[ncci], plci->Id, plci->State));

    msg = _CONNECT_B3_I;
    if (a->ncci_state[ncci] == IDLE)
      plci->channels++;
    else if (plci->B3_prot == 1)
      msg = _CONNECT_B3_T90_ACTIVE_I;

    a->ncci_state[ncci] = INC_CON_PENDING;
    if(plci->B3_prot == 4)
      sendf(plci->appl,msg,Id,0,"s","");
    else
      sendf(plci->appl,msg,Id,0,"S",plci->ncpi_buffer);
    break;
  case N_CONNECT_ACK:
    dbug(1,dprintf("N_connect_Ack"));
    if (plci->internal_command_queue[0]
     && ((plci->adjust_b_state == ADJUST_B_CONNECT_2)
      || (plci->adjust_b_state == ADJUST_B_CONNECT_3)
      || (plci->adjust_b_state == ADJUST_B_CONNECT_4)))
    {
      (*(plci->internal_command_queue[0]))(Id, plci, 0);
      if (!plci->internal_command)
        next_internal_command (Id, plci);
      break;
    }
    msg = _CONNECT_B3_ACTIVE_I;
    if (plci->B3_prot == 1)
    {
      if (a->ncci_state[ncci] != OUTG_CON_PENDING)
        msg = _CONNECT_B3_T90_ACTIVE_I;
      a->ncci_state[ncci] = INC_ACT_PENDING;
      sendf(plci->appl,msg,Id,0,"S",plci->ncpi_buffer);
    }
    else if ((plci->B3_prot == 4) || (plci->B3_prot == 5) || (plci->B3_prot == 7))
    {
      if ((a->ncci_state[ncci] == OUTG_CON_PENDING)
       && (plci->ncpi_state & NCPI_VALID_CONNECT_B3_ACT)
       && !(plci->ncpi_state & NCPI_CONNECT_B3_ACT_SENT))
      {
        a->ncci_state[ncci] = INC_ACT_PENDING;
        if (plci->B3_prot == 4)
          sendf(plci->appl,msg,Id,0,"s","");
        else
          sendf(plci->appl,msg,Id,0,"S",plci->ncpi_buffer);
        plci->ncpi_state |= NCPI_CONNECT_B3_ACT_SENT;
      }
    }
    else
    {
      a->ncci_state[ncci] = INC_ACT_PENDING;
      sendf(plci->appl,msg,Id,0,"S",plci->ncpi_buffer);
    }
    if (plci->adjust_b_restore)
    {
      plci->adjust_b_restore = FALSE;
      start_internal_command (Id, plci, adjust_b_restore);
    }
    break;
  case N_DISC:
  case N_DISC_ACK:
    if (plci->internal_command_queue[0]
     && ((plci->internal_command == FAX_DISCONNECT_COMMAND_1)
      || (plci->internal_command == FAX_DISCONNECT_COMMAND_2)
      || (plci->internal_command == FAX_DISCONNECT_COMMAND_3)))
    {
      (*(plci->internal_command_queue[0]))(Id, plci, 0);
      if (!plci->internal_command)
        next_internal_command (Id, plci);
    }
    ncci_state = a->ncci_state[ncci];
    ncci_remove (plci, ncci, FALSE);

        /* with N_DISC or N_DISC_ACK the IDI frees the respective   */
        /* channel, so we cannot store the state in ncci_state! The */
        /* information which channel we received a N_DISC is thus   */
        /* stored in the inc_dis_ncci_table buffer.                 */
    for(i=0; plci->inc_dis_ncci_table[i]; i++);
    plci->inc_dis_ncci_table[i] = (byte) ncci;

      /* need a connect_b3_ind before a disconnect_b3_ind with FAX */
    if (!plci->channels
     && (plci->B1_resource == 16)
     && (plci->State <= CONNECTED))
    {
      len = 9;
      i = ((T30_INFO   *)plci->fax_connect_info_buffer)->rate_div_2400 * 2400;
      PUT_WORD (&plci->ncpi_buffer[1], i);
      PUT_WORD (&plci->ncpi_buffer[3], 0);
      i = ((T30_INFO   *)plci->fax_connect_info_buffer)->data_format;
      PUT_WORD (&plci->ncpi_buffer[5], i);
      PUT_WORD (&plci->ncpi_buffer[7], 0);
      plci->ncpi_buffer[len] = 0;
      plci->ncpi_buffer[0] = len;
      if(plci->B3_prot == 4)
        sendf(plci->appl,_CONNECT_B3_I,Id,0,"s","");
      else
      {

        if ((plci->requested_options_conn | plci->requested_options | a->requested_options_table[plci->appl->Id-1])
          & ((1L << PRIVATE_FAX_SUB_SEP_PWD) | (1L << PRIVATE_FAX_NONSTANDARD)))
        {
          plci->ncpi_buffer[++len] = 0;
          plci->ncpi_buffer[++len] = 0;
          plci->ncpi_buffer[++len] = 0;
          plci->ncpi_buffer[0] = len;
        }

        sendf(plci->appl,_CONNECT_B3_I,Id,0,"S",plci->ncpi_buffer);
      }
      sendf(plci->appl,_DISCONNECT_B3_I,Id,0,"wS",info,plci->ncpi_buffer);
      plci->ncpi_state = 0;
      sig_req(plci,HANGUP,0);
      send_req(plci);
      plci->State = OUTG_DIS_PENDING;
      /* disc here */
    }
    else if ((a->manufacturer_features & MANUFACTURER_FEATURE_FAX_PAPER_FORMATS)
     && ((plci->B3_prot == 4) || (plci->B3_prot == 5))
     && ((ncci_state == INC_DIS_PENDING) || (ncci_state == IDLE)))
    {
      if (ncci_state == IDLE)
      {
        if (plci->channels)
          plci->channels--;
        if((plci->State==IDLE || plci->State==SUSPENDING) && !plci->channels){
          if(plci->State == SUSPENDING){
            sendf(plci->appl,
                  _FACILITY_I,
                  Id & 0xffffL,
                  0,
                  "ws", (word)3, "\x03\x04\x00\x00");
            sendf(plci->appl, _DISCONNECT_I, Id & 0xffffL, 0, "w", 0);
          }
          plci_remove(plci);
          plci->State=IDLE;
        }
      }
    }
    else if (plci->channels)
    {
      sendf(plci->appl,_DISCONNECT_B3_I,Id,0,"wS",info,plci->ncpi_buffer);
      plci->ncpi_state = 0;
      if ((ncci_state == OUTG_REJ_PENDING)
       && ((plci->B3_prot != B3_T90NL) && (plci->B3_prot != B3_ISO8208) && (plci->B3_prot != B3_X25_DCE)))
      {
        sig_req(plci,HANGUP,0);
        send_req(plci);
        plci->State = OUTG_DIS_PENDING;
      }
    }
    break;
  case N_RESET:
    a->ncci_state[ncci] = INC_RES_PENDING;
    sendf(plci->appl,_RESET_B3_I,Id,0,"S",plci->ncpi_buffer);
    break;
  case N_RESET_ACK:
    a->ncci_state[ncci] = CONNECTED;
    sendf(plci->appl,_RESET_B3_I,Id,0,"S",plci->ncpi_buffer);
    break;

  case N_UDATA:
    if (!(udata_forwarding_table[plci->NL.RBuffer->P[0] >> 5] & (1L << (plci->NL.RBuffer->P[0] & 0x1f))))
    {
      plci->RData[0].P = plci->internal_ind_buffer + (-((int)(plci->internal_ind_buffer)) & 3);
      plci->RData[0].PLength = INTERNAL_IND_BUFFER_SIZE;
      plci->NL.R = plci->RData;
      plci->NL.RNum = 1;
      return;
    }
  case N_BDATA:
  case N_DATA:
    if (((a->ncci_state[ncci] != CONNECTED) && (plci->B2_prot == 1)) /* transparent */
     || (a->ncci_state[ncci] == IDLE)
     || (a->ncci_state[ncci] == INC_DIS_PENDING))
    {
      plci->NL.RNR = 2;
      break;
    }
    if ((a->ncci_state[ncci] != CONNECTED)
     && (a->ncci_state[ncci] != OUTG_DIS_PENDING)
     && (a->ncci_state[ncci] != OUTG_REJ_PENDING))
    {
      dbug(1,dprintf("flow control"));
      plci->NL.RNR = 1; /* flow control  */
      channel_x_off (plci, ch, 0);
      break;
    }

    NCCIcode = ncci | (((word)a->Id) << 8);

                /* count all buffers within the Application pool    */
                /* belonging to the same NCCI. If this is below the */
                /* number of buffers available per NCCI we accept   */
                /* this packet, otherwise we reject it              */
    count = 0;
    Num = 0xffff;
    for(i=0; i<APPLptr->MaxBuffer; i++) {
      if(NCCIcode==APPLptr->DataNCCI[i]) count++;
      if(!APPLptr->DataNCCI[i] && Num==0xffff) Num = i;
    }

    if(count>=APPLptr->MaxNCCIData || Num==0xffff)
    {
      dbug(3,dprintf("Flow-Control"));
      plci->NL.RNR = 1;
      if( ++(APPLptr->NCCIDataFlowCtrlTimer)>=
       (word)((a->manufacturer_features & MANUFACTURER_FEATURE_OOB_CHANNEL) ? 40 : 2000))
      {
        plci->NL.RNR = 2;
        dbug(3,dprintf("DiscardData"));
      } else {
        channel_x_off (plci, ch, 0);
      }
      break;
    }
    else
    {
      APPLptr->NCCIDataFlowCtrlTimer = 0;
    }

    plci->RData[0].P = ReceiveBufferGet(APPLptr,Num);
    if(!plci->RData[0].P) {
      plci->NL.RNR = 1;
      channel_x_off (plci, ch, 0);
      break;
    }

    APPLptr->DataNCCI[Num] = NCCIcode;
    APPLptr->DataFlags[Num] = (plci->Id<<8) | (plci->NL.Ind>>4);
    dbug(3,dprintf("Buffer(%d), Max = %d",Num,APPLptr->MaxBuffer));

    plci->RNum = Num;
    plci->RFlags = plci->NL.Ind>>4;
    plci->RData[0].PLength = APPLptr->MaxDataLength;
    plci->NL.R = plci->RData;
    if ((plci->NL.RLength != 0)
     && ((plci->B2_prot == B2_V120_ASYNC)
      || (plci->B2_prot == B2_V120_ASYNC_V42BIS)
      || (plci->B2_prot == B2_V120_BIT_TRANSPARENT)))
    {
      plci->RData[1].P = plci->RData[0].P;
      plci->RData[1].PLength = plci->RData[0].PLength;
      plci->RData[0].P = v120_header_buffer + (-((int) v120_header_buffer) & 3);
      if ((plci->NL.RBuffer->P[0] & V120_HEADER_EXTEND_BIT) || (plci->NL.RLength == 1))
        plci->RData[0].PLength = 1;
      else
        plci->RData[0].PLength = 2;
      if (plci->NL.RBuffer->P[0] & V120_HEADER_BREAK_BIT)
        plci->RFlags |= 0x0010;
      if (plci->NL.RBuffer->P[0] & (V120_HEADER_C1_BIT | V120_HEADER_C2_BIT))
        plci->RFlags |= 0x8000;
      plci->NL.RNum = 2;
    }
    else
    {
      if((plci->NL.Ind &0x0f)==N_UDATA)
        plci->RFlags |= 0x0010;

      else if ((plci->B3_prot == B3_RTP) && ((plci->NL.Ind & 0x0f) == N_BDATA))
        plci->RFlags |= 0x0001;

      plci->NL.RNum = 1;
    }
    break;
  case N_DATA_ACK:
    data_ack (plci, ch);
    break;
  default:
    plci->NL.RNR = 2;
    break;
  }
}

/*------------------------------------------------------------------*/
/* find a free PLCI                                                 */
/*------------------------------------------------------------------*/

word get_plci(DIVA_CAPI_ADAPTER   * a)
{
  word i,j;
  PLCI   * plci;

  dump_plcis (a);
  for(i=0;i<a->max_plci && a->plci[i].Id;i++);
  if(i==a->max_plci) {
    dbug(1,dprintf("get_plci: out of PLCIs"));
    return 0;
  }
  plci = &a->plci[i];
  plci->Id = (byte)(i+1);

  plci->Sig.Id = 0;
  plci->NL.Id = 0;
  plci->sig_req = 0;
  plci->nl_req = 0;

  plci->appl = NULL;
  plci->relatedPTYPLCI = NULL;
  plci->State = IDLE;
  plci->SuppState = IDLE;
  plci->channels = 0;
  plci->tel = 0;
  plci->B1_resource = 0;
  plci->B2_prot = 0;
  plci->B3_prot = 0;

  plci->command = 0;
  plci->m_command = 0;
  init_internal_command_queue (plci);
  plci->number = 0;
  plci->req_in_start = 0;
  plci->req_in = 0;
  plci->req_out = 0;
  plci->msg_in_write_pos = MSG_IN_QUEUE_SIZE;
  plci->msg_in_read_pos = MSG_IN_QUEUE_SIZE;
  plci->msg_in_wrap_pos = MSG_IN_QUEUE_SIZE;

  plci->data_sent = FALSE;
  plci->send_disc = 0;
  plci->sig_global_req = 0;
  plci->sig_remove_id = 0;
  plci->nl_global_req = 0;
  plci->nl_remove_id = 0;
  plci->adv_nl = 0;
  plci->manufacturer = FALSE;
  plci->call_dir = CALL_DIR_OUT | CALL_DIR_ORIGINATE;
  plci->spoofed_msg = 0;
  plci->ptyState = 0;
  plci->cr_enquiry = FALSE;
  plci->hangup_flow_ctrl_timer = 0;

  plci->ncci_ring_list = 0;
  for(j=0;j<MAX_CHANNELS_PER_PLCI;j++) plci->inc_dis_ncci_table[j] = 0;
  clear_c_ind_mask (plci);
  set_group_ind_mask (plci);
  plci->fax_connect_info_length = 0;
  plci->nsf_control_bits = 0;
  plci->ncpi_state = 0x00;
  plci->ncpi_buffer[0] = 0;

  plci->requested_options_conn = 0;
  plci->requested_options = 0;
  plci->notifiedcall = 0;
  plci->vswitchstate = 0;
  plci->vsprot = 0;
  plci->vsprotdialect = 0;
  init_b1_config (plci);
  dbug(1,dprintf("get_plci(%x)",plci->Id));
  return i+1;
}

/*------------------------------------------------------------------*/
/* put a parameter in the parameter buffer                          */
/*------------------------------------------------------------------*/

static void add_p(PLCI   * plci, byte code, byte   * p)
{
  word p_length;

  p_length = 0;
  if(p) p_length = p[0];
  add_ie(plci, code, p, p_length);
}

/*------------------------------------------------------------------*/
/* put a structure in the parameter buffer                          */
/*------------------------------------------------------------------*/
static void add_s(PLCI   * plci, byte code, API_PARSE * p)
{
  if(p) add_ie(plci, code, p->info, (word)p->length);
}

/*------------------------------------------------------------------*/
/* put multiple structures in the parameter buffer                  */
/*------------------------------------------------------------------*/
static void add_ss(PLCI   * plci, byte code, API_PARSE * p)
{
  byte i;

  if(p){
    dbug(1,dprintf("add_ss(%x,len=%d)",code,p->length));
    for(i=2;i<(byte)p->length;i+=p->info[i]+2){
      dbug(1,dprintf("add_ss_ie(%x,len=%d)",p->info[i-1],p->info[i]));
      add_ie(plci, p->info[i-1], (byte   *)&(p->info[i]), (word)p->info[i]);
    }
  }
}

/*------------------------------------------------------------------*/
/* return the channel number sent by the application in a esc_chi   */
/*------------------------------------------------------------------*/
static byte getChannel(API_PARSE * p)
{
  byte i;

  if(p){
    for(i=2;i<(byte)p->length;i+=p->info[i]+2){
      if(p->info[i]==2){
        if(p->info[i-1]==ESC && p->info[i+1]==CHI) return (p->info[i+2]);
      }
    }
  }
  return 0;
}


/*------------------------------------------------------------------*/
/* put an information element in the parameter buffer               */
/*------------------------------------------------------------------*/

static void add_ie(PLCI   * plci, byte code, byte   * p, word p_length)
{
  word i;

  if(!(code &0x80) && !p_length) return;

  if(plci->req_in==plci->req_in_start) {
    plci->req_in +=2;
  }
  else {
    plci->req_in--;
  }
  plci->RBuffer[plci->req_in++] = code;

  if(p) {
    plci->RBuffer[plci->req_in++] = (byte)p_length;
    for(i=0;i<p_length;i++) plci->RBuffer[plci->req_in++] = p[1+i];
  }

  plci->RBuffer[plci->req_in++] = 0;
}

/*------------------------------------------------------------------*/
/* put a unstructured data into the buffer                          */
/*------------------------------------------------------------------*/

void add_d(PLCI   * plci, word length, byte   * p)
{
  word i;

  if(plci->req_in==plci->req_in_start) {
    plci->req_in +=2;
  }
  else {
    plci->req_in--;
  }
  for(i=0;i<length;i++) plci->RBuffer[plci->req_in++] = p[i];
}

/*------------------------------------------------------------------*/
/* put parameters from the Additional Info parameter in the         */
/* parameter buffer                                                 */
/*------------------------------------------------------------------*/

void add_ai(PLCI   * plci, API_PARSE * ai)
{
  word i;
    API_PARSE ai_parms[5];

  for(i=0;i<5;i++) ai_parms[i].length = 0;

  if(!ai->length)
    return;
  if(api_parse(&ai->info[1], (word)ai->length, "ssss", ai_parms))
    return;

  add_s (plci,KEY,&ai_parms[1]);
  add_s (plci,UUI,&ai_parms[2]);
  add_ss(plci,FTY,&ai_parms[3]);
}

/*------------------------------------------------------------------*/
/* put parameter for b1 protocol in the parameter buffer            */
/*------------------------------------------------------------------*/

word add_b1(PLCI   * plci, API_PARSE * bp, word b_channel_info, word b1_facilities)
{
    API_PARSE bp_parms[8];
    API_PARSE mdm_cfg[9];
    API_PARSE global_config[2];
    byte cai[256];
  byte resource[] = {5,9,13,12,16,39,9,17,17,18};
  byte voice_cai[] = "\x06\x14\x00\x00\x00\x00\x08";
  word i;

    API_PARSE mdm_cfg_v18[4];
  word j, n, w;
  dword d;


  for(i=0;i<8;i++) bp_parms[i].length = 0;
  for(i=0;i<2;i++) global_config[i].length = 0;

  dbug(1,dprintf("add_b1"));
  api_save_msg(bp, "s", &plci->B_protocol);

  if(b_channel_info==2){
    plci->B1_resource = 0;
    adjust_b1_facilities (plci, plci->B1_resource, b1_facilities);
    add_p(plci, CAI, "\x01\x00");
    dbug(1,dprintf("Cai=1,0 (no resource)"));
    return 0;
  }

  if(plci->tel == CODEC_PERMANENT) return 0;
  else if(plci->tel == CODEC){
    plci->B1_resource = 1;
    adjust_b1_facilities (plci, plci->B1_resource, b1_facilities);
    add_p(plci, CAI, "\x01\x01");
    dbug(1,dprintf("Cai=1,1 (Codec)"));
    return 0;
  }
  else if(plci->tel == ADV_VOICE){
    plci->B1_resource = add_b1_facilities (plci, 9, (word)(b1_facilities | B1_FACILITY_VOICE));
    adjust_b1_facilities (plci, plci->B1_resource, (word)(b1_facilities | B1_FACILITY_VOICE));
    voice_cai[1] = plci->B1_resource;
    PUT_WORD (&voice_cai[5], plci->appl->MaxDataLength);
    add_p(plci, CAI, voice_cai);
    dbug(1,dprintf("Cai=1,0x%x (AdvVoice)",voice_cai[1]));
    return 0;
  }
  plci->call_dir &= ~(CALL_DIR_ORIGINATE | CALL_DIR_ANSWER);
  if (plci->call_dir & CALL_DIR_OUT)
    plci->call_dir |= CALL_DIR_ORIGINATE;
  else if (plci->call_dir & CALL_DIR_IN)
    plci->call_dir |= CALL_DIR_ANSWER;

  if(!bp->length){
    plci->B1_resource = 0x5;
    adjust_b1_facilities (plci, plci->B1_resource, b1_facilities);
    add_p(plci, CAI, "\x01\x05");
    return 0;
  }

  dbug(1,dprintf("b_prot_len=%d",(word)bp->length));
  if(bp->length>256) return _WRONG_MESSAGE_FORMAT;
  if(api_parse(&bp->info[1], (word)bp->length, "wwwsssb", bp_parms))
  {
    bp_parms[6].length = 0;
    if(api_parse(&bp->info[1], (word)bp->length, "wwwsss", bp_parms))
    {
      dbug(1,dprintf("b-form.!"));
      return _WRONG_MESSAGE_FORMAT;
    }
  }
  else if (api_parse(&bp->info[1], (word)bp->length, "wwwssss", bp_parms))
  {
    dbug(1,dprintf("b-form.!"));
    return _WRONG_MESSAGE_FORMAT;
  }

  if(bp_parms[6].length)
  {
    if(api_parse(&bp_parms[6].info[1], (word)bp_parms[6].length, "w", global_config))
    {
      return _WRONG_MESSAGE_FORMAT;
    }
    switch(GET_WORD(global_config[0].info))
    {
    case 1:
      plci->call_dir = (plci->call_dir & ~CALL_DIR_ANSWER) | CALL_DIR_ORIGINATE;
      break;
    case 2:
      plci->call_dir = (plci->call_dir & ~CALL_DIR_ORIGINATE) | CALL_DIR_ANSWER;
      break;
    }
  }
  dbug(1,dprintf("call_dir=%04x", plci->call_dir));


  if ((GET_WORD(bp_parms[0].info) == B1_RTP)
   && (plci->adapter->man_profile.private_options & (1L << PRIVATE_RTP)))
  {
    plci->B1_resource = add_b1_facilities (plci, 31, (word)(b1_facilities & ~B1_FACILITY_VOICE));
    adjust_b1_facilities (plci, plci->B1_resource, (word)(b1_facilities & ~B1_FACILITY_VOICE));
    cai[1] = plci->B1_resource;
    cai[2] = 0;
    cai[3] = 0;
    cai[4] = 0;
    PUT_WORD(&cai[5],plci->appl->MaxDataLength);
    for (i = 0; i < bp_parms[3].length; i++)
      cai[7+i] = bp_parms[3].info[1+i];
    cai[0] = 6 + bp_parms[3].length;
    add_p(plci, CAI, cai);
    return 0;
  }


  if ((GET_WORD(bp_parms[0].info) == B1_PIAFS)
   && (plci->adapter->man_profile.private_options & (1L << PRIVATE_PIAFS)))
  {
    plci->B1_resource = add_b1_facilities (plci, 35/* PIAFS HARDWARE FACILITY */, (word)(b1_facilities & ~B1_FACILITY_VOICE));
    adjust_b1_facilities (plci, plci->B1_resource, (word)(b1_facilities & ~B1_FACILITY_VOICE));
    cai[1] = plci->B1_resource;
    cai[2] = 0;
    cai[3] = 0;
    cai[4] = 0;
    PUT_WORD(&cai[5],plci->appl->MaxDataLength);
    cai[0] = 6;
    add_p(plci, CAI, cai);
    return 0;
  }


  if ((GET_WORD(bp_parms[0].info) >= 32)
   || (!((1L << GET_WORD(bp_parms[0].info)) & plci->adapter->profile.B1_Protocols)
    && ((GET_WORD(bp_parms[0].info) != 3)
     || !((1L << B1_HDLC) & plci->adapter->profile.B1_Protocols)
     || ((bp_parms[3].length != 0) && (GET_WORD(&bp_parms[3].info[1]) != 0) && (GET_WORD(&bp_parms[3].info[1]) != 56000)))))
  {
    return _B1_NOT_SUPPORTED;
  }
  plci->B1_resource = add_b1_facilities (plci, resource[GET_WORD(bp_parms[0].info)],
    (word)(b1_facilities & ~B1_FACILITY_VOICE));
  adjust_b1_facilities (plci, plci->B1_resource, (word)(b1_facilities & ~B1_FACILITY_VOICE));
  cai[0] = 6;
  cai[1] = plci->B1_resource;
  for (i=2;i<sizeof(cai);i++) cai[i] = 0;

  if ((GET_WORD(bp_parms[0].info) == B1_MODEM_ALL_NEGOTIATE)
   || (GET_WORD(bp_parms[0].info) == B1_MODEM_ASYNC)
   || (GET_WORD(bp_parms[0].info) == B1_MODEM_SYNC_HDLC))
  { /* B1 - modem */
    for (i=0;i<7;i++) mdm_cfg[i].length = 0;

    if (bp_parms[3].length)
    {
      if(api_parse(&bp_parms[3].info[1],(word)bp_parms[3].length,"wwwwww", mdm_cfg))
      {
        return (_WRONG_MESSAGE_FORMAT);
      }
        
      cai[2] = 0; /* Bit rate for adaptation */

      dbug(1,dprintf("MDM Max Bit Rate:<%d>", GET_WORD(mdm_cfg[0].info)));

      PUT_WORD (&cai[13], 0);                          /* Min Tx speed */
      PUT_WORD (&cai[15], GET_WORD(mdm_cfg[0].info)); /* Max Tx speed */
      PUT_WORD (&cai[17], 0);                          /* Min Rx speed */
      PUT_WORD (&cai[19], GET_WORD(mdm_cfg[0].info)); /* Max Rx speed */

      cai[3] = 0; /* Async framing parameters */
      switch (GET_WORD (mdm_cfg[2].info))
      {       /* Parity     */
      case 1: /* odd parity */
        cai[3] |= (DSP_CAI_ASYNC_PARITY_ENABLE | DSP_CAI_ASYNC_PARITY_ODD);
        dbug(1,dprintf("MDM: odd parity"));
        break;

      case 2: /* even parity */
        cai[3] |= (DSP_CAI_ASYNC_PARITY_ENABLE | DSP_CAI_ASYNC_PARITY_EVEN);
        dbug(1,dprintf("MDM: even parity"));
        break;

      default:
        dbug(1,dprintf("MDM: no parity"));
        break;
      }

      switch (GET_WORD (mdm_cfg[3].info))
      {       /* stop bits   */
      case 1: /* 2 stop bits */
        cai[3] |= DSP_CAI_ASYNC_TWO_STOP_BITS;
        dbug(1,dprintf("MDM: 2 stop bits"));
        break;

      default:
        dbug(1,dprintf("MDM: 1 stop bit"));
        break;
      }

      switch (GET_WORD (mdm_cfg[1].info))
      {     /* char length */
      case 5:
        cai[3] |= DSP_CAI_ASYNC_CHAR_LENGTH_5;
        dbug(1,dprintf("MDM: 5 bits"));
        break;

      case 6:
        cai[3] |= DSP_CAI_ASYNC_CHAR_LENGTH_6;
        dbug(1,dprintf("MDM: 6 bits"));
        break;

      case 7:
        cai[3] |= DSP_CAI_ASYNC_CHAR_LENGTH_7;
        dbug(1,dprintf("MDM: 7 bits"));
        break;

      default:
        dbug(1,dprintf("MDM: 8 bits"));
        break;
      }

      cai[7] = 0; /* Line taking options */
      cai[8] = 0; /* Modulation negotiation options */
      cai[9] = 0; /* Modulation options */

      if (((plci->call_dir & CALL_DIR_ORIGINATE) != 0) ^ ((plci->call_dir & CALL_DIR_OUT) != 0))
      {
        cai[9] |= DSP_CAI_MODEM_REVERSE_DIRECTION;
        dbug(1, dprintf("MDM: Reverse direction"));
      }

      if (GET_WORD (mdm_cfg[4].info) & MDM_CAPI_DISABLE_RETRAIN)
      {
        cai[9] |= DSP_CAI_MODEM_DISABLE_RETRAIN;
        dbug(1, dprintf("MDM: Disable retrain"));
      }

      if (GET_WORD (mdm_cfg[4].info) & MDM_CAPI_DISABLE_RING_TONE)
      {
        cai[7] |= DSP_CAI_MODEM_DISABLE_CALLING_TONE | DSP_CAI_MODEM_DISABLE_ANSWER_TONE;
        dbug(1, dprintf("MDM: Disable ring tone"));
      }

      if (GET_WORD (mdm_cfg[4].info) & MDM_CAPI_GUARD_1800)
      {
        cai[8] |= DSP_CAI_MODEM_GUARD_TONE_1800HZ;
        dbug(1, dprintf("MDM: 1800 guard tone"));
      }
      else if (GET_WORD (mdm_cfg[4].info) & MDM_CAPI_GUARD_550 )
      {
        cai[8] |= DSP_CAI_MODEM_GUARD_TONE_550HZ;
        dbug(1, dprintf("MDM: 550 guard tone"));
      }

      if ((GET_WORD (mdm_cfg[5].info) & 0x00ff) == MDM_CAPI_NEG_V100)
      {
        cai[8] |= DSP_CAI_MODEM_NEGOTIATE_V100;
        dbug(1, dprintf("MDM: V100"));
      }
      else if ((GET_WORD (mdm_cfg[5].info) & 0x00ff) == MDM_CAPI_NEG_MOD_CLASS)
      {
        cai[8] |= DSP_CAI_MODEM_NEGOTIATE_IN_CLASS;
        dbug(1, dprintf("MDM: IN CLASS"));
      }
      else if ((GET_WORD (mdm_cfg[5].info) & 0x00ff) == MDM_CAPI_NEG_DISABLED)
      {
        cai[8] |= DSP_CAI_MODEM_NEGOTIATE_DISABLED;
        dbug(1, dprintf("MDM: DISABLED"));
      }
      cai[0] = 20;

      if ((plci->adapter->man_profile.private_options & (1L << PRIVATE_V18))
       && (GET_WORD(mdm_cfg[5].info) & 0x8000)) /* Private V.18 enable */
      {
        plci->requested_options |= 1L << PRIVATE_V18;
      }
      if (GET_WORD(mdm_cfg[5].info) & 0x4000) /* Private VOWN enable */
        plci->requested_options |= 1L << PRIVATE_VOWN;

      if ((plci->requested_options_conn | plci->requested_options | plci->adapter->requested_options_table[plci->appl->Id-1])
        & ((1L << PRIVATE_V18) | (1L << PRIVATE_VOWN)))
      {
        if (!api_parse(&bp_parms[3].info[1],(word)bp_parms[3].length,"wwwwwws", mdm_cfg))
        {
          i = 27;
          if (mdm_cfg[6].length >= 4)
          {
            d = GET_DWORD(&mdm_cfg[6].info[1]);
            cai[7] |= (byte) d;          /* line taking options */
            cai[9] |= (byte)(d >> 8);    /* modulation options */
            cai[++i] = (byte)(d >> 16);  /* vown modulation options */
            cai[++i] = (byte)(d >> 24);
            if (mdm_cfg[6].length >= 8)
            {
              d = GET_DWORD(&mdm_cfg[6].info[5]);
              cai[10] |= (byte) d;        /* disabled modulations mask */
              cai[11] |= (byte)(d >> 8);
              if (mdm_cfg[6].length >= 12)
              {
                d = GET_DWORD(&mdm_cfg[6].info[9]);
                cai[12] = (byte) d;          /* enabled modulations mask */
                cai[++i] = (byte)(d >> 8);   /* vown enabled modulations */
                cai[++i] = (byte)(d >> 16);
                cai[++i] = (byte)(d >> 24);
                cai[++i] = 0;
                if (mdm_cfg[6].length >= 14)
                {
                  w = GET_WORD(&mdm_cfg[6].info[13]);
                  if (w != 0)
                    PUT_WORD(&cai[13], w);  /* min tx speed */
                  if (mdm_cfg[6].length >= 16)
                  {
                    w = GET_WORD(&mdm_cfg[6].info[15]);
                    if (w != 0)
                      PUT_WORD(&cai[15], w);  /* max tx speed */
                    if (mdm_cfg[6].length >= 18)
                    {
                      w = GET_WORD(&mdm_cfg[6].info[17]);
                      if (w != 0)
                        PUT_WORD(&cai[17], w);  /* min rx speed */
                      if (mdm_cfg[6].length >= 20)
                      {
                        w = GET_WORD(&mdm_cfg[6].info[19]);
                        if (w != 0)
                          PUT_WORD(&cai[19], w);  /* max rx speed */
                        if (mdm_cfg[6].length >= 22)
                        {
                          w = GET_WORD(&mdm_cfg[6].info[21]);
                          cai[23] = (byte)(-((short) w));  /* transmit level */
                          if (mdm_cfg[6].length >= 24)
                          {
                            w = GET_WORD(&mdm_cfg[6].info[23]);
                            cai[22] |= (byte) w;        /* info options mask */
                            cai[21] |= (byte)(w >> 8);  /* disabled symbol rates */
                          }
                        }
                      }
                    }
                  }
                }
              }
            }
          }
          cai[27] = i - 27;
          i++;
          if (!api_parse(&bp_parms[3].info[1],(word)bp_parms[3].length,"wwwwwwss", mdm_cfg))
          {
            if (!api_parse(&mdm_cfg[7].info[1],(word)mdm_cfg[7].length,"sss", mdm_cfg_v18))
            {
              for (n = 0; n < 3; n++)
              {
                cai[i] = (byte)(mdm_cfg_v18[n].length);
                for (j = 1; j < ((word)(cai[i] + 1)); j++)
                  cai[i+j] = mdm_cfg_v18[n].info[j];
                i += cai[i] + 1;
              }
            }
          }
          cai[0] = (byte)(i - 1);
        }
      }

    }
  }
  if(GET_WORD(bp_parms[0].info)==2 ||                         /* V.110 async */
     GET_WORD(bp_parms[0].info)==3 )                          /* V.110 sync */
  {
    if(bp_parms[3].length){
      dbug(1,dprintf("V.110,%d",GET_WORD(&bp_parms[3].info[1])));
      switch(GET_WORD(&bp_parms[3].info[1])){                 /* Rate */
        case 0:
        case 56000:
          if(GET_WORD(bp_parms[0].info)==3){                  /* V.110 sync 56k */
            dbug(1,dprintf("56k sync HSCX"));
            cai[1] = 8;
            cai[2] = 0;
            cai[3] = 0;
          }
          else if(GET_WORD(bp_parms[0].info)==2){
            dbug(1,dprintf("56k async DSP"));
            cai[2] = 9;
          }
          break;
        case 50:     cai[2] = 1;  break;
        case 75:     cai[2] = 1;  break;
        case 110:    cai[2] = 1;  break;
        case 150:    cai[2] = 1;  break;
        case 200:    cai[2] = 1;  break;
        case 300:    cai[2] = 1;  break;
        case 600:    cai[2] = 1;  break;
        case 1200:   cai[2] = 2;  break;
        case 2400:   cai[2] = 3;  break;
        case 4800:   cai[2] = 4;  break;
        case 7200:   cai[2] = 10; break;
        case 9600:   cai[2] = 5;  break;
        case 12000:  cai[2] = 13; break;
        case 24000:  cai[2] = 0;  break;
        case 14400:  cai[2] = 11; break;
        case 19200:  cai[2] = 6;  break;
        case 28800:  cai[2] = 12; break;
        case 38400:  cai[2] = 7;  break;
        case 48000:  cai[2] = 8;  break;
        case 76:     cai[2] = 15; break;  /* 75/1200     */
        case 1201:   cai[2] = 14; break;  /* 1200/75     */
        case 56001:  cai[2] = 9;  break;  /* V.110 56000 */

        default:
          return _B1_PARM_NOT_SUPPORTED;
      }
      cai[3] = 0;
      if (cai[1] == 13)                                        /* v.110 async */
      {
        if (bp_parms[3].length >= 8)
        {
          switch (GET_WORD (&bp_parms[3].info[3]))
          {       /* char length */
          case 5:
            cai[3] |= DSP_CAI_ASYNC_CHAR_LENGTH_5;
            break;
          case 6:
            cai[3] |= DSP_CAI_ASYNC_CHAR_LENGTH_6;
            break;
          case 7:
            cai[3] |= DSP_CAI_ASYNC_CHAR_LENGTH_7;
            break;
          }
          switch (GET_WORD (&bp_parms[3].info[5]))
          {       /* Parity     */
          case 1: /* odd parity */
            cai[3] |= (DSP_CAI_ASYNC_PARITY_ENABLE | DSP_CAI_ASYNC_PARITY_ODD);
            break;
          case 2: /* even parity */
            cai[3] |= (DSP_CAI_ASYNC_PARITY_ENABLE | DSP_CAI_ASYNC_PARITY_EVEN);
            break;
          }
          switch (GET_WORD (&bp_parms[3].info[7]))
          {       /* stop bits   */
          case 1: /* 2 stop bits */
            cai[3] |= DSP_CAI_ASYNC_TWO_STOP_BITS;
            break;
          }
        }
      }
    }
    else if(cai[1]==8 || GET_WORD(bp_parms[0].info)==3 ){
      dbug(1,dprintf("V.110 default 56k sync"));
      cai[1] = 8;
      cai[2] = 0;
      cai[3] = 0;
    }
    else {
      dbug(1,dprintf("V.110 default 9600 async"));
      cai[2] = 5;
    }
  }
  PUT_WORD(&cai[5],plci->appl->MaxDataLength);
  dbug(1,dprintf("CAI[%d]=%x,%x,%x,%x,%x,%x", cai[0], cai[1], cai[2], cai[3], cai[4], cai[5], cai[6]));
/* HexDump ("CAI", sizeof(cai), &cai[0]); */

  add_p(plci, CAI, cai);
  return 0;
}

/*------------------------------------------------------------------*/
/* put parameter for b2 and B3  protocol in the parameter buffer    */
/*------------------------------------------------------------------*/

word add_b23(PLCI   * plci, API_PARSE * bp)
{
  word i, fax_control_bits;
  byte pos, len;
  byte SAPI = 0x40;  /* default SAPI 16 for x.31 */
    API_PARSE bp_parms[8];
  API_PARSE * b1_config;
  API_PARSE * b2_config;
    API_PARSE b2_config_parms[8];
  API_PARSE * b3_config;
    API_PARSE b3_config_parms[6];
    API_PARSE global_config[2];

  static byte llc[3] = {2,0,0};
  static byte dlc[20] = {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0};
  static byte nlc[256];
  static byte lli[12] = {1,1};

  const byte llc2_out[] = {1,2,4,6,2,0,0,0, X75_V42BIS,V120_L2,V120_V42BIS,V120_L2,6};
  const byte llc2_in[]  = {1,3,4,6,3,0,0,0, X75_V42BIS,V120_L2,V120_V42BIS,V120_L2,6};

  const byte llc3[] = {4,3,2,2,6,6,0};
  const byte header[] = {0,2,3,3,0,0,0};

  for(i=0;i<8;i++) bp_parms[i].length = 0;
  for(i=0;i<6;i++) b2_config_parms[i].length = 0;
  for(i=0;i<5;i++) b3_config_parms[i].length = 0;

  lli[0] = 1;
  lli[1] = 1;
  if (plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_XONOFF_FLOW_CONTROL)
    lli[1] |= 2;
  if (plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_OOB_CHANNEL)
    lli[1] |= 4;

  if ((lli[1] & 0x02) && (diva_xdi_extended_features & DIVA_CAPI_USE_CMA)) {
    lli[1] |= 0x10;
    if (plci->rx_dma_descriptor <= 0) {
      plci->rx_dma_descriptor=diva_get_dma_descriptor(plci,&plci->rx_dma_magic);
      if (plci->rx_dma_descriptor >= 0)
        plci->rx_dma_descriptor++;
    }
    if (plci->rx_dma_descriptor > 0) {
      lli[0] = 6;
      lli[1] |= 0x40;
      lli[2] = (byte)(plci->rx_dma_descriptor - 1);
      lli[3] = (byte)plci->rx_dma_magic;
      lli[4] = (byte)(plci->rx_dma_magic >>  8);
      lli[5] = (byte)(plci->rx_dma_magic >> 16);
      lli[6] = (byte)(plci->rx_dma_magic >> 24);
    }
  }

  if (DIVA_CAPI_SUPPORTS_NO_CANCEL(plci->adapter)) {
    lli[1] |= 0x20;
  }

  dbug(1,dprintf("add_b23"));
  api_save_msg(bp, "s", &plci->B_protocol);

  if(!bp->length && plci->tel)
  {
    plci->adv_nl = TRUE;
    dbug(1,dprintf("Default adv.Nl"));
    add_p(plci,LLI,lli);
    plci->B2_prot = 1 /*XPARENT*/;
    plci->B3_prot = 0 /*XPARENT*/;
    llc[1] = 2;
    llc[2] = 4;
    add_p(plci, LLC, llc);
    dlc[0] = 2;
    PUT_WORD(&dlc[1],plci->appl->MaxDataLength);
    add_p(plci, DLC, dlc);
    return 0;
  }

  if(!bp->length) /*default*/
  {   
    dbug(1,dprintf("ret default"));
    add_p(plci,LLI,lli);
    plci->B2_prot = 0 /*X.75   */;
    plci->B3_prot = 0 /*XPARENT*/;
    llc[1] = 1;
    llc[2] = 4;
    add_p(plci, LLC, llc);
    dlc[0] = 2;
    PUT_WORD(&dlc[1],plci->appl->MaxDataLength);
    add_p(plci, DLC, dlc);
    return 0;
  }
  dbug(1,dprintf("b_prot_len=%d",(word)bp->length));
  if((word)bp->length > 256)    return _WRONG_MESSAGE_FORMAT;

  if(api_parse(&bp->info[1], (word)bp->length, "wwwsssb", bp_parms))
  {
    bp_parms[6].length = 0;
    if(api_parse(&bp->info[1], (word)bp->length, "wwwsss", bp_parms))
    {
      dbug(1,dprintf("b-form.!"));
      return _WRONG_MESSAGE_FORMAT;
    }
  }
  else if (api_parse(&bp->info[1], (word)bp->length, "wwwssss", bp_parms))
  {
    dbug(1,dprintf("b-form.!"));
    return _WRONG_MESSAGE_FORMAT;
  }

  if(plci->tel==ADV_VOICE) /* transparent B on advanced voice */
  {  
    if(GET_WORD(bp_parms[1].info)!=1
    || GET_WORD(bp_parms[2].info)!=0) return _B2_NOT_SUPPORTED;
    plci->adv_nl = TRUE;
  }
  else if(plci->tel) return _B2_NOT_SUPPORTED;


  if ((GET_WORD(bp_parms[1].info) == B2_RTP)
   && (GET_WORD(bp_parms[2].info) == B3_RTP)
   && (plci->adapter->man_profile.private_options & (1L << PRIVATE_RTP)))
  {
    add_p(plci,LLI,lli);
    plci->B2_prot = (byte) GET_WORD(bp_parms[1].info);
    plci->B3_prot = (byte) GET_WORD(bp_parms[2].info);
    llc[1] = (plci->call_dir & (CALL_DIR_ORIGINATE | CALL_DIR_FORCE_OUTG_NL)) ? 14 : 13;
    llc[2] = 4;
    add_p(plci, LLC, llc);
    dlc[0] = 2;
    PUT_WORD(&dlc[1],plci->appl->MaxDataLength);
    dlc[3] = 3; /* Addr A */
    dlc[4] = 1; /* Addr B */
    dlc[5] = 7; /* modulo mode */
    dlc[6] = 7; /* window size */
    dlc[7] = 0; /* XID len Lo  */
    dlc[8] = 0; /* XID len Hi  */
    for (i = 0; i < bp_parms[4].length; i++)
      dlc[9+i] = bp_parms[4].info[1+i];
    dlc[0] = (byte)(8 + bp_parms[4].length);
    add_p(plci, DLC, dlc);
    for (i = 0; i < bp_parms[5].length; i++)
      nlc[1+i] = bp_parms[5].info[1+i];
    nlc[0] = (byte)(bp_parms[5].length);
    add_p(plci, NLC, nlc);
    return 0;
  }



  if ((GET_WORD(bp_parms[1].info) >= 32)
   || (!((1L << GET_WORD(bp_parms[1].info)) & plci->adapter->profile.B2_Protocols)
    && ((GET_WORD(bp_parms[1].info) != B2_PIAFS)
     || !(plci->adapter->man_profile.private_options & (1L << PRIVATE_PIAFS)))))

  {
    return _B2_NOT_SUPPORTED;
  }
  if ((GET_WORD(bp_parms[2].info) >= 32)
   || !((1L << GET_WORD(bp_parms[2].info)) & plci->adapter->profile.B3_Protocols))
  {
    return _B3_NOT_SUPPORTED;
  }
  if ((GET_WORD(bp_parms[1].info) != B2_SDLC)
   && ((GET_WORD(bp_parms[0].info) == B1_MODEM_ALL_NEGOTIATE)
    || (GET_WORD(bp_parms[0].info) == B1_MODEM_ASYNC)
    || (GET_WORD(bp_parms[0].info) == B1_MODEM_SYNC_HDLC)))
  {
    return (add_modem_b23 (plci, bp_parms));
  }

  add_p(plci,LLI,lli);

  plci->B2_prot = (byte) GET_WORD(bp_parms[1].info);
  plci->B3_prot = (byte) GET_WORD(bp_parms[2].info);
  if(plci->B2_prot==12) SAPI = 0; /* default SAPI D-channel */

  if(bp_parms[6].length)
  {
    if(api_parse(&bp_parms[6].info[1], (word)bp_parms[6].length, "w", global_config))
    {
      return _WRONG_MESSAGE_FORMAT;
    }
    switch(GET_WORD(global_config[0].info))
    {
    case 1:
      plci->call_dir = (plci->call_dir & ~CALL_DIR_ANSWER) | CALL_DIR_ORIGINATE;
      break;
    case 2:
      plci->call_dir = (plci->call_dir & ~CALL_DIR_ORIGINATE) | CALL_DIR_ANSWER;
      break;
    }
  }
  dbug(1,dprintf("call_dir=%04x", plci->call_dir));


  if (plci->B2_prot == B2_PIAFS)
    llc[1] = PIAFS_CRC;
  else
/* IMPLEMENT_PIAFS */
  {
    llc[1] = (plci->call_dir & (CALL_DIR_ORIGINATE | CALL_DIR_FORCE_OUTG_NL)) ?
             llc2_out[GET_WORD(bp_parms[1].info)] : llc2_in[GET_WORD(bp_parms[1].info)];
  }
  llc[2] = llc3[GET_WORD(bp_parms[2].info)];

  add_p(plci, LLC, llc);

  dlc[0] = 2;
  PUT_WORD(&dlc[1], plci->appl->MaxDataLength +
                      header[GET_WORD(bp_parms[2].info)]);

  b1_config = &bp_parms[3];
  nlc[0] = 0;
  if(plci->B3_prot == 4
  || plci->B3_prot == 5)
  {
    for (i=0;i<sizeof(T30_INFO);i++) nlc[i] = 0;
    nlc[0] = sizeof(T30_INFO);
    if (plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_FAX_PAPER_FORMATS)
      ((T30_INFO *)&nlc[1])->operating_mode = T30_OPERATING_MODE_CAPI;
    ((T30_INFO *)&nlc[1])->rate_div_2400 = 0xff;
    if(b1_config->length>=2)
    {
      ((T30_INFO *)&nlc[1])->rate_div_2400 = (byte)(GET_WORD(&b1_config->info[1])/2400);
    }
  }
  b2_config = &bp_parms[4];


  if (llc[1] == PIAFS_CRC)
  {
    if (plci->B3_prot != B3_TRANSPARENT)
    {
      return _B_STACK_NOT_SUPPORTED;
    }
    if(b2_config->length && api_parse(&b2_config->info[1], (word)b2_config->length, "bwww", b2_config_parms)) {
      return _WRONG_MESSAGE_FORMAT;
    }
    PUT_WORD(&dlc[1],plci->appl->MaxDataLength);
    dlc[3] = 0; /* Addr A */
    dlc[4] = 0; /* Addr B */
    dlc[5] = 0; /* modulo mode */
    dlc[6] = 0; /* window size */
    if (b2_config->length >= 7){
      dlc[ 7] = 7; 
      dlc[ 8] = 0; 
      dlc[ 9] = b2_config_parms[0].info[0]; /* PIAFS protocol Speed configuration */
      dlc[10] = b2_config_parms[1].info[0]; /* V.42bis P0 */
      dlc[11] = b2_config_parms[1].info[1]; /* V.42bis P0 */
      dlc[12] = b2_config_parms[2].info[0]; /* V.42bis P1 */
      dlc[13] = b2_config_parms[2].info[1]; /* V.42bis P1 */
      dlc[14] = b2_config_parms[3].info[0]; /* V.42bis P2 */
      dlc[15] = b2_config_parms[3].info[1]; /* V.42bis P2 */
      dlc[ 0] = 15;
      if(b2_config->length >= 8) { /* PIAFS control abilities */
        dlc[ 7] = 10; 
        dlc[16] = 2; /* Length of PIAFS extention */
        dlc[17] = PIAFS_UDATA_ABILITIES; /* control (UDATA) ability */
        dlc[18] = b2_config_parms[4].info[0]; /* value */
        dlc[ 0] = 18;
      }
    }
    else /* default values, 64K, variable, no compression */
    {
      dlc[ 7] = 7; 
      dlc[ 8] = 0; 
      dlc[ 9] = 0x03; /* PIAFS protocol Speed configuration */
      dlc[10] = 0x03; /* V.42bis P0 */
      dlc[11] = 0;    /* V.42bis P0 */
      dlc[12] = 0;    /* V.42bis P1 */
      dlc[13] = 0;    /* V.42bis P1 */
      dlc[14] = 0;    /* V.42bis P2 */
      dlc[15] = 0;    /* V.42bis P2 */
    dlc[ 0] = 15;
    }
    add_p(plci, DLC, dlc);
  }
  else

  if ((llc[1] == V120_L2) || (llc[1] == V120_V42BIS))
  {
    if (plci->B3_prot != B3_TRANSPARENT)
      return _B_STACK_NOT_SUPPORTED;

    dlc[0] = 6;
    PUT_WORD (&dlc[1], GET_WORD (&dlc[1]) + 2);
    dlc[3] = 0x08;
    dlc[4] = 0x01;
    dlc[5] = 127;
    dlc[6] = 7;
    if (b2_config->length != 0)
    {
      if((llc[1]==V120_V42BIS) && api_parse(&b2_config->info[1], (word)b2_config->length, "bbbbwww", b2_config_parms)) {
        return _WRONG_MESSAGE_FORMAT;
      }
      dlc[3] = (byte)((b2_config->info[2] << 3) | ((b2_config->info[1] >> 5) & 0x04));
      dlc[4] = (byte)((b2_config->info[1] << 1) | 0x01);
      if (b2_config->info[3] != 128)
      {
        dbug(1,dprintf("1D-dlc= %x %x %x %x %x", dlc[0], dlc[1], dlc[2], dlc[3], dlc[4]));
        return _B2_PARM_NOT_SUPPORTED;
      }
      dlc[5] = (byte)(b2_config->info[3] - 1);
      dlc[6] = b2_config->info[4];
      if(llc[1]==V120_V42BIS){
        if (b2_config->length >= 10){
          dlc[ 7] = 6; 
          dlc[ 8] = 0; 
          dlc[ 9] = b2_config_parms[4].info[0];
          dlc[10] = b2_config_parms[4].info[1];
          dlc[11] = b2_config_parms[5].info[0];
          dlc[12] = b2_config_parms[5].info[1];
          dlc[13] = b2_config_parms[6].info[0];
          dlc[14] = b2_config_parms[6].info[1];
          dlc[ 0] = 14;
          dbug(1,dprintf("b2_config_parms[4].info[0] [1]:  %x %x", b2_config_parms[4].info[0], b2_config_parms[4].info[1]));
          dbug(1,dprintf("b2_config_parms[5].info[0] [1]:  %x %x", b2_config_parms[5].info[0], b2_config_parms[5].info[1]));
          dbug(1,dprintf("b2_config_parms[6].info[0] [1]:  %x %x", b2_config_parms[6].info[0], b2_config_parms[6].info[1]));
        }
        else {
          dlc[ 6] = 14;
        }
      }
    }
  }
  else
  {
    if(b2_config->length)
    {
      dbug(1,dprintf("B2-Config"));
      if(llc[1]==X75_V42BIS){
        if(api_parse(&b2_config->info[1], (word)b2_config->length, "bbbbwww", b2_config_parms))
        {
          return _WRONG_MESSAGE_FORMAT;
        }
      }
      else {
        if(api_parse(&b2_config->info[1], (word)b2_config->length, "bbbbs", b2_config_parms))
        {
          return _WRONG_MESSAGE_FORMAT;
        }
      }
          /* if B2 Protocol is LAPD, b2_config structure is different */
      if(llc[1]==6)
      {
        dlc[0] = 4;
        if(b2_config->length>=1) dlc[2] = b2_config->info[1];      /* TEI */
        else dlc[2] = 0x01;
        if( (b2_config->length>=2) && (plci->B2_prot==12) )
        {
          SAPI = b2_config->info[2];    /* SAPI */
        }
        dlc[1] = SAPI;
        if( (b2_config->length>=3) && (b2_config->info[3]==128) )
        {
          dlc[3] = 127;      /* Mode */
        }
        else
        {
          dlc[3] = 7;        /* Mode */
        }
   
        if(b2_config->length>=4) dlc[4] = b2_config->info[4];      /* Window */
        else dlc[4] = 1;
        dbug(1,dprintf("D-dlc[%d]=%x,%x,%x,%x", dlc[0], dlc[1], dlc[2], dlc[3], dlc[4]));
        if(b2_config->length>5) return _B2_PARM_NOT_SUPPORTED;
      }
      else
      {
        dlc[0] = (byte)(b2_config_parms[4].length+6);
        dlc[3] = b2_config->info[1];
        dlc[4] = b2_config->info[2];
        if(b2_config->info[3]!=8 && b2_config->info[3]!=128){
          dbug(1,dprintf("1D-dlc= %x %x %x %x %x", dlc[0], dlc[1], dlc[2], dlc[3], dlc[4]));
          return _B2_PARM_NOT_SUPPORTED;
        }

        dlc[5] = (byte)(b2_config->info[3]-1);
        dlc[6] = b2_config->info[4];
        if(dlc[6]>dlc[5]){
          dbug(1,dprintf("2D-dlc= %x %x %x %x %x %x %x", dlc[0], dlc[1], dlc[2], dlc[3], dlc[4], dlc[5], dlc[6]));
          return _B2_PARM_NOT_SUPPORTED;
        }
 
        if(llc[1]==X75_V42BIS) {
          if (b2_config->length >= 10){
            dlc[ 7] = 6; 
            dlc[ 8] = 0; 
            dlc[ 9] = b2_config_parms[4].info[0];
            dlc[10] = b2_config_parms[4].info[1];
            dlc[11] = b2_config_parms[5].info[0];
            dlc[12] = b2_config_parms[5].info[1];
            dlc[13] = b2_config_parms[6].info[0];
            dlc[14] = b2_config_parms[6].info[1];
            dlc[ 0] = 14;
            dbug(1,dprintf("b2_config_parms[4].info[0] [1]:  %x %x", b2_config_parms[4].info[0], b2_config_parms[4].info[1]));
            dbug(1,dprintf("b2_config_parms[5].info[0] [1]:  %x %x", b2_config_parms[5].info[0], b2_config_parms[5].info[1]));
            dbug(1,dprintf("b2_config_parms[6].info[0] [1]:  %x %x", b2_config_parms[6].info[0], b2_config_parms[6].info[1]));
          }
          else {
            dlc[ 6] = 14;
          }

        }
        else {
          PUT_WORD(&dlc[7], (word)b2_config_parms[4].length);
          for(i=0; i<b2_config_parms[4].length; i++)
            dlc[11+i] = b2_config_parms[4].info[1+i];
        }
      }
    }
  }
  add_p(plci, DLC, dlc);

  b3_config = &bp_parms[5];
  if(b3_config->length)
  {
    if(plci->B3_prot == 4 
    || plci->B3_prot == 5)
    {
      if(api_parse(&b3_config->info[1], (word)b3_config->length, "wwss", b3_config_parms))
      {
        return _WRONG_MESSAGE_FORMAT;
      }
      i = GET_WORD((byte   *)(b3_config_parms[0].info));
      ((T30_INFO *)&nlc[1])->resolution = (byte)(((i & 0x0001) ||
        ((plci->B3_prot == 4) && (((byte)(GET_WORD((byte   *)b3_config_parms[1].info))) != 5))) ? T30_RESOLUTION_R8_0770_OR_200 : 0);
      ((T30_INFO *)&nlc[1])->data_format = (byte)(GET_WORD((byte   *)b3_config_parms[1].info));
      fax_control_bits = T30_CONTROL_BIT_ALL_FEATURES;
      if ((((T30_INFO *)&nlc[1])->rate_div_2400 != 0) && (((T30_INFO *)&nlc[1])->rate_div_2400 <= 6))
        fax_control_bits &= ~T30_CONTROL_BIT_ENABLE_V34FAX;
      if (plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_FAX_PAPER_FORMATS)
      {

        if ((plci->requested_options_conn | plci->requested_options | plci->adapter->requested_options_table[plci->appl->Id-1])
          & (1L << PRIVATE_FAX_PAPER_FORMATS))
        {
          ((T30_INFO *)&nlc[1])->resolution |= T30_RESOLUTION_R8_1540 |
            T30_RESOLUTION_R16_1540_OR_400 | T30_RESOLUTION_300_300 |
            T30_RESOLUTION_INCH_BASED | T30_RESOLUTION_METRIC_BASED;
        }

 ((T30_INFO *)&nlc[1])->recording_properties =
   T30_RECORDING_WIDTH_ISO_A3 |
   (T30_RECORDING_LENGTH_UNLIMITED << 2) |
   (T30_MIN_SCANLINE_TIME_00_00_00 << 4);
      }
      if(plci->B3_prot == 5)
      {
        if (i & 0x0002) /* Accept incoming fax-polling requests */
          fax_control_bits |= T30_CONTROL_BIT_ACCEPT_POLLING;
        if (i & 0x2000) /* Do not use MR compression */
          fax_control_bits &= ~T30_CONTROL_BIT_ENABLE_2D_CODING;
        if (i & 0x4000) /* Do not use MMR compression */
          fax_control_bits &= ~T30_CONTROL_BIT_ENABLE_T6_CODING;
        if (i & 0x8000) /* Do not use ECM */
          fax_control_bits &= ~T30_CONTROL_BIT_ENABLE_ECM;
        if (plci->fax_connect_info_length != 0)
        {
          ((T30_INFO *)&nlc[1])->resolution = ((T30_INFO   *)plci->fax_connect_info_buffer)->resolution;
          ((T30_INFO *)&nlc[1])->data_format = ((T30_INFO   *)plci->fax_connect_info_buffer)->data_format;
          ((T30_INFO *)&nlc[1])->recording_properties = ((T30_INFO   *)plci->fax_connect_info_buffer)->recording_properties;
          fax_control_bits |= GET_WORD(&((T30_INFO   *)plci->fax_connect_info_buffer)->control_bits_low) &
            (T30_CONTROL_BIT_REQUEST_POLLING | T30_CONTROL_BIT_MORE_DOCUMENTS);
        }
      }
      /* copy station id to NLC */
      for(i=0; i<20; i++)
      {
        if(i<b3_config_parms[2].length)
        {
          ((T30_INFO *)&nlc[1])->station_id[i] = ((byte   *)b3_config_parms[2].info)[1+i];
        }
        else
        {
          ((T30_INFO *)&nlc[1])->station_id[i] = ' ';
        }
      }
      ((T30_INFO *)&nlc[1])->station_id_len = 20;
      /* copy head line to NLC */
      if(b3_config_parms[3].length)
      {

        pos = (byte)(fax_head_line_time (&(((T30_INFO *)&nlc[1])->station_id[20])));
        if (pos != 0)
        {
          if (CAPI_MAX_DATE_TIME_LENGTH + 2 + b3_config_parms[3].length > CAPI_MAX_HEAD_LINE_SPACE)
            pos = 0;
          else
          {
            ((T30_INFO *)&nlc[1])->station_id[20 + pos++] = ' ';
            ((T30_INFO *)&nlc[1])->station_id[20 + pos++] = ' ';
            len = (byte)b3_config_parms[2].length;
            if (len > 20)
              len = 20;
            if (CAPI_MAX_DATE_TIME_LENGTH + 2 + len + 2 + b3_config_parms[3].length <= CAPI_MAX_HEAD_LINE_SPACE)
            {
              for (i = 0; i < len; i++)
                ((T30_INFO *)&nlc[1])->station_id[20 + pos++] = ((byte   *)b3_config_parms[2].info)[1+i];
              ((T30_INFO *)&nlc[1])->station_id[20 + pos++] = ' ';
              ((T30_INFO *)&nlc[1])->station_id[20 + pos++] = ' ';
            }
          }
        }

        len = (byte)b3_config_parms[3].length;
        if (len > CAPI_MAX_HEAD_LINE_SPACE - pos)
          len = (byte)(CAPI_MAX_HEAD_LINE_SPACE - pos);
        ((T30_INFO *)&nlc[1])->head_line_len = (byte)(pos + len);
        nlc[0] += (byte)(pos + len);
        for (i = 0; i < len; i++)
          ((T30_INFO *)&nlc[1])->station_id[20 + pos++] = ((byte   *)b3_config_parms[3].info)[1+i];
        }
      else
        ((T30_INFO *)&nlc[1])->head_line_len = 0;

      plci->nsf_control_bits = 0;
      if(plci->B3_prot == 5)
      {
        if ((plci->adapter->man_profile.private_options & (1L << PRIVATE_FAX_SUB_SEP_PWD))
         && (GET_WORD((byte   *)b3_config_parms[1].info) & 0x8000)) /* Private SUB/SEP/PWD enable */
        {
          plci->requested_options |= 1L << PRIVATE_FAX_SUB_SEP_PWD;
        }
        if ((plci->adapter->man_profile.private_options & (1L << PRIVATE_FAX_NONSTANDARD))
         && (GET_WORD((byte   *)b3_config_parms[1].info) & 0x4000)) /* Private non-standard facilities enable */
        {
          plci->requested_options |= 1L << PRIVATE_FAX_NONSTANDARD;
        }
        if ((plci->requested_options_conn | plci->requested_options | plci->adapter->requested_options_table[plci->appl->Id-1])
          & ((1L << PRIVATE_FAX_SUB_SEP_PWD) | (1L << PRIVATE_FAX_NONSTANDARD)))
        {
        if ((plci->requested_options_conn | plci->requested_options | plci->adapter->requested_options_table[plci->appl->Id-1])
          & (1L << PRIVATE_FAX_SUB_SEP_PWD))
        {
          fax_control_bits |= T30_CONTROL_BIT_ACCEPT_SUBADDRESS | T30_CONTROL_BIT_ACCEPT_PASSWORD;
          if (fax_control_bits & T30_CONTROL_BIT_ACCEPT_POLLING)
            fax_control_bits |= T30_CONTROL_BIT_ACCEPT_SEL_POLLING;
          }
            len = nlc[0];
          pos = ((byte)(((T30_INFO *) 0)->station_id + 20));
   if (pos < plci->fax_connect_info_length)
   {
     for (i = 1 + plci->fax_connect_info_buffer[pos]; i != 0; i--)
              nlc[++len] = plci->fax_connect_info_buffer[pos++];
          }
   else
     nlc[++len] = 0;
   if (pos < plci->fax_connect_info_length)
   {
     for (i = 1 + plci->fax_connect_info_buffer[pos]; i != 0; i--)
              nlc[++len] = plci->fax_connect_info_buffer[pos++];
          }
   else
     nlc[++len] = 0;
          if ((plci->requested_options_conn | plci->requested_options | plci->adapter->requested_options_table[plci->appl->Id-1])
            & (1L << PRIVATE_FAX_NONSTANDARD))
          {
     if ((pos < plci->fax_connect_info_length) && (plci->fax_connect_info_buffer[pos] != 0))
     {
              if ((plci->fax_connect_info_buffer[pos] >= 3) && (plci->fax_connect_info_buffer[pos+1] >= 2))
                plci->nsf_control_bits = GET_WORD(&plci->fax_connect_info_buffer[pos+2]);
       for (i = 1 + plci->fax_connect_info_buffer[pos]; i != 0; i--)
                nlc[++len] = plci->fax_connect_info_buffer[pos++];
            }
     else
     {
              if(api_parse(&b3_config->info[1], (word)b3_config->length, "wwsss", b3_config_parms))
              {
                dbug(1,dprintf("non-standard facilities info missing or wrong format"));
                nlc[++len] = 0;
              }
       else
       {
                if ((b3_config_parms[4].length >= 3) && (b3_config_parms[4].info[1] >= 2))
                  plci->nsf_control_bits = GET_WORD(&b3_config_parms[4].info[2]);
         nlc[++len] = (byte)(b3_config_parms[4].length);
         for (i = 0; i < b3_config_parms[4].length; i++)
    nlc[++len] = b3_config_parms[4].info[1+i];
       }
            }
          }
            nlc[0] = len;
   if ((plci->nsf_control_bits & T30_NSF_CONTROL_BIT_ENABLE_NSF)
    && (plci->nsf_control_bits & T30_NSF_CONTROL_BIT_NEGOTIATE_RESP))
   {
            ((T30_INFO *)&nlc[1])->operating_mode = T30_OPERATING_MODE_CAPI_NEG;
          }
        }
      }

      PUT_WORD(&(((T30_INFO *)&nlc[1])->control_bits_low), fax_control_bits);
      len = ((byte)(((T30_INFO *) 0)->station_id + 20));
      for (i = 0; i < len; i++)
        plci->fax_connect_info_buffer[i] = nlc[1+i];
      ((T30_INFO   *) plci->fax_connect_info_buffer)->head_line_len = 0;
      i += ((T30_INFO *)&nlc[1])->head_line_len;
      while (i < nlc[0])
        plci->fax_connect_info_buffer[len++] = nlc[++i];
      plci->fax_connect_info_length = len;
    }
    else
    {
      nlc[0] = 14;
      if(b3_config->length!=16)
        return _B3_PARM_NOT_SUPPORTED;
      for(i=0; i<12; i++) nlc[1+i] = b3_config->info[1+i];
      if(GET_WORD(&b3_config->info[13])!=8 && GET_WORD(&b3_config->info[13])!=128)
        return _B3_PARM_NOT_SUPPORTED;
      nlc[13] = b3_config->info[13];
      if(GET_WORD(&b3_config->info[15])>=nlc[13])
        return _B3_PARM_NOT_SUPPORTED;
      nlc[14] = b3_config->info[15];
    }
  }
  else
  {
    if (plci->B3_prot == 4 
     || plci->B3_prot == 5 /*T.30 - FAX*/ ) return _B3_PARM_NOT_SUPPORTED;
  }
  add_p(plci, NLC, nlc);
  return 0;
}

/*----------------------------------------------------------------*/
/*      make the same as add_b23, but only for the modem related  */
/*      L2 and L3 B-Chan protocol.                                */
/*                                                                */
/*      Enabled L2 and L3 Configurations:                         */
/*        If L1 == Modem all negotiation                          */
/*          only L2 == Modem with full negotiation is allowed     */
/*        If L1 == Modem async or sync                            */
/*          only L2 == Transparent is allowed                     */
/*        L3 == Modem or L3 == Transparent are allowed            */
/*      B2 Configuration for modem:                               */
/*          word : enable/disable compression, bitoptions         */
/*      B3 Configuration for modem:                               */
/*          empty                                                 */
/*----------------------------------------------------------------*/
static word add_modem_b23 (PLCI  * plci, API_PARSE* bp_parms)
{
  static byte lli[12] = {1,1};
  static byte llc[3] = {2,0,0};
  static byte dlc[16] = {0,0,0,0,0,0,0,0,0,0,0,0,0,0,0,0};
    API_PARSE mdm_config[2];
  word i;
  word b2_config = 0;

  for(i=0;i<2;i++) mdm_config[i].length = 0;
  for(i=0;i<sizeof(dlc);i++) dlc[i] = 0;

  if (((GET_WORD(bp_parms[0].info) == B1_MODEM_ALL_NEGOTIATE)
    && (GET_WORD(bp_parms[1].info) != B2_MODEM_EC_COMPRESSION))
   || ((GET_WORD(bp_parms[0].info) != B1_MODEM_ALL_NEGOTIATE)
    && (GET_WORD(bp_parms[1].info) != B2_TRANSPARENT)))
  {
    return (_B_STACK_NOT_SUPPORTED);
  }
  if ((GET_WORD(bp_parms[2].info) != B3_MODEM)
   && (GET_WORD(bp_parms[2].info) != B3_TRANSPARENT))
  {
    return (_B_STACK_NOT_SUPPORTED);
  }

  plci->B2_prot = (byte) GET_WORD(bp_parms[1].info);
  plci->B3_prot = (byte) GET_WORD(bp_parms[2].info);

  if ((GET_WORD(bp_parms[1].info) == B2_MODEM_EC_COMPRESSION) && bp_parms[4].length)
  {
    if (api_parse (&bp_parms[4].info[1],
                  (word)bp_parms[4].length, "w",
                  mdm_config))
    {
      return (_WRONG_MESSAGE_FORMAT);
    }
    b2_config = GET_WORD(mdm_config[0].info);
  }

  /* OK, L2 is modem */

  lli[0] = 1;
  lli[1] = 1;
  if (plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_XONOFF_FLOW_CONTROL)
    lli[1] |= 2;
  if (plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_OOB_CHANNEL)
    lli[1] |= 4;

  if ((lli[1] & 0x02) && (diva_xdi_extended_features & DIVA_CAPI_USE_CMA)) {
    lli[1] |= 0x10;
    if (plci->rx_dma_descriptor <= 0) {
      plci->rx_dma_descriptor=diva_get_dma_descriptor(plci,&plci->rx_dma_magic);
      if (plci->rx_dma_descriptor >= 0)
        plci->rx_dma_descriptor++;
    }
    if (plci->rx_dma_descriptor > 0) {
      lli[1] |= 0x40;
      lli[0] = 6;
      lli[2] = (byte)(plci->rx_dma_descriptor - 1);
      lli[3] = (byte)plci->rx_dma_magic;
      lli[4] = (byte)(plci->rx_dma_magic >>  8);
      lli[5] = (byte)(plci->rx_dma_magic >> 16);
      lli[6] = (byte)(plci->rx_dma_magic >> 24);
    }
  }

  if (DIVA_CAPI_SUPPORTS_NO_CANCEL(plci->adapter)) {
    lli[1] |= 0x20;
  }

  llc[1] = (plci->call_dir & (CALL_DIR_ORIGINATE | CALL_DIR_FORCE_OUTG_NL)) ?
    /*V42*/ 10 : /*V42_IN*/ 9;
  llc[2] = 4;                      /* pass L3 always transparent */
  add_p(plci, LLI, lli);
  add_p(plci, LLC, llc);
  i =  1;
  PUT_WORD (&dlc[i], plci->appl->MaxDataLength);
  i += 2;
  if (GET_WORD(bp_parms[1].info) == B2_MODEM_EC_COMPRESSION)
  {
    if (bp_parms[4].length)
  {
    dbug(1, dprintf("MDM b2_config=%02x", b2_config));
    dlc[i++] = 3; /* Addr A */
    dlc[i++] = 1; /* Addr B */
    dlc[i++] = 7; /* modulo mode */
    dlc[i++] = 7; /* window size */
    dlc[i++] = 0; /* XID len Lo  */
    dlc[i++] = 0; /* XID len Hi  */

    if (b2_config & MDM_B2_DISABLE_V42bis)
    {
      dlc[i] |= DLC_MODEMPROT_DISABLE_V42_V42BIS;
    }
    if (b2_config & MDM_B2_DISABLE_MNP)
    {
      dlc[i] |= DLC_MODEMPROT_DISABLE_MNP_MNP5;
    }
    if (b2_config & MDM_B2_DISABLE_TRANS)
    {
      dlc[i] |= DLC_MODEMPROT_REQUIRE_PROTOCOL;
    }
    if (b2_config & MDM_B2_DISABLE_V42)
    {
      dlc[i] |= DLC_MODEMPROT_DISABLE_V42_DETECT;
    }
    if (b2_config & MDM_B2_DISABLE_COMP)
    {
      dlc[i] |= DLC_MODEMPROT_DISABLE_COMPRESSION;
    }
    i++;
  }
  }
  else
  {
    dlc[i++] = 3; /* Addr A */
    dlc[i++] = 1; /* Addr B */
    dlc[i++] = 7; /* modulo mode */
    dlc[i++] = 7; /* window size */
    dlc[i++] = 0; /* XID len Lo  */
    dlc[i++] = 0; /* XID len Hi  */
    dlc[i++] = DLC_MODEMPROT_DISABLE_V42_V42BIS |
               DLC_MODEMPROT_DISABLE_MNP_MNP5 |
               DLC_MODEMPROT_DISABLE_V42_DETECT |
               DLC_MODEMPROT_DISABLE_COMPRESSION;
  }
  dlc[0] = (byte)(i - 1);
/* HexDump ("DLC", sizeof(dlc), &dlc[0]); */
  add_p(plci, DLC, dlc);
  return (0);
}


/*------------------------------------------------------------------*/
/* send a request for the signaling entity                          */
/*------------------------------------------------------------------*/

void sig_req(PLCI   * plci, byte req, byte Id)
{
  if(!plci) return;
  if(plci->adapter->adapter_disabled) return;
  dbug(1,dprintf("sig_req(%x)",req));
  if (req == REMOVE)
    plci->sig_remove_id = plci->Sig.Id;
  if(plci->req_in==plci->req_in_start) {
    plci->req_in +=2;
    plci->RBuffer[plci->req_in++] = 0;
  }
  PUT_WORD(&plci->RBuffer[plci->req_in_start], plci->req_in-plci->req_in_start-2);
  plci->RBuffer[plci->req_in++] = Id;   /* sig/nl flag */
  plci->RBuffer[plci->req_in++] = req;  /* request */
  plci->RBuffer[plci->req_in++] = 0;    /* channel */
  plci->req_in_start = plci->req_in;
}

/*------------------------------------------------------------------*/
/* send a request for the network layer entity                      */
/*------------------------------------------------------------------*/

void nl_req_ncci(PLCI   * plci, byte req, byte ncci)
{
  if(!plci) return;
  if(plci->adapter->adapter_disabled) return;
  dbug(1,dprintf("nl_req %02x %02x %02x", plci->Id, req, ncci));
  if (req == REMOVE)
  {
    plci->nl_remove_id = plci->NL.Id;
    ncci_remove (plci, 0, (byte)(ncci != 0));
    ncci = 0;
  }
  if(plci->req_in==plci->req_in_start) {
    plci->req_in +=2;
    plci->RBuffer[plci->req_in++] = 0;
  }
  PUT_WORD(&plci->RBuffer[plci->req_in_start], plci->req_in-plci->req_in_start-2);
  plci->RBuffer[plci->req_in++] = 1;    /* sig/nl flag */
  plci->RBuffer[plci->req_in++] = req;  /* request */
  plci->RBuffer[plci->req_in++] = plci->adapter->ncci_ch[ncci];   /* channel */
  plci->req_in_start = plci->req_in;
}

void send_req(PLCI   * plci)
{
  ENTITY   * e;
  word l;
/*  word i; */

  if(!plci) return;
  if(plci->adapter->adapter_disabled) return;
  channel_xmit_xon (plci);

        /* if nothing to do, return */
  if(plci->req_in==plci->req_out) return;
  dbug(1,dprintf("send_req(in=%d,out=%d)",plci->req_in,plci->req_out));

  if(plci->nl_req || plci->sig_req) return;

  l = GET_WORD(&plci->RBuffer[plci->req_out]);
  plci->req_out += 2;
  plci->XData[0].P = &plci->RBuffer[plci->req_out];
  plci->req_out += l;
  if(plci->RBuffer[plci->req_out]==1)
  {
    e = &plci->NL;
    plci->req_out++;
    e->Req = plci->nl_req = plci->RBuffer[plci->req_out++];
    e->ReqCh = plci->RBuffer[plci->req_out++];
    if(!(e->Id & 0x1f))
    {
      e->Id = NL_ID;
      plci->RBuffer[plci->req_out-4] = CAI;
      plci->RBuffer[plci->req_out-3] = 1;
      plci->RBuffer[plci->req_out-2] = (plci->Sig.Id==0xff) ? 0 : plci->Sig.Id;
      plci->RBuffer[plci->req_out-1] = 0;
      l+=3;
      plci->nl_global_req = plci->nl_req;
    }
    dbug(1,dprintf("%x:NLREQ(%x:%x:%x)",plci->adapter->Id,e->Id,e->Req,e->ReqCh));
  }
  else
  {
    e = &plci->Sig;
    if(plci->RBuffer[plci->req_out])
      e->Id = plci->RBuffer[plci->req_out];
    plci->req_out++;
    e->Req = plci->sig_req = plci->RBuffer[plci->req_out++];
    e->ReqCh = plci->RBuffer[plci->req_out++];
    if(!(e->Id & 0x1f))
      plci->sig_global_req = plci->sig_req;
    dbug(1,dprintf("%x:SIGREQ(%x:%x:%x)",plci->adapter->Id,e->Id,e->Req,e->ReqCh));
  }
  plci->XData[0].PLength = l;
  e->X = plci->XData;
  plci->adapter->request(e);
  dbug(1,dprintf("send_ok"));
}

void send_data(PLCI   * plci)
{
  DIVA_CAPI_ADAPTER   * a;
  DATA_B3_DESC   * data;
  NCCI   *ncci_ptr;
  word ncci;

  if (!plci->nl_req && plci->ncci_ring_list)
  {
    a = plci->adapter;
    ncci = plci->ncci_ring_list;
    do
    {
      ncci = a->ncci_next[ncci];
      ncci_ptr = &(a->ncci[ncci]);
      if (!(a->ncci_ch[ncci]
         && (a->ch_flow_control[a->ncci_ch[ncci]] & N_OK_FC_PENDING)))
      {
        if (ncci_ptr->data_pending)
        {
          if ((a->ncci_state[ncci] == CONNECTED)
           || (a->ncci_state[ncci] == INC_ACT_PENDING)
           || (plci->send_disc == ncci))
          {
            data = &(ncci_ptr->DBuffer[ncci_ptr->data_out]);
            if ((plci->B2_prot == B2_V120_ASYNC)
             || (plci->B2_prot == B2_V120_ASYNC_V42BIS)
             || (plci->B2_prot == B2_V120_BIT_TRANSPARENT))
            {
              plci->NData[1].P = TransmitBufferGet (plci->appl, data->P);
              plci->NData[1].PLength = data->Length;
              if (data->Flags & 0x10)
                plci->NData[0].P = v120_break_header;
              else
                plci->NData[0].P = v120_default_header;
              plci->NData[0].PLength = 1 ;
              plci->NL.XNum = 2;
              plci->NL.Req = plci->nl_req = (byte)((data->Flags&0x07)<<4 |N_DATA);
            }
            else
            {
              plci->NData[0].P = TransmitBufferGet (plci->appl, data->P);
              plci->NData[0].PLength = data->Length;
              if (data->Flags & 0x10)
                plci->NL.Req = plci->nl_req = (byte)N_UDATA;

              else if ((plci->B3_prot == B3_RTP) && (data->Flags & 0x01))
                plci->NL.Req = plci->nl_req = (byte)N_BDATA;

              else
                plci->NL.Req = plci->nl_req = (byte)((data->Flags&0x07)<<4 |N_DATA);
            }
            plci->NL.X = plci->NData;
            plci->NL.ReqCh = a->ncci_ch[ncci];
            dbug(1,dprintf("%x:DREQ(%x:%x)",a->Id,plci->NL.Id,plci->NL.Req));
            plci->data_sent = TRUE;
            plci->data_sent_ptr = data->P;
            a->request(&plci->NL);
          }
          else {
            cleanup_ncci_data (plci, ncci);
          }
        }
        else if (plci->send_disc == ncci)
        {
          /* dprintf("N_DISC"); */
          plci->NData[0].PLength = 0;
          plci->NL.ReqCh = a->ncci_ch[ncci];
          plci->NL.Req = plci->nl_req = N_DISC;
          a->request(&plci->NL);
          plci->command = _DISCONNECT_B3_R;
          plci->send_disc = 0;
        }
      }
    } while (!plci->nl_req && (ncci != plci->ncci_ring_list));
    plci->ncci_ring_list = ncci;
  }
}

void listen_check(DIVA_CAPI_ADAPTER   * a)
{
  word i,j;
  PLCI   * plci;
  byte activnotifiedcalls = 0;

  dbug(1,dprintf("listen_check(%d,%d)",a->listen_active,a->max_listen));
  if (!remove_started && !a->adapter_disabled)
  {
    for(i=0;i<a->max_plci;i++)
    {
      plci = &(a->plci[i]);
      if(plci->notifiedcall) activnotifiedcalls++;
    }
    dbug(1,dprintf("listen_check(%d)",activnotifiedcalls));

    for(i=a->listen_active; i < ((word)(a->max_listen+activnotifiedcalls)); i++) {
      if((j=get_plci(a))) {
        a->listen_active++;
        plci = &a->plci[j-1];
        plci->State = LISTENING;

        add_p(plci,OAD,"\x01\xfd");

        add_p(plci,KEY,"\x04\x43\x41\x32\x30");

        add_p(plci,CAI,"\x01\xc0");
        add_p(plci,UID,"\x06\x43\x61\x70\x69\x32\x30");
        add_p(plci,LLI,"\x01\xc4");                  /* support Dummy CR FAC + MWI + SpoofNotify */       
        add_p(plci,SHIFT|6,NULL);
        add_p(plci,SIN,"\x02\x00\x00");
        plci->internal_command = LISTEN_SIG_ASSIGN_PEND;     /* do indicate_req if OK  */
        sig_req(plci,ASSIGN,DSIG_ID);
        send_req(plci);
      }
    }
  }
}

/*------------------------------------------------------------------*/
/* functions for all parameters sent in INDs                        */
/*------------------------------------------------------------------*/

void IndParse(PLCI   * plci, word * parms_id, byte   ** parms, byte multiIEsize)
{
  word ploc;            /* points to current location within packet */
  byte w;
  byte wlen;
  byte codeset,lock;
  byte   * in;
  word i;
  word code;
  word mIEindex = 0;
  ploc = 0;
  codeset = 0;
  lock = 0;

  in = plci->Sig.RBuffer->P;
  for(i=0; i<parms_id[0]; i++)   /* multiIE parms_id contains just the 1st */
  {                            /* element but parms array is larger      */
    parms[i] = (byte   *)"";
  }
  for(i=0; i<multiIEsize; i++)
  {
    parms[i] = (byte   *)"";
  }

  while(ploc<plci->Sig.RBuffer->length-1) {

        /* read information element id and length                   */
    w = in[ploc];

    if(w & 0x80) {
/*    w &=0xf0; removed, cannot detect congestion levels */
/*    upper 4 bit masked with w==SHIFT now               */
      wlen = 0;
    }
    else {
      wlen = (byte)(in[ploc+1]+1);
    }
        /* check if length valid (not exceeding end of packet)      */
    if((ploc+wlen) > 270) return ;
    if(lock & 0x80) lock &=0x7f;
    else codeset = lock;

    if((w&0xf0)==SHIFT) {
      codeset = in[ploc];
      if(!(codeset & 0x08)) lock = (byte)(codeset & 7);
      codeset &=7;
      lock |=0x80;
    }
    else {
      if(w==ESC && wlen>=3) code = in[ploc+2] |0x800;
      else code = w;
      code |= (codeset<<8);

      for(i=1; i<parms_id[0]+1 && parms_id[i]!=code; i++);

      if(i<parms_id[0]+1) {
        if(!multiIEsize) { /* with multiIEs use next field index,          */
          mIEindex = i-1;    /* with normal IEs use same index like parms_id */
        }

        parms[mIEindex] = &in[ploc+1];
        dbug(1,dprintf("mIE[%d]=0x%x",*parms[mIEindex],in[ploc]));
        if(parms_id[i]==OAD
        || parms_id[i]==CONN_NR
        || parms_id[i]==CAD) {
          if(in[ploc+2] &0x80) {
            in[ploc+0] = (byte)(in[ploc+1]+1);
            in[ploc+1] = (byte)(in[ploc+2] &0x7f);
            in[ploc+2] = 0x80;
            parms[mIEindex] = &in[ploc];
          }
        }
        mIEindex++;       /* effects multiIEs only */
      }
    }

    ploc +=(wlen+1);
  }
  return ;
}

/*------------------------------------------------------------------*/
/* try to match a cip from received BC and HLC                      */
/*------------------------------------------------------------------*/

byte ie_compare(byte   * ie1, byte * ie2)
{
  word i;
  if(!ie1 || ! ie2) return FALSE;
  if(!ie1[0]) return FALSE;
  for(i=0;i<(word)(ie1[0]+1);i++) if(ie1[i]!=ie2[i]) return FALSE;
  return TRUE;
}

word find_cip(DIVA_CAPI_ADAPTER   * a, byte   * bc, byte   * hlc)
{
  word i;
  word j;

  for(i=9;i && !ie_compare(bc,cip_bc[i][a->u_law]);i--);

  for(j=16;j<29 &&
           (!ie_compare(bc,cip_bc[j][a->u_law]) || !ie_compare(hlc,cip_hlc[j])); j++);
  if(j==29) return i;
  return j;
}


static byte AddInfo(byte   **add_i,
                    byte   **fty_i,
                    byte   *esc_chi,
                    byte *facility)
{
  byte i;
  byte j;
  byte k;
  byte flen;
  byte len=0;
   /* facility is a nested structure */
   /* FTY can be more than once      */

  if(esc_chi[0] && !(esc_chi[esc_chi[0]])&0x7f )
  {
    add_i[0] = (byte   *)"\x02\x02\x00"; /* use neither b nor d channel */
  }

  else
  {
    add_i[0] = (byte   *)"";
  }
  if(!fty_i[0][0])
  {
    add_i[3] = (byte   *)"";
  }
  else
  {    /* facility array found  */
    for(i=0,j=1;i<MAX_MULTI_IE && fty_i[i][0];i++)
    {
      dbug(1,dprintf("AddIFac[%d]",fty_i[i][0]));
      len += fty_i[i][0];
      len += 2;
      flen=fty_i[i][0];
      facility[j++]=0x1c; /* copy fac IE */
      for(k=0;k<=flen;k++,j++)
      {
        facility[j]=fty_i[i][k];
/*      dbug(1,dprintf("%x ",facility[j])); */
      }
    }
    facility[0] = len;
    add_i[3] = facility;
  }
/*  dbug(1,dprintf("FacArrLen=%d ",len)); */
  len = add_i[0][0]+add_i[1][0]+add_i[2][0]+add_i[3][0];
  len += 4;                          /* calculate length of all */
  return(len);
}

/*------------------------------------------------------------------*/
/* voice and codec features                                         */
/*------------------------------------------------------------------*/

void SetVoiceChannel(PLCI   *plci, byte   *chi, DIVA_CAPI_ADAPTER   * a)
{
  byte voice_chi[] = "\x02\x18\x01";
  byte channel;

  channel = chi[chi[0]]&0x3;
  dbug(1,dprintf("ExtDevON(Ch=0x%x)",channel));
  voice_chi[2] = (channel) ? channel : 1;
  add_p(plci,FTY,"\x02\x01\x07");             /* B On, default on 1 */
  add_p(plci,ESC,voice_chi);                  /* Channel */
  sig_req(plci,TEL_CTRL,0);
  send_req(plci);
  if(a->AdvSignalPLCI)
  {
    adv_voice_write_coefs (a->AdvSignalPLCI, ADV_VOICE_WRITE_ACTIVATION);
  }
}

void VoiceChannelOff(PLCI   *plci)
{
  dbug(1,dprintf("ExtDevOFF"));
  add_p(plci,FTY,"\x02\x01\x08");             /* B Off */
  sig_req(plci,TEL_CTRL,0);
  send_req(plci);
  if(plci->adapter->AdvSignalPLCI)
  {
    adv_voice_clear_config (plci->adapter->AdvSignalPLCI);
  }
}


word AdvCodecSupport(DIVA_CAPI_ADAPTER   *a, PLCI   *plci, APPL   *appl, byte hook_listen)
{
  word j;
  PLCI   *splci;

  /* check if hardware supports handset with hook states (adv.codec) */
  /* or if just a on board codec is supported                        */
  /* the advanced codec plci is just for internal use                */

  /* diva Pro with on-board codec:                                   */
  if(a->profile.Global_Options & HANDSET)
  {
    /* new call, but hook states are already signalled */
    if(a->AdvCodecFLAG)
    {
      if(a->AdvSignalAppl!=appl || a->AdvSignalPLCI)
      {
        dbug(1,dprintf("AdvSigPlci=0x%x",a->AdvSignalPLCI));
        return 0x2001; /* codec in use by another application */
      }
      if(plci!=0)
      {
        a->AdvSignalPLCI = plci;
        plci->tel=ADV_VOICE;
      }
      return 0;                      /* adv codec still used */
    }
    if((j=get_plci(a)))
    {
      splci = &a->plci[j-1];
      splci->tel = CODEC_PERMANENT;
      /* hook_listen indicates if a facility_req with handset/hook support */
      /* was sent. Otherwise if just a call on an external device was made */
      /* the codec will be used but the hook info will be discarded (just  */
      /* the external controller is in use                                 */
      if(hook_listen) splci->State = ADVANCED_VOICE_SIG;
      else
      {
        splci->State = ADVANCED_VOICE_NOSIG;
        if(plci)
        {
          plci->spoofed_msg = SPOOFING_REQUIRED;
        }
                                               /* indicate D-ch connect if  */
      }                                        /* codec is connected OK     */
      if(plci!=0)
      {
        a->AdvSignalPLCI = plci;
        plci->tel=ADV_VOICE;
      }
      a->AdvSignalAppl = appl;
      a->AdvCodecFLAG = TRUE;
      a->AdvCodecPLCI = splci;
      add_p(splci,CAI,"\x01\x15");
      add_p(splci,LLI,"\x01\x00");
      add_p(splci,ESC,"\x02\x18\x00");
      add_p(splci,UID,"\x06\x43\x61\x70\x69\x32\x30");
      splci->internal_command = PERM_COD_ASSIGN;
      dbug(1,dprintf("Codec Assign"));
      sig_req(splci,ASSIGN,DSIG_ID);
      send_req(splci);
    }
    else
    {
      return 0x2001; /* wrong state, no more plcis */
    }
  }
  else if(a->profile.Global_Options & ON_BOARD_CODEC)
  {
    if(hook_listen) return 0x300B;               /* Facility not supported */
                                                 /* no hook with SCOM      */
    if(plci!=0) plci->tel = CODEC;
    dbug(1,dprintf("S/SCOM codec"));
    /* first time we use the scom-s codec we must shut down the internal   */
    /* handset application of the card. This can be done by an assign with */
    /* a cai with the 0x80 bit set. Assign return code is 'out of resource'*/
    if(!a->scom_appl_disable){
      if((j=get_plci(a))) {
        splci = &a->plci[j-1];
        add_p(splci,CAI,"\x01\x80");
        add_p(splci,UID,"\x06\x43\x61\x70\x69\x32\x30");
        sig_req(splci,ASSIGN,0xC0);  /* 0xc0 is the TEL_ID */
        send_req(splci);
        a->scom_appl_disable = TRUE;
      }
      else{
        return 0x2001; /* wrong state, no more plcis */
      }
    }
  }
  else return 0x300B;               /* Facility not supported */

  return 0;
}


void CodecIdCheck(DIVA_CAPI_ADAPTER   *a, PLCI   *plci)
{

  dbug(1,dprintf("CodecIdCheck"));

  if(a->AdvSignalPLCI == plci)
  {
    dbug(1,dprintf("PLCI owns codec"));
    VoiceChannelOff(a->AdvCodecPLCI);
    if(a->AdvCodecPLCI->State == ADVANCED_VOICE_NOSIG)
    {
      dbug(1,dprintf("remove temp codec PLCI"));
      plci_remove(a->AdvCodecPLCI);
      a->AdvCodecFLAG  = 0;
      a->AdvCodecPLCI  = NULL;
      a->AdvSignalAppl = NULL;
    }
    a->AdvSignalPLCI = NULL;
  }
}

/* -------------------------------------------------------------------
    Ask for physical address of card on PCI bus
   ------------------------------------------------------------------- */
static void diva_ask_for_xdi_sdram_bar (DIVA_CAPI_ADAPTER  * a,
                                        IDI_SYNC_REQ  * preq) {
  a->sdram_bar = 0;
  if (diva_xdi_extended_features & DIVA_CAPI_XDI_PROVIDES_SDRAM_BAR) {
    ENTITY   * e = (ENTITY   *)preq;

    e->user[0] = a->Id - 1;
    preq->xdi_sdram_bar.info.bar    = 0;
    preq->xdi_sdram_bar.Req         = 0;
    preq->xdi_sdram_bar.Rc           = IDI_SYNC_REQ_XDI_GET_ADAPTER_SDRAM_BAR;

    (*(a->request))(e);

    a->sdram_bar = preq->xdi_sdram_bar.info.bar;
    dbug(3,dprintf("A(%d) SDRAM BAR = %08x", a->Id, a->sdram_bar));
  }
}

/* -------------------------------------------------------------------
     Ask XDI about extended features
   ------------------------------------------------------------------- */
static void diva_get_extended_adapter_features (DIVA_CAPI_ADAPTER  * a) {
  IDI_SYNC_REQ   * preq;
    char buffer[              ((sizeof(preq->xdi_extended_features)+4) > sizeof(ENTITY)) ?                     (sizeof(preq->xdi_extended_features)+4) : sizeof(ENTITY)];

    char features[4];
  preq = (IDI_SYNC_REQ   *)&buffer[0];

  if (!diva_xdi_extended_features) {
    ENTITY   * e = (ENTITY   *)preq;
    diva_xdi_extended_features |= 0x80000000;

    e->user[0] = a->Id - 1;
    preq->xdi_extended_features.Req = 0;
    preq->xdi_extended_features.Rc  = IDI_SYNC_REQ_XDI_GET_EXTENDED_FEATURES;
    preq->xdi_extended_features.info.buffer_length_in_bytes = sizeof(features);
    preq->xdi_extended_features.info.features = &features[0];

    (*(a->request))(e);

    if (features[0] & DIVA_XDI_EXTENDED_FEATURES_VALID) {
      /*
         Check features located in the byte '0'
         */
      if (features[0] & DIVA_XDI_EXTENDED_FEATURE_CMA) {
        diva_xdi_extended_features |= DIVA_CAPI_USE_CMA;
      }
      if (features[0] & DIVA_XDI_EXTENDED_FEATURE_RX_DMA) {
        diva_xdi_extended_features |= DIVA_CAPI_XDI_PROVIDES_RX_DMA;
        dbug(1,dprintf("XDI provides RxDMA"));
      }
      if (features[0] & DIVA_XDI_EXTENDED_FEATURE_SDRAM_BAR) {
        diva_xdi_extended_features |= DIVA_CAPI_XDI_PROVIDES_SDRAM_BAR;
      }
      if (features[0] & DIVA_XDI_EXTENDED_FEATURE_NO_CANCEL_RC) {
        diva_xdi_extended_features |= DIVA_CAPI_XDI_PROVIDES_NO_CANCEL;
        dbug(3,dprintf("XDI provides NO_CANCEL_RC feature"));
      }

    }
  }

  diva_ask_for_xdi_sdram_bar (a, preq);
}

/*------------------------------------------------------------------*/
/* automatic law                                                    */
/*------------------------------------------------------------------*/
/* called from OS specific part after init time to get the Law              */
/* a-law (Euro) and u-law (us,japan) use different BCs in the Setup message */
void AutomaticLaw(DIVA_CAPI_ADAPTER   *a)
{
  word j;
  PLCI   *splci;

  if(a->automatic_law) {
    return;
  }
  if((j=get_plci(a))) {
    diva_get_extended_adapter_features (a);
    splci = &a->plci[j-1];
    a->automatic_lawPLCI = splci;
    a->automatic_law = 1;
    add_p(splci,CAI,"\x01\x80");
    add_p(splci,UID,"\x06\x43\x61\x70\x69\x32\x30");
    splci->internal_command = USELAW_REQ;
    splci->command = 0;
    splci->number = 0;
    sig_req(splci,ASSIGN,DSIG_ID);
    send_req(splci);
  }
}

/* called from OS specific part if an application sends an Capi20Release */
word CapiRelease(word Id)
{
  word i, j, appls_found;
  PLCI   *plci;
  APPL   *this;
  DIVA_CAPI_ADAPTER   *a;

  if (!Id)
  {
    dbug(0,dprintf("A: CapiRelease(Id==0)"));
    return (_WRONG_APPL_ID);
  }

  this = &application[Id-1];               /* get application pointer */

  for(i=0,appls_found=0; i<max_appl; i++)
  {
    if(application[i].Id)       /* an application has been found        */
    {
      appls_found++;
    }
  }

  for(i=0; i<max_adapter; i++)             /* scan all adapters...    */
  {
    a = &adapter[i];
    if (a->request)
    {
      a->Info_Mask[Id-1] = 0;
      a->CIP_Mask[Id-1] = 0;
      a->Notification_Mask[Id-1] = 0;
      a->codec_listen[Id-1] = NULL;
      a->requested_options_table[Id-1] = 0;
      for(j=0; j<a->max_plci; j++)           /* and all PLCIs connected */
      {                                      /* with this application   */
        plci = &a->plci[j];
        if(plci->Id)                         /* if plci owns no application */
        {                                    /* it may be not jet connected */
          if(plci->State==INC_CON_PENDING
          || plci->State==INC_CON_ALERT)
          {
            if(test_c_ind_mask_bit (plci, (word)(Id-1)))
            {
              clear_c_ind_mask_bit (plci, (word)(Id-1));
              if(c_ind_mask_empty (plci))
              {
                sig_req(plci,HANGUP,0);
                send_req(plci);
                plci->State = OUTG_DIS_PENDING;
              }
            }
          }
          if(test_c_ind_mask_bit (plci, (word)(Id-1)))
          {
            clear_c_ind_mask_bit (plci, (word)(Id-1));
            if(c_ind_mask_empty (plci))
            {
              if(!plci->appl)
              {
                plci_remove(plci);
                plci->State = IDLE;
              }
            }
          }
          if(plci->appl==this)
          {
            plci->appl = NULL;
            plci_remove(plci);
            plci->State = IDLE;
          }
        }
      }
      listen_check(a);

      if(a->flag_dynamic_l1_down)
      {
        if(appls_found==1)            /* last application does a capi release */
        {
          if((j=get_plci(a)))
          {
            plci = &a->plci[j-1];
            plci->command = 0;
            add_p(plci,OAD,"\x01\xfd");
            add_p(plci,CAI,"\x01\x80");
            add_p(plci,UID,"\x06\x43\x61\x70\x69\x32\x30");
            add_p(plci,SHIFT|6,NULL);
            add_p(plci,SIN,"\x02\x00\x00");
            plci->internal_command = REM_L1_SIG_ASSIGN_PEND;
            sig_req(plci,ASSIGN,DSIG_ID);
            add_p(plci,FTY,"\x02\xff\x06"); /* l1 down */
            sig_req(plci,SIG_CTRL,0);
            send_req(plci);
          }
        }
      }
      if(a->AdvSignalAppl==this)
      {
        this->NullCREnable = FALSE;
        if (a->AdvCodecPLCI)
        {
          plci_remove(a->AdvCodecPLCI);
          a->AdvCodecPLCI->tel = 0;
          a->AdvCodecPLCI->adv_nl = 0;
        }
        a->AdvSignalAppl = NULL;
        a->AdvSignalPLCI = NULL;
        a->AdvCodecFLAG = 0;
        a->AdvCodecPLCI = NULL;
      }
    }
  }

  this->Id = 0;

  return GOOD;
}

static word plci_remove_check(PLCI   *plci)
{
  if(!plci) return TRUE;
  if(!plci->NL.Id && c_ind_mask_empty (plci))
  {
    if(plci->Sig.Id == 0xff)
      plci->Sig.Id = 0;
    if(!plci->Sig.Id)
    {
      dbug(1,dprintf("plci_remove_complete(%x)",plci->Id));
      dbug(1,dprintf("tel=0x%x,Sig=0x%x",plci->tel,plci->Sig.Id));
      if (plci->Id)
      {
        CodecIdCheck(plci->adapter, plci);
        clear_b1_config (plci);
        ncci_remove (plci, 0, FALSE);
        plci_free_msg_in_queue (plci);
        channel_flow_control_remove (plci);
        plci->Id = 0;
        plci->State = IDLE;
        plci->channels = 0;
        plci->appl = NULL;
        plci->notifiedcall = 0;
      }
      listen_check(plci->adapter);
      return TRUE;
    }
  }
  return FALSE;
}


/*------------------------------------------------------------------*/

static byte plci_nl_busy (PLCI   *plci)
{
  /* only applicable for non-multiplexed protocols */
  return (plci->nl_req
    || (plci->ncci_ring_list
     && plci->adapter->ncci_ch[plci->ncci_ring_list]
     && (plci->adapter->ch_flow_control[plci->adapter->ncci_ch[plci->ncci_ring_list]] & N_OK_FC_PENDING)));
}


/*------------------------------------------------------------------*/
/* DTMF facilities                                                  */
/*------------------------------------------------------------------*/


static struct
{
  byte send_mask;
  byte listen_mask;
  byte character;
  byte code;
} dtmf_digit_map[] =
{
  { 0x01, 0x01, 0x23, DTMF_DIGIT_TONE_CODE_HASHMARK },
  { 0x01, 0x01, 0x2a, DTMF_DIGIT_TONE_CODE_STAR },
  { 0x01, 0x01, 0x30, DTMF_DIGIT_TONE_CODE_0 },
  { 0x01, 0x01, 0x31, DTMF_DIGIT_TONE_CODE_1 },
  { 0x01, 0x01, 0x32, DTMF_DIGIT_TONE_CODE_2 },
  { 0x01, 0x01, 0x33, DTMF_DIGIT_TONE_CODE_3 },
  { 0x01, 0x01, 0x34, DTMF_DIGIT_TONE_CODE_4 },
  { 0x01, 0x01, 0x35, DTMF_DIGIT_TONE_CODE_5 },
  { 0x01, 0x01, 0x36, DTMF_DIGIT_TONE_CODE_6 },
  { 0x01, 0x01, 0x37, DTMF_DIGIT_TONE_CODE_7 },
  { 0x01, 0x01, 0x38, DTMF_DIGIT_TONE_CODE_8 },
  { 0x01, 0x01, 0x39, DTMF_DIGIT_TONE_CODE_9 },
  { 0x01, 0x01, 0x41, DTMF_DIGIT_TONE_CODE_A },
  { 0x01, 0x01, 0x42, DTMF_DIGIT_TONE_CODE_B },
  { 0x01, 0x01, 0x43, DTMF_DIGIT_TONE_CODE_C },
  { 0x01, 0x01, 0x44, DTMF_DIGIT_TONE_CODE_D },
  { 0x01, 0x00, 0x61, DTMF_DIGIT_TONE_CODE_A },
  { 0x01, 0x00, 0x62, DTMF_DIGIT_TONE_CODE_B },
  { 0x01, 0x00, 0x63, DTMF_DIGIT_TONE_CODE_C },
  { 0x01, 0x00, 0x64, DTMF_DIGIT_TONE_CODE_D },

  { 0x04, 0x04, 0x80, DTMF_SIGNAL_NO_TONE },
  { 0x00, 0x04, 0x81, DTMF_SIGNAL_UNIDENTIFIED_TONE },
  { 0x04, 0x04, 0x82, DTMF_SIGNAL_DIAL_TONE },
  { 0x04, 0x04, 0x83, DTMF_SIGNAL_PABX_INTERNAL_DIAL_TONE },
  { 0x04, 0x04, 0x84, DTMF_SIGNAL_SPECIAL_DIAL_TONE },
  { 0x04, 0x04, 0x85, DTMF_SIGNAL_SECOND_DIAL_TONE },
  { 0x04, 0x04, 0x86, DTMF_SIGNAL_RINGING_TONE },
  { 0x04, 0x04, 0x87, DTMF_SIGNAL_SPECIAL_RINGING_TONE },
  { 0x04, 0x04, 0x88, DTMF_SIGNAL_BUSY_TONE },
  { 0x04, 0x04, 0x89, DTMF_SIGNAL_CONGESTION_TONE },
  { 0x04, 0x04, 0x8a, DTMF_SIGNAL_SPECIAL_INFORMATION_TONE },
  { 0x04, 0x04, 0x8b, DTMF_SIGNAL_COMFORT_TONE },
  { 0x04, 0x04, 0x8c, DTMF_SIGNAL_HOLD_TONE },
  { 0x04, 0x04, 0x8d, DTMF_SIGNAL_RECORD_TONE },
  { 0x04, 0x04, 0x8e, DTMF_SIGNAL_CALLER_WAITING_TONE },
  { 0x04, 0x04, 0x8f, DTMF_SIGNAL_CALL_WAITING_TONE },
  { 0x04, 0x04, 0x90, DTMF_SIGNAL_PAY_TONE },
  { 0x04, 0x04, 0x91, DTMF_SIGNAL_POSITIVE_INDICATION_TONE },
  { 0x04, 0x04, 0x92, DTMF_SIGNAL_NEGATIVE_INDICATION_TONE },
  { 0x04, 0x04, 0x93, DTMF_SIGNAL_WARNING_TONE },
  { 0x04, 0x04, 0x94, DTMF_SIGNAL_INTRUSION_TONE },
  { 0x04, 0x04, 0x95, DTMF_SIGNAL_CALLING_CARD_SERVICE_TONE },
  { 0x04, 0x04, 0x96, DTMF_SIGNAL_PAYPHONE_RECOGNITION_TONE },
  { 0x04, 0x04, 0x97, DTMF_SIGNAL_CPE_ALERTING_SIGNAL },
  { 0x04, 0x04, 0x98, DTMF_SIGNAL_OFF_HOOK_WARNING_TONE },
  { 0x04, 0x04, 0xbf, DTMF_SIGNAL_INTERCEPT_TONE },
  { 0x04, 0x04, 0xc0, DTMF_SIGNAL_MODEM_CALLING_TONE },
  { 0x04, 0x04, 0xc1, DTMF_SIGNAL_FAX_CALLING_TONE },
  { 0x04, 0x04, 0xc2, DTMF_SIGNAL_ANSWER_TONE },
  { 0x04, 0x04, 0xc3, DTMF_SIGNAL_REVERSED_ANSWER_TONE },
  { 0x04, 0x04, 0xc4, DTMF_SIGNAL_ANSAM_TONE },
  { 0x04, 0x04, 0xc5, DTMF_SIGNAL_REVERSED_ANSAM_TONE },
  { 0x04, 0x04, 0xc6, DTMF_SIGNAL_BELL103_ANSWER_TONE },
  { 0x04, 0x04, 0xc7, DTMF_SIGNAL_FAX_FLAGS },
  { 0x04, 0x04, 0xc8, DTMF_SIGNAL_G2_FAX_GROUP_ID },
  { 0x00, 0x04, 0xc9, DTMF_SIGNAL_HUMAN_SPEECH },
  { 0x04, 0x04, 0xca, DTMF_SIGNAL_ANSWERING_MACHINE_390 },
  { 0x02, 0x02, 0xf1, DTMF_MF_DIGIT_TONE_CODE_1 },
  { 0x02, 0x02, 0xf2, DTMF_MF_DIGIT_TONE_CODE_2 },
  { 0x02, 0x02, 0xf3, DTMF_MF_DIGIT_TONE_CODE_3 },
  { 0x02, 0x02, 0xf4, DTMF_MF_DIGIT_TONE_CODE_4 },
  { 0x02, 0x02, 0xf5, DTMF_MF_DIGIT_TONE_CODE_5 },
  { 0x02, 0x02, 0xf6, DTMF_MF_DIGIT_TONE_CODE_6 },
  { 0x02, 0x02, 0xf7, DTMF_MF_DIGIT_TONE_CODE_7 },
  { 0x02, 0x02, 0xf8, DTMF_MF_DIGIT_TONE_CODE_8 },
  { 0x02, 0x02, 0xf9, DTMF_MF_DIGIT_TONE_CODE_9 },
  { 0x02, 0x02, 0xfa, DTMF_MF_DIGIT_TONE_CODE_0 },
  { 0x02, 0x02, 0xfb, DTMF_MF_DIGIT_TONE_CODE_K1 },
  { 0x02, 0x02, 0xfc, DTMF_MF_DIGIT_TONE_CODE_K2 },
  { 0x02, 0x02, 0xfd, DTMF_MF_DIGIT_TONE_CODE_KP },
  { 0x02, 0x02, 0xfe, DTMF_MF_DIGIT_TONE_CODE_S1 },
  { 0x02, 0x02, 0xff, DTMF_MF_DIGIT_TONE_CODE_ST },

};

#define DTMF_DIGIT_MAP_ENTRIES (sizeof(dtmf_digit_map) / sizeof(dtmf_digit_map[0]))


static void dtmf_enable_receiver (PLCI   *plci, byte enable_mask)
{
  word min_digit_duration, min_gap_duration;

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_enable_receiver %02x",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__, enable_mask));

  if (enable_mask != 0)
  {
    min_digit_duration = (plci->dtmf_rec_pulse_ms == 0) ? 40 : plci->dtmf_rec_pulse_ms;
    min_gap_duration = (plci->dtmf_rec_pause_ms == 0) ? 40 : plci->dtmf_rec_pause_ms;
    plci->internal_req_buffer[0] = DTMF_UDATA_REQUEST_ENABLE_RECEIVER;
    PUT_WORD (&plci->internal_req_buffer[1], min_digit_duration);
    PUT_WORD (&plci->internal_req_buffer[3], min_gap_duration);
    plci->NData[0].PLength = 5;

    PUT_WORD (&plci->internal_req_buffer[5], INTERNAL_IND_BUFFER_SIZE);
    plci->NData[0].PLength += 2;
    capidtmf_recv_enable (&(plci->capidtmf_state), min_digit_duration, min_gap_duration);

  }
  else
  {
    plci->internal_req_buffer[0] = DTMF_UDATA_REQUEST_DISABLE_RECEIVER;
    plci->NData[0].PLength = 1;

    capidtmf_recv_disable (&(plci->capidtmf_state));

  }
  plci->NData[0].P = plci->internal_req_buffer;
  plci->NL.X = plci->NData;
  plci->NL.ReqCh = 0;
  plci->NL.Req = plci->nl_req = (byte) N_UDATA;
  plci->adapter->request (&plci->NL);
}


static void dtmf_send_digits (PLCI   *plci, byte   *digit_buffer, word digit_count)
{
  word w, i;

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_send_digits %d",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__, digit_count));

  plci->internal_req_buffer[0] = DTMF_UDATA_REQUEST_SEND_DIGITS;
  w = (plci->dtmf_send_pulse_ms == 0) ? 40 : plci->dtmf_send_pulse_ms;
  PUT_WORD (&plci->internal_req_buffer[1], w);
  w = (plci->dtmf_send_pause_ms == 0) ? 40 : plci->dtmf_send_pause_ms;
  PUT_WORD (&plci->internal_req_buffer[3], w);
  for (i = 0; i < digit_count; i++)
  {
    w = 0;
    while ((w < DTMF_DIGIT_MAP_ENTRIES)
      && (digit_buffer[i] != dtmf_digit_map[w].character))
    {
      w++;
    }
    plci->internal_req_buffer[5+i] = (w < DTMF_DIGIT_MAP_ENTRIES) ?
      dtmf_digit_map[w].code : DTMF_DIGIT_TONE_CODE_STAR;
  }
  plci->NData[0].PLength = 5 + digit_count;
  plci->NData[0].P = plci->internal_req_buffer;
  plci->NL.X = plci->NData;
  plci->NL.ReqCh = 0;
  plci->NL.Req = plci->nl_req = (byte) N_UDATA;
  plci->adapter->request (&plci->NL);
}


static void dtmf_rec_clear_config (PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_rec_clear_config",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  plci->dtmf_rec_active = 0;
  plci->dtmf_rec_pulse_ms = 0;
  plci->dtmf_rec_pause_ms = 0;

  capidtmf_init (&(plci->capidtmf_state), plci->adapter->u_law);

}


static void dtmf_send_clear_config (PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_send_clear_config",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  plci->dtmf_send_requests = 0;
  plci->dtmf_send_pulse_ms = 0;
  plci->dtmf_send_pause_ms = 0;
}


static void dtmf_prepare_switch (dword Id, PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_prepare_switch",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  while (plci->dtmf_send_requests != 0)
    dtmf_confirmation (Id, plci);
}


static word dtmf_save_config (dword Id, PLCI   *plci, byte Rc)
{

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_save_config %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  return (GOOD);
}


static word dtmf_restore_config (dword Id, PLCI   *plci, byte Rc)
{
  word Info;

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_restore_config %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  Info = GOOD;
  if (plci->B1_facilities & B1_FACILITY_DTMFR)
  {
    switch (plci->adjust_b_state)
    {
    case ADJUST_B_RESTORE_DTMF_1:
      plci->internal_command = plci->adjust_b_command;
      if (plci_nl_busy (plci))
      {
        plci->adjust_b_state = ADJUST_B_RESTORE_DTMF_1;
        break;
      }
      dtmf_enable_receiver (plci, plci->dtmf_rec_active);
      plci->adjust_b_state = ADJUST_B_RESTORE_DTMF_2;
      break;
    case ADJUST_B_RESTORE_DTMF_2:
      if ((Rc != OK) && (Rc != OK_FC))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Reenable DTMF receiver failed %02x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
        Info = _WRONG_STATE;
        break;
      }
      break;
    }
  }
  return (Info);
}


static void dtmf_command (dword Id, PLCI   *plci, byte Rc)
{
  word internal_command, Info;
  byte mask;
    byte result[4];

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_command %02x %04x %04x %d %d %d %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command,
    plci->dtmf_cmd, plci->dtmf_rec_pulse_ms, plci->dtmf_rec_pause_ms,
    plci->dtmf_send_pulse_ms, plci->dtmf_send_pause_ms));

  Info = GOOD;
  result[0] = 2;
  PUT_WORD (&result[1], DTMF_SUCCESS);
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  mask = 0x01;
  switch (plci->dtmf_cmd)
  {

  case DTMF_LISTEN_TONE_START:
    mask <<= 1;
  case DTMF_LISTEN_MF_START:
    mask <<= 1;

  case DTMF_LISTEN_START:
    switch (internal_command)
    {
    default:
      adjust_b1_resource (Id, plci, NULL, (word)(plci->B1_facilities |
        B1_FACILITY_DTMFR), DTMF_COMMAND_1);
    case DTMF_COMMAND_1:
      if (adjust_b_process (Id, plci, Rc) != GOOD)
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Load DTMF failed",
          UnMapId (Id), (char   *)(FILE_), __LINE__));
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
      if (plci->internal_command)
        return;
    case DTMF_COMMAND_2:
      if (plci_nl_busy (plci))
      {
        plci->internal_command = DTMF_COMMAND_2;
        return;
      }
      plci->internal_command = DTMF_COMMAND_3;
      dtmf_enable_receiver (plci, (byte)(plci->dtmf_rec_active | mask));
      return;
    case DTMF_COMMAND_3:
      if ((Rc != OK) && (Rc != OK_FC))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Enable DTMF receiver failed %02x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }

      plci->tone_last_indication_code = DTMF_SIGNAL_NO_TONE;

      plci->dtmf_rec_active |= mask;
      break;
    }
    break;


  case DTMF_LISTEN_TONE_STOP:
    mask <<= 1;
  case DTMF_LISTEN_MF_STOP:
    mask <<= 1;

  case DTMF_LISTEN_STOP:
    switch (internal_command)
    {
    default:
      plci->dtmf_rec_active &= ~mask;
      if (plci->dtmf_rec_active)
        break;
/*
    case DTMF_COMMAND_1:
      if (plci->dtmf_rec_active)
      {
        if (plci_nl_busy (plci))
        {
          plci->internal_command = DTMF_COMMAND_1;
          return;
        }
        plci->dtmf_rec_active &= ~mask;
        plci->internal_command = DTMF_COMMAND_2;
        dtmf_enable_receiver (plci, FALSE);
        return;
      }
      Rc = OK;
    case DTMF_COMMAND_2:
      if ((Rc != OK) && (Rc != OK_FC))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Disable DTMF receiver failed %02x",
          UnMapId (Id), (char far *)(FILE_), __LINE__, Rc));
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
*/
      adjust_b1_resource (Id, plci, NULL, (word)(plci->B1_facilities &
        ~(B1_FACILITY_DTMFX | B1_FACILITY_DTMFR)), DTMF_COMMAND_3);
    case DTMF_COMMAND_3:
      if (adjust_b_process (Id, plci, Rc) != GOOD)
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Unload DTMF failed",
          UnMapId (Id), (char   *)(FILE_), __LINE__));
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
      if (plci->internal_command)
        return;
      break;
    }
    break;


  case DTMF_SEND_TONE:
    mask <<= 1;
  case DTMF_SEND_MF:
    mask <<= 1;

  case DTMF_DIGITS_SEND:
    switch (internal_command)
    {
    default:
      adjust_b1_resource (Id, plci, NULL, (word)(plci->B1_facilities |
        ((plci->dtmf_parameter_length != 0) ? B1_FACILITY_DTMFX | B1_FACILITY_DTMFR : B1_FACILITY_DTMFX)),
        DTMF_COMMAND_1);
    case DTMF_COMMAND_1:
      if (adjust_b_process (Id, plci, Rc) != GOOD)
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Load DTMF failed",
          UnMapId (Id), (char   *)(FILE_), __LINE__));
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
      if (plci->internal_command)
        return;
    case DTMF_COMMAND_2:
      if (plci_nl_busy (plci))
      {
        plci->internal_command = DTMF_COMMAND_2;
        return;
      }
      plci->dtmf_msg_number_queue[(plci->dtmf_send_requests)++] = plci->number;
      plci->internal_command = DTMF_COMMAND_3;
      dtmf_send_digits (plci, &plci->saved_msg.parms[3].info[1], plci->saved_msg.parms[3].length);
      return;
    case DTMF_COMMAND_3:
      if ((Rc != OK) && (Rc != OK_FC))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Send DTMF digits failed %02x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
        if (plci->dtmf_send_requests != 0)
          (plci->dtmf_send_requests)--;
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
      return;
    }
    break;
  }
  sendf (plci->appl, _FACILITY_R | CONFIRM, Id & 0xffffL, plci->number,
    "wws", Info, SELECTOR_DTMF, result);
}


static byte dtmf_request (dword Id, word Number, DIVA_CAPI_ADAPTER   *a, PLCI   *plci, APPL   *appl, API_PARSE *msg)
{
  word Info;
  word i, j;
  byte mask;
    API_PARSE dtmf_parms[5];
    byte result[40];

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_request",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  Info = GOOD;
  result[0] = 2;
  PUT_WORD (&result[1], DTMF_SUCCESS);
  if (!(a->profile.Global_Options & GL_DTMF_SUPPORTED))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: Facility not supported",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    Info = _FACILITY_NOT_SUPPORTED;
  }
  else if (api_parse (&msg[1].info[1], msg[1].length, "w", dtmf_parms))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    Info = _WRONG_MESSAGE_FORMAT;
  }

  else if ((GET_WORD (dtmf_parms[0].info) == DTMF_GET_SUPPORTED_DETECT_CODES)
    || (GET_WORD (dtmf_parms[0].info) == DTMF_GET_SUPPORTED_SEND_CODES))
  {
    if (!((a->requested_options_table[appl->Id-1])
        & (1L << PRIVATE_DTMF_TONE)))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: DTMF unknown request %04x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, GET_WORD (dtmf_parms[0].info)));
      PUT_WORD (&result[1], DTMF_UNKNOWN_REQUEST);
    }
    else
    {
      for (i = 0; i < 32; i++)
        result[4 + i] = 0;
      if (GET_WORD (dtmf_parms[0].info) == DTMF_GET_SUPPORTED_DETECT_CODES)
      {
        for (i = 0; i < DTMF_DIGIT_MAP_ENTRIES; i++)
        {
          if (dtmf_digit_map[i].listen_mask != 0)
            result[4 + (dtmf_digit_map[i].character >> 3)] |= (1 << (dtmf_digit_map[i].character & 0x7));
        }
      }
      else
      {
        for (i = 0; i < DTMF_DIGIT_MAP_ENTRIES; i++)
        {
          if (dtmf_digit_map[i].send_mask != 0)
            result[4 + (dtmf_digit_map[i].character >> 3)] |= (1 << (dtmf_digit_map[i].character & 0x7));
        }
      }
      result[0] = 3 + 32;
      result[3] = 32;
    }
  }

  else if (plci == NULL)
  {
    dbug (1, dprintf ("[%06lx] %s,%d: Wrong PLCI",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    Info = _WRONG_IDENTIFIER;
  }
  else
  {
    if (!plci->State
     || !plci->NL.Id || plci->nl_remove_id)
    {
      dbug (1, dprintf ("[%06lx] %s,%d: Wrong state",
        UnMapId (Id), (char   *)(FILE_), __LINE__));
      Info = _WRONG_STATE;
    }
    else
    {
      plci->command = 0;
      plci->dtmf_cmd = GET_WORD (dtmf_parms[0].info);
      mask = 0x01;
      switch (plci->dtmf_cmd)
      {

      case DTMF_LISTEN_TONE_START:
      case DTMF_LISTEN_TONE_STOP:
        mask <<= 1;
      case DTMF_LISTEN_MF_START:
      case DTMF_LISTEN_MF_STOP:
        mask <<= 1;
        if (!((plci->requested_options_conn | plci->requested_options | plci->adapter->requested_options_table[appl->Id-1])
          & (1L << PRIVATE_DTMF_TONE)))
        {
          dbug (1, dprintf ("[%06lx] %s,%d: DTMF unknown request %04x",
            UnMapId (Id), (char   *)(FILE_), __LINE__, GET_WORD (dtmf_parms[0].info)));
          PUT_WORD (&result[1], DTMF_UNKNOWN_REQUEST);
          break;
        }

      case DTMF_LISTEN_START:
      case DTMF_LISTEN_STOP:
        if (!(a->manufacturer_features & MANUFACTURER_FEATURE_HARDDTMF)
         && !(a->manufacturer_features & MANUFACTURER_FEATURE_SOFTDTMF_RECEIVE))
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Facility not supported",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _FACILITY_NOT_SUPPORTED;
          break;
        }
        if (mask & DTMF_LISTEN_ACTIVE_FLAG)
        {
          if (api_parse (&msg[1].info[1], msg[1].length, "wwws", dtmf_parms))
          {
            plci->dtmf_rec_pulse_ms = 0;
            plci->dtmf_rec_pause_ms = 0;
          }
          else
          {
            plci->dtmf_rec_pulse_ms = GET_WORD (dtmf_parms[1].info);
            plci->dtmf_rec_pause_ms = GET_WORD (dtmf_parms[2].info);
          }
        }
        start_internal_command (Id, plci, dtmf_command);
        return (FALSE);


      case DTMF_SEND_TONE:
        mask <<= 1;
      case DTMF_SEND_MF:
        mask <<= 1;
        if (!((plci->requested_options_conn | plci->requested_options | plci->adapter->requested_options_table[appl->Id-1])
          & (1L << PRIVATE_DTMF_TONE)))
        {
          dbug (1, dprintf ("[%06lx] %s,%d: DTMF unknown request %04x",
            UnMapId (Id), (char   *)(FILE_), __LINE__, GET_WORD (dtmf_parms[0].info)));
          PUT_WORD (&result[1], DTMF_UNKNOWN_REQUEST);
          break;
        }

      case DTMF_DIGITS_SEND:
        if (api_parse (&msg[1].info[1], msg[1].length, "wwws", dtmf_parms))
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _WRONG_MESSAGE_FORMAT;
          break;
        }
        if (mask & DTMF_LISTEN_ACTIVE_FLAG)
        {
          plci->dtmf_send_pulse_ms = GET_WORD (dtmf_parms[1].info);
          plci->dtmf_send_pause_ms = GET_WORD (dtmf_parms[2].info);
        }
        i = 0;
        j = 0;
        while ((i < dtmf_parms[3].length) && (j < DTMF_DIGIT_MAP_ENTRIES))
        {
          j = 0;
          while ((j < DTMF_DIGIT_MAP_ENTRIES)
            && ((dtmf_parms[3].info[i+1] != dtmf_digit_map[j].character)
             || ((dtmf_digit_map[j].send_mask & mask) == 0)))
          {
            j++;
          }
          i++;
        }
        if (j == DTMF_DIGIT_MAP_ENTRIES)
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Incorrect DTMF digit %02x",
            UnMapId (Id), (char   *)(FILE_), __LINE__, dtmf_parms[3].info[i]));
          PUT_WORD (&result[1], DTMF_INCORRECT_DIGIT);
          break;
        }
        if (plci->dtmf_send_requests >=
          sizeof(plci->dtmf_msg_number_queue) / sizeof(plci->dtmf_msg_number_queue[0]))
        {
          dbug (1, dprintf ("[%06lx] %s,%d: DTMF request overrun",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _WRONG_STATE;
          break;
        }
        api_save_msg (dtmf_parms, "wwws", &plci->saved_msg);
        start_internal_command (Id, plci, dtmf_command);
        return (FALSE);

      default:
        dbug (1, dprintf ("[%06lx] %s,%d: DTMF unknown request %04x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, plci->dtmf_cmd));
        PUT_WORD (&result[1], DTMF_UNKNOWN_REQUEST);
      }
    }
  }
  sendf (appl, _FACILITY_R | CONFIRM, Id & 0xffffL, Number,
    "wws", Info, SELECTOR_DTMF, result);
  return (FALSE);
}


static void dtmf_confirmation (dword Id, PLCI   *plci)
{
  word Info;
  word i;
    byte result[4];

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_confirmation",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  Info = GOOD;
  result[0] = 2;
  PUT_WORD (&result[1], DTMF_SUCCESS);
  if (plci->dtmf_send_requests != 0)
  {
    sendf (plci->appl, _FACILITY_R | CONFIRM, Id & 0xffffL, plci->dtmf_msg_number_queue[0],
      "wws", GOOD, SELECTOR_DTMF, result);
    (plci->dtmf_send_requests)--;
    for (i = 0; i < plci->dtmf_send_requests; i++)
      plci->dtmf_msg_number_queue[i] = plci->dtmf_msg_number_queue[i+1];      
  }
}


static void dtmf_indication (dword Id, PLCI   *plci, byte   *msg, word length)
{
  word i, j, n;

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_indication",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  n = 0;
  for (i = 1; i < length; i++)
  {
    j = 0;
    while ((j < DTMF_DIGIT_MAP_ENTRIES)
      && ((msg[i] != dtmf_digit_map[j].code)
       || ((dtmf_digit_map[j].listen_mask & plci->dtmf_rec_active) == 0)))
    {
      j++;
    }
    if (j < DTMF_DIGIT_MAP_ENTRIES)
    {

      if ((dtmf_digit_map[j].listen_mask & DTMF_TONE_LISTEN_ACTIVE_FLAG)
       && (plci->tone_last_indication_code == DTMF_SIGNAL_NO_TONE)
       && (dtmf_digit_map[j].character != DTMF_SIGNAL_UNIDENTIFIED_TONE))
      {
        if (n + 1 == i)
        {
          for (i = length; i > n + 1; i--)
            msg[i] = msg[i - 1];
          length++;
          i++;
        }
        msg[++n] = DTMF_SIGNAL_UNIDENTIFIED_TONE;
      }
      plci->tone_last_indication_code = dtmf_digit_map[j].character;

      msg[++n] = dtmf_digit_map[j].character;
    }
  }
  if (n != 0)
  {
    msg[0] = (byte) n;
    sendf (plci->appl, _FACILITY_I, Id & 0xffffL, 0, "wS", SELECTOR_DTMF, msg);
  }
}


/*------------------------------------------------------------------*/
/* DTMF parameters                                                  */
/*------------------------------------------------------------------*/

static void dtmf_parameter_write (PLCI   *plci)
{
  word i;
    byte parameter_buffer[DTMF_PARAMETER_BUFFER_SIZE + 2];

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_parameter_write",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  parameter_buffer[0] = plci->dtmf_parameter_length + 1;
  parameter_buffer[1] = DSP_CTRL_SET_DTMF_PARAMETERS;
  for (i = 0; i < plci->dtmf_parameter_length; i++)
    parameter_buffer[2+i] = plci->dtmf_parameter_buffer[i];
  add_p (plci, FTY, parameter_buffer);
  sig_req (plci, TEL_CTRL, 0);
  send_req (plci);
}


static void dtmf_parameter_clear_config (PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_parameter_clear_config",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  plci->dtmf_parameter_length = 0;
}


static void dtmf_parameter_prepare_switch (dword Id, PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_parameter_prepare_switch",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

}


static word dtmf_parameter_save_config (dword Id, PLCI   *plci, byte Rc)
{

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_parameter_save_config %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  return (GOOD);
}


static word dtmf_parameter_restore_config (dword Id, PLCI   *plci, byte Rc)
{
  word Info;

  dbug (1, dprintf ("[%06lx] %s,%d: dtmf_parameter_restore_config %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  Info = GOOD;
  if ((plci->B1_facilities & B1_FACILITY_DTMFR)
   && (plci->dtmf_parameter_length != 0))
  {
    switch (plci->adjust_b_state)
    {
    case ADJUST_B_RESTORE_DTMF_PARAMETER_1:
      plci->internal_command = plci->adjust_b_command;
      if (plci->sig_req)
      {
        plci->adjust_b_state = ADJUST_B_RESTORE_DTMF_PARAMETER_1;
        break;
      }
      dtmf_parameter_write (plci);
      plci->adjust_b_state = ADJUST_B_RESTORE_DTMF_PARAMETER_2;
      break;
    case ADJUST_B_RESTORE_DTMF_PARAMETER_2:
      if ((Rc != OK) && (Rc != OK_FC))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Restore DTMF parameters failed %02x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
        Info = _WRONG_STATE;
        break;
      }
      break;
    }
  }
  return (Info);
}


/*------------------------------------------------------------------*/
/* Line interconnect facilities                                     */
/*------------------------------------------------------------------*/


LI_CONFIG   *li_config_table;
word li_total_channels;


/*------------------------------------------------------------------*/
/* translate a CHI information element to a channel number          */
/* returns 0xff - any channel                                       */
/*         0xfe - chi wrong coding                                  */
/*         0xfd - D-channel                                         */
/*         0x00 - no channel                                        */
/*         else channel number / PRI: timeslot                      */
/* if channels is provided we accept more than one channel.         */
/*------------------------------------------------------------------*/

static byte chi_to_channel (byte   *chi, dword *pchannelmap)
{
  int p;
  int i;
  dword map;
  byte excl;
  byte ofs;
  byte ch;

  if (pchannelmap) *pchannelmap = 0;
  if(!chi[0]) return 0xff;
  excl = 0;

  if(chi[1] & 0x20) {
    if(chi[0]==1 && chi[1]==0xac) return 0xfd; /* exclusive d-channel */
    for(i=1; i<chi[0] && !(chi[i] &0x80); i++);
    if(i==chi[0] || !(chi[i] &0x80)) return 0xfe;
    if((chi[1] |0xc8)!=0xe9) return 0xfe;
    if(chi[1] &0x08) excl = 0x40;

        /* int. id present */
    if(chi[1] &0x40) {
      p=i+1;
      for(i=p; i<chi[0] && !(chi[i] &0x80); i++);
      if(i==chi[0] || !(chi[i] &0x80)) return 0xfe;
    }

        /* coding standard, Number/Map, Channel Type */
    p=i+1;
    for(i=p; i<chi[0] && !(chi[i] &0x80); i++);
    if(i==chi[0] || !(chi[i] &0x80)) return 0xfe;
    if((chi[p]|0xd0)!=0xd3) return 0xfe;

        /* Number/Map */
    if(chi[p] &0x10) {

        /* map */
      if((chi[0]-p)==4) ofs = 0;
      else if((chi[0]-p)==3) ofs = 1;
      else return 0xfe;
      ch = 0;
      map = 0;
      for(i=0; i<4 && p<chi[0]; i++) {
        p++;
        ch += 8;
        map <<= 8;
        if(chi[p]) {
          for (ch=0; !(chi[p] & (1 << ch)); ch++);
          map |= chi[p];
        }
      }
      ch += ofs;
      map <<= ofs;
    }
    else {

        /* number */
      p=i+1;
      ch = chi[p] &0x3f;
      if(pchannelmap) {
        if((byte)(chi[0]-p)>30) return 0xfe;
        map = 0;
        for(i=p; i<=chi[0]; i++) {
          if ((chi[i] &0x7f) > 31) return 0xfe;
          map |= (1L << (chi[i] &0x7f));
        }
      }
      else {
        if(p!=chi[0]) return 0xfe;
        if (ch > 31) return 0xfe;
        map = (1L << ch);
      }
      if(chi[p] &0x40) return 0xfe;
    }
    if (pchannelmap) *pchannelmap = map;
    else if (map != ((dword)(1L << ch))) return 0xfe;
    return (byte)(excl | ch);
  }
  else {  /* not PRI */
    for(i=1; i<chi[0] && !(chi[i] &0x80); i++);
    if(i!=chi[0] || !(chi[i] &0x80)) return 0xfe;
    if(chi[1] &0x08) excl = 0x40;

    switch(chi[1] |0x98) {
    case 0x98: return 0;
    case 0x99:
      if (pchannelmap) *pchannelmap = 2;
      return excl |1;
    case 0x9a:
      if (pchannelmap) *pchannelmap = 4;
      return excl |2;
    case 0x9b: return 0xff;
    case 0x9c: return 0xfd; /* d-ch */
    default: return 0xfe;
    }
  }
}


static void mixer_set_bchannel_id_esc (PLCI   *plci, byte bchannel_id)
{
  DIVA_CAPI_ADAPTER   *a;
  PLCI   *splci;
  byte old_id;

  a = plci->adapter;
  old_id = plci->li_bchannel_id;
  if (a->li_pri)
  {
    if ((old_id != 0) && (li_config_table[a->li_base + (old_id - 1)].plci == plci))
      li_config_table[a->li_base + (old_id - 1)].plci = NULL;
    plci->li_bchannel_id = (bchannel_id & 0x1f) + 1;
    if (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == NULL)
      li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci = plci;
  }
  else
  {
    if (((bchannel_id & 0x03) == 1) || ((bchannel_id & 0x03) == 2))
    {
      if ((old_id != 0) && (li_config_table[a->li_base + (old_id - 1)].plci == plci))
        li_config_table[a->li_base + (old_id - 1)].plci = NULL;
      plci->li_bchannel_id = bchannel_id & 0x03;
      if ((a->AdvSignalPLCI != NULL) && (a->AdvSignalPLCI != plci) && (a->AdvSignalPLCI->tel == ADV_VOICE))
      {
        splci = a->AdvSignalPLCI;
        if (li_config_table[a->li_base + (2 - plci->li_bchannel_id)].plci == NULL)
        {
          if ((splci->li_bchannel_id != 0)
           && (li_config_table[a->li_base + (splci->li_bchannel_id - 1)].plci == splci))
          {
            li_config_table[a->li_base + (splci->li_bchannel_id - 1)].plci = NULL;
          }
          splci->li_bchannel_id = 3 - plci->li_bchannel_id;
          li_config_table[a->li_base + (2 - plci->li_bchannel_id)].plci = splci;
          dbug (1, dprintf ("[%06lx] %s,%d: adv_voice_set_bchannel_id_esc %d",
            (dword)((splci->Id << 8) | UnMapController (splci->adapter->Id)),
            (char   *)(FILE_), __LINE__, splci->li_bchannel_id));
        }
      }
      if (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == NULL)
        li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci = plci;
    }
  }
  if ((old_id == 0) && (plci->li_bchannel_id != 0)
   && (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == plci))
  {
    mixer_clear_config (plci);
  }
  dbug (1, dprintf ("[%06lx] %s,%d: mixer_set_bchannel_id_esc %d %d",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__, bchannel_id, plci->li_bchannel_id));
}


static void mixer_set_bchannel_id (PLCI   *plci, byte   *chi)
{
  DIVA_CAPI_ADAPTER   *a;
  PLCI   *splci;
  byte ch, old_id;

  a = plci->adapter;
  old_id = plci->li_bchannel_id;
  ch = chi_to_channel (chi, NULL);
  if (!(ch & 0x80))
  {
    if (a->li_pri)
    {
      if ((old_id != 0) && (li_config_table[a->li_base + (old_id - 1)].plci == plci))
        li_config_table[a->li_base + (old_id - 1)].plci = NULL;
      plci->li_bchannel_id = (ch & 0x1f) + 1;
      if (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == NULL)
        li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci = plci;
    }
    else
    {
      if (((ch & 0x1f) == 1) || ((ch & 0x1f) == 2))
      {
        if ((old_id != 0) && (li_config_table[a->li_base + (old_id - 1)].plci == plci))
          li_config_table[a->li_base + (old_id - 1)].plci = NULL;
        plci->li_bchannel_id = ch & 0x1f;
        if ((a->AdvSignalPLCI != NULL) && (a->AdvSignalPLCI != plci) && (a->AdvSignalPLCI->tel == ADV_VOICE))
        {
          splci = a->AdvSignalPLCI;
          if (li_config_table[a->li_base + (2 - plci->li_bchannel_id)].plci == NULL)
          {
            if ((splci->li_bchannel_id != 0)
             && (li_config_table[a->li_base + (splci->li_bchannel_id - 1)].plci == splci))
            {
              li_config_table[a->li_base + (splci->li_bchannel_id - 1)].plci = NULL;
            }
            splci->li_bchannel_id = 3 - plci->li_bchannel_id;
            li_config_table[a->li_base + (2 - plci->li_bchannel_id)].plci = splci;
            dbug (1, dprintf ("[%06lx] %s,%d: adv_voice_set_bchannel_id %d",
              (dword)((splci->Id << 8) | UnMapController (splci->adapter->Id)),
              (char   *)(FILE_), __LINE__, splci->li_bchannel_id));
          }
        }
        if (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == NULL)
          li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci = plci;
      }
    }
  }
  if ((old_id == 0) && (plci->li_bchannel_id != 0)
   && (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == plci))
  {
    mixer_clear_config (plci);
  }
  dbug (1, dprintf ("[%06lx] %s,%d: mixer_set_bchannel_id %02x %d",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__, ch, plci->li_bchannel_id));
}


#define MIXER_MAX_DUMP_CHANNELS 34

static void mixer_calculate_coefs (DIVA_CAPI_ADAPTER   *a)
{
static char hex_digit_table[0x10] = {'0','1','2','3','4','5','6','7','8','9','a','b','c','d','e','f'};
  word n, i, j;
  char *p;
    char hex_line[2 * MIXER_MAX_DUMP_CHANNELS + MIXER_MAX_DUMP_CHANNELS / 8 + 4];

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_calculate_coefs",
    (dword)(UnMapController (a->Id)), (char   *)(FILE_), __LINE__));

  for (i = 0; i < li_total_channels; i++)
  {
    li_config_table[i].channel &= LI_CHANNEL_ADDRESSES_SET;
    if (li_config_table[i].chflags != 0)
      li_config_table[i].channel |= LI_CHANNEL_INVOLVED;
    else
    {
      for (j = 0; j < li_total_channels; j++)
      {
        if (((li_config_table[i].flag_table[j]) != 0)
         || ((li_config_table[j].flag_table[i]) != 0))
        {
          li_config_table[i].channel |= LI_CHANNEL_INVOLVED;
        }
        if (((li_config_table[i].flag_table[j] & LI_FLAG_CONFERENCE) != 0)
         || ((li_config_table[j].flag_table[i] & LI_FLAG_CONFERENCE) != 0))
        {
          li_config_table[i].channel |= LI_CHANNEL_CONFERENCE;
        }
      }
    }
  }
  for (i = 0; i < li_total_channels; i++)
  {
    for (j = 0; j < li_total_channels; j++)
    {
      li_config_table[i].coef_table[j] &= ~(LI_COEF_CH_CH | LI_COEF_CH_PC | LI_COEF_PC_CH | LI_COEF_PC_PC);
      if (li_config_table[i].flag_table[j] & LI_FLAG_CONFERENCE)
        li_config_table[i].coef_table[j] |= LI_COEF_CH_CH;
    }
  }
  for (n = 0; n < li_total_channels; n++)
  {
    if (li_config_table[n].channel & LI_CHANNEL_CONFERENCE)
    {
      for (i = 0; i < li_total_channels; i++)
      {
        if (li_config_table[i].channel & LI_CHANNEL_CONFERENCE)
        {
          for (j = 0; j < li_total_channels; j++)
          {
            li_config_table[i].coef_table[j] |=
              li_config_table[i].coef_table[n] & li_config_table[n].coef_table[j];
          }
        }
      }
    }
  }
  for (i = 0; i < li_total_channels; i++)
  {
    if (li_config_table[i].channel & LI_CHANNEL_INVOLVED)
    {
      li_config_table[i].coef_table[i] &= ~LI_COEF_CH_CH;
      for (j = 0; j < li_total_channels; j++)
      {
        if (li_config_table[i].coef_table[j] & LI_COEF_CH_CH)
          li_config_table[i].flag_table[j] |= LI_FLAG_CONFERENCE;
      }
      if (li_config_table[i].flag_table[i] & LI_FLAG_CONFERENCE)
        li_config_table[i].coef_table[i] |= LI_COEF_CH_CH;
    }
  }
  for (i = 0; i < li_total_channels; i++)
  {
    if (li_config_table[i].channel & LI_CHANNEL_INVOLVED)
    {
      for (j = 0; j < li_total_channels; j++)
      {
        if (li_config_table[i].flag_table[j] & LI_FLAG_INTERCONNECT)
          li_config_table[i].coef_table[j] |= LI_COEF_CH_CH;
        if (li_config_table[i].flag_table[j] & LI_FLAG_MONITOR)
          li_config_table[i].coef_table[j] |= LI_COEF_CH_PC;
        if (li_config_table[i].flag_table[j] & LI_FLAG_MIX)
          li_config_table[i].coef_table[j] |= LI_COEF_PC_CH;
        if (li_config_table[i].flag_table[j] & LI_FLAG_PCCONNECT)
          li_config_table[i].coef_table[j] |= LI_COEF_PC_PC;
      }
      if (li_config_table[i].chflags & LI_CHFLAG_MONITOR)
      {
        for (j = 0; j < li_total_channels; j++)
        {
          if (li_config_table[i].flag_table[j] & LI_FLAG_INTERCONNECT)
          {
            li_config_table[i].coef_table[j] |= LI_COEF_CH_PC;
            if (li_config_table[j].chflags & LI_CHFLAG_MIX)
              li_config_table[i].coef_table[j] |= LI_COEF_PC_CH | LI_COEF_PC_PC;
          }
        }
      }
      if (li_config_table[i].chflags & LI_CHFLAG_MIX)
      {
        for (j = 0; j < li_total_channels; j++)
        {
          if (li_config_table[j].flag_table[i] & LI_FLAG_INTERCONNECT)
            li_config_table[j].coef_table[i] |= LI_COEF_PC_CH;
        }
      }
      if (li_config_table[i].chflags & LI_CHFLAG_LOOP)
      {
        for (j = 0; j < li_total_channels; j++)
        {
          if (li_config_table[i].flag_table[j] & LI_FLAG_INTERCONNECT)
          {
            for (n = 0; n < li_total_channels; n++)
            {
              if (li_config_table[n].flag_table[i] & LI_FLAG_INTERCONNECT)
              {
                li_config_table[n].coef_table[j] |= LI_COEF_CH_CH;
                if (li_config_table[j].chflags & LI_CHFLAG_MIX)
                {
                  li_config_table[n].coef_table[j] |= LI_COEF_PC_CH;
                  if (li_config_table[n].chflags & LI_CHFLAG_MONITOR)
                    li_config_table[n].coef_table[j] |= LI_COEF_CH_PC | LI_COEF_PC_PC;
                }
                else if (li_config_table[n].chflags & LI_CHFLAG_MONITOR)
                  li_config_table[n].coef_table[j] |= LI_COEF_CH_PC;
              }
            }
          }
        }
      }
    }
  }
  for (i = 0; i < li_total_channels; i++)
  {
    if (li_config_table[i].channel & LI_CHANNEL_INVOLVED)
    {
      if (li_config_table[i].chflags & (LI_CHFLAG_MONITOR | LI_CHFLAG_MIX | LI_CHFLAG_LOOP))
        li_config_table[i].channel |= LI_CHANNEL_ACTIVE;
      if (li_config_table[i].chflags & LI_CHFLAG_MONITOR)
        li_config_table[i].channel |= LI_CHANNEL_RX_DATA;
      if (li_config_table[i].chflags & LI_CHFLAG_MIX)
        li_config_table[i].channel |= LI_CHANNEL_TX_DATA;
      for (j = 0; j < li_total_channels; j++)
      {
        if ((li_config_table[i].flag_table[j] &
          (LI_FLAG_INTERCONNECT | LI_FLAG_PCCONNECT | LI_FLAG_CONFERENCE | LI_FLAG_MONITOR))
         || (li_config_table[j].flag_table[i] &
          (LI_FLAG_INTERCONNECT | LI_FLAG_PCCONNECT | LI_FLAG_CONFERENCE | LI_FLAG_ANNOUNCEMENT | LI_FLAG_MIX)))
        {
          li_config_table[i].channel |= LI_CHANNEL_ACTIVE;
        }
        if (li_config_table[i].flag_table[j] & (LI_FLAG_PCCONNECT | LI_FLAG_MONITOR))
          li_config_table[i].channel |= LI_CHANNEL_RX_DATA;
        if (li_config_table[j].flag_table[i] & (LI_FLAG_PCCONNECT | LI_FLAG_ANNOUNCEMENT | LI_FLAG_MIX))
          li_config_table[i].channel |= LI_CHANNEL_TX_DATA;
      }
      if (!(li_config_table[i].channel & LI_CHANNEL_ACTIVE))
      {
        li_config_table[i].coef_table[i] |= LI_COEF_PC_CH | LI_COEF_CH_PC;
        li_config_table[i].channel |= LI_CHANNEL_TX_DATA | LI_CHANNEL_RX_DATA;
      }
    }
  }
  for (i = 0; i < li_total_channels; i++)
  {
    if (li_config_table[i].channel & LI_CHANNEL_INVOLVED)
    {
      j = 0;
      while ((j < li_total_channels) && !(li_config_table[i].flag_table[j] & LI_FLAG_ANNOUNCEMENT))
        j++;
      if (j < li_total_channels)
      {
        for (j = 0; j < li_total_channels; j++)
        {
          li_config_table[i].coef_table[j] &= ~(LI_COEF_CH_CH | LI_COEF_PC_CH);
          if (li_config_table[i].flag_table[j] & LI_FLAG_ANNOUNCEMENT)
            li_config_table[i].coef_table[j] |= LI_COEF_PC_CH;
        }
      }
    }
  }
  n = li_total_channels;
  if (n > MIXER_MAX_DUMP_CHANNELS)
    n = MIXER_MAX_DUMP_CHANNELS;
  p = hex_line;
  for (j = 0; j < n; j++)
  {
    if ((j & 0x7) == 0)
      *(p++) = ' ';
    *(p++) = hex_digit_table[li_config_table[j].curchnl >> 4];
    *(p++) = hex_digit_table[li_config_table[j].curchnl & 0xf];
  }
  *p = '\0';
  dbug (1, dprintf ("[%06lx] CURRENT %s",
    (dword)(UnMapController (a->Id)), (char   *) hex_line));
  p = hex_line;
  for (j = 0; j < n; j++)
  {
    if ((j & 0x7) == 0)
      *(p++) = ' ';
    *(p++) = hex_digit_table[li_config_table[j].channel >> 4];
    *(p++) = hex_digit_table[li_config_table[j].channel & 0xf];
  }
  *p = '\0';
  dbug (1, dprintf ("[%06lx] CHANNEL %s",
    (dword)(UnMapController (a->Id)), (char   *) hex_line));
  p = hex_line;
  for (j = 0; j < n; j++)
  {
    if ((j & 0x7) == 0)
      *(p++) = ' ';
    *(p++) = hex_digit_table[li_config_table[j].chflags >> 4];
    *(p++) = hex_digit_table[li_config_table[j].chflags & 0xf];
  }
  *p = '\0';
  dbug (1, dprintf ("[%06lx] CHFLAG  %s",
    (dword)(UnMapController (a->Id)), (char   *) hex_line));
  for (i = 0; i < n; i++)
  {
    p = hex_line;
    for (j = 0; j < n; j++)
    {
      if ((j & 0x7) == 0)
        *(p++) = ' ';
      *(p++) = hex_digit_table[li_config_table[i].flag_table[j] >> 4];
      *(p++) = hex_digit_table[li_config_table[i].flag_table[j] & 0xf];
    }
    *p = '\0';
    dbug (1, dprintf ("[%06lx] FLAG[%02x]%s",
      (dword)(UnMapController (a->Id)), i, (char   *) hex_line));
  }
  for (i = 0; i < n; i++)
  {
    p = hex_line;
    for (j = 0; j < n; j++)
    {
      if ((j & 0x7) == 0)
        *(p++) = ' ';
      *(p++) = hex_digit_table[li_config_table[i].coef_table[j] >> 4];
      *(p++) = hex_digit_table[li_config_table[i].coef_table[j] & 0xf];
    }
    *p = '\0';
    dbug (1, dprintf ("[%06lx] COEF[%02x]%s",
      (dword)(UnMapController (a->Id)), i, (char   *) hex_line));
  }
}


static struct
{
  byte mask;
  byte line_flags;
} mixer_write_prog_pri[] =
{
  { LI_COEF_CH_CH, 0 },
  { LI_COEF_CH_PC, MIXER_COEF_LINE_TO_PC_FLAG },
  { LI_COEF_PC_CH, MIXER_COEF_LINE_FROM_PC_FLAG },
  { LI_COEF_PC_PC, MIXER_COEF_LINE_TO_PC_FLAG | MIXER_COEF_LINE_FROM_PC_FLAG }
};

static struct
{
  byte from_ch;
  byte to_ch;
  byte mask;
  byte xconnect_override;
} mixer_write_prog_bri[] =
{
  { 0, 0, LI_COEF_CH_CH, 0x01 },  /* B      to B      */
  { 1, 0, LI_COEF_CH_CH, 0x01 },  /* Alt B  to B      */
  { 0, 0, LI_COEF_PC_CH, 0x80 },  /* PC     to B      */
  { 1, 0, LI_COEF_PC_CH, 0x01 },  /* Alt PC to B      */
  { 2, 0, LI_COEF_CH_CH, 0x00 },  /* IC     to B      */
  { 3, 0, LI_COEF_CH_CH, 0x00 },  /* Alt IC to B      */
  { 0, 0, LI_COEF_CH_PC, 0x80 },  /* B      to PC     */
  { 1, 0, LI_COEF_CH_PC, 0x01 },  /* Alt B  to PC     */
  { 0, 0, LI_COEF_PC_PC, 0x01 },  /* PC     to PC     */
  { 1, 0, LI_COEF_PC_PC, 0x01 },  /* Alt PC to PC     */
  { 2, 0, LI_COEF_CH_PC, 0x00 },  /* IC     to PC     */
  { 3, 0, LI_COEF_CH_PC, 0x00 },  /* Alt IC to PC     */
  { 0, 2, LI_COEF_CH_CH, 0x00 },  /* B      to IC     */
  { 1, 2, LI_COEF_CH_CH, 0x00 },  /* Alt B  to IC     */
  { 0, 2, LI_COEF_PC_CH, 0x00 },  /* PC     to IC     */
  { 1, 2, LI_COEF_PC_CH, 0x00 },  /* Alt PC to IC     */
  { 2, 2, LI_COEF_CH_CH, 0x00 },  /* IC     to IC     */
  { 3, 2, LI_COEF_CH_CH, 0x00 },  /* Alt IC to IC     */
  { 1, 1, LI_COEF_CH_CH, 0x01 },  /* Alt B  to Alt B  */
  { 0, 1, LI_COEF_CH_CH, 0x01 },  /* B      to Alt B  */
  { 1, 1, LI_COEF_PC_CH, 0x80 },  /* Alt PC to Alt B  */
  { 0, 1, LI_COEF_PC_CH, 0x01 },  /* PC     to Alt B  */
  { 3, 1, LI_COEF_CH_CH, 0x00 },  /* Alt IC to Alt B  */
  { 2, 1, LI_COEF_CH_CH, 0x00 },  /* IC     to Alt B  */
  { 1, 1, LI_COEF_CH_PC, 0x80 },  /* Alt B  to Alt PC */
  { 0, 1, LI_COEF_CH_PC, 0x01 },  /* B      to Alt PC */
  { 1, 1, LI_COEF_PC_PC, 0x01 },  /* Alt PC to Alt PC */
  { 0, 1, LI_COEF_PC_PC, 0x01 },  /* PC     to Alt PC */
  { 3, 1, LI_COEF_CH_PC, 0x00 },  /* Alt IC to Alt PC */
  { 2, 1, LI_COEF_CH_PC, 0x00 },  /* IC     to Alt PC */
  { 1, 3, LI_COEF_CH_CH, 0x00 },  /* Alt B  to Alt IC */
  { 0, 3, LI_COEF_CH_CH, 0x00 },  /* B      to Alt IC */
  { 1, 3, LI_COEF_PC_CH, 0x00 },  /* Alt PC to Alt IC */
  { 0, 3, LI_COEF_PC_CH, 0x00 },  /* PC     to Alt IC */
  { 3, 3, LI_COEF_CH_CH, 0x00 },  /* Alt IC to Alt IC */
  { 2, 3, LI_COEF_CH_CH, 0x00 }   /* IC     to Alt IC */
};

static byte mixer_swapped_index_bri[] =
{
  18,  /* B      to B      */
  19,  /* Alt B  to B      */
  20,  /* PC     to B      */
  21,  /* Alt PC to B      */
  22,  /* IC     to B      */
  23,  /* Alt IC to B      */
  24,  /* B      to PC     */
  25,  /* Alt B  to PC     */
  26,  /* PC     to PC     */
  27,  /* Alt PC to PC     */
  28,  /* IC     to PC     */
  29,  /* Alt IC to PC     */
  30,  /* B      to IC     */
  31,  /* Alt B  to IC     */
  32,  /* PC     to IC     */
  33,  /* Alt PC to IC     */
  34,  /* IC     to IC     */
  35,  /* Alt IC to IC     */
  0,   /* Alt B  to Alt B  */
  1,   /* B      to Alt B  */
  2,   /* Alt PC to Alt B  */
  3,   /* PC     to Alt B  */
  4,   /* Alt IC to Alt B  */
  5,   /* IC     to Alt B  */
  6,   /* Alt B  to Alt PC */
  7,   /* B      to Alt PC */
  8,   /* Alt PC to Alt PC */
  9,   /* PC     to Alt PC */
  10,  /* Alt IC to Alt PC */
  11,  /* IC     to Alt PC */
  12,  /* Alt B  to Alt IC */
  13,  /* B      to Alt IC */
  14,  /* Alt PC to Alt IC */
  15,  /* PC     to Alt IC */
  16,  /* Alt IC to Alt IC */
  17   /* IC     to Alt IC */
};

static struct
{
  byte mask;
  byte from_pc;
  byte to_pc;
} xconnect_write_prog[] =
{
  { LI_COEF_CH_CH, FALSE, FALSE },
  { LI_COEF_CH_PC, FALSE, TRUE },
  { LI_COEF_PC_CH, TRUE, FALSE },
  { LI_COEF_PC_PC, TRUE, TRUE }
};


static void xconnect_query_addresses (PLCI   *plci)
{
  DIVA_CAPI_ADAPTER   *a;
  word w, ch;
  byte   *p;

  dbug (1, dprintf ("[%06lx] %s,%d: xconnect_query_addresses",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  a = plci->adapter;
  if (a->li_pri && ((plci->li_bchannel_id == 0)
   || (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci != plci)))
  {
    dbug (1, dprintf ("[%06x] %s,%d: Channel id wiped out",
      (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
      (char   *)(FILE_), __LINE__));
    return;
  }
  p = plci->internal_req_buffer;
  ch = (a->li_pri) ? plci->li_bchannel_id - 1 : 0;
  *(p++) = UDATA_REQUEST_XCONNECT_FROM;
  w = ch;
  *(p++) = (byte) w;
  *(p++) = (byte)(w >> 8);
  w = ch | XCONNECT_CHANNEL_PORT_PC;
  *(p++) = (byte) w;
  *(p++) = (byte)(w >> 8);
  plci->NData[0].P = plci->internal_req_buffer;
  plci->NData[0].PLength = p - plci->internal_req_buffer;
  plci->NL.X = plci->NData;
  plci->NL.ReqCh = 0;
  plci->NL.Req = plci->nl_req = (byte) N_UDATA;
  plci->adapter->request (&plci->NL);
}


static void xconnect_write_coefs (PLCI   *plci, word internal_command)
{

  dbug (1, dprintf ("[%06lx] %s,%d: xconnect_write_coefs %04x",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__, internal_command));

  plci->li_write_command = internal_command;
  plci->li_write_channel = 0;
}


static byte xconnect_write_coefs_process (dword Id, PLCI   *plci, byte Rc)
{
  DIVA_CAPI_ADAPTER   *a;
  word w, n, i, j, r, s, to_ch;
  dword d;
  byte   *p;
  struct xconnect_transfer_address_s   *transfer_address;
  byte ch_map[MIXER_CHANNELS_BRI];

  dbug (1, dprintf ("[%06x] %s,%d: xconnect_write_coefs_process %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->li_write_channel));

  a = plci->adapter;
  if ((plci->li_bchannel_id == 0)
   || (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci != plci))
  {
    dbug (1, dprintf ("[%06x] %s,%d: Channel id wiped out",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    return (TRUE);
  }
  i = a->li_base + (plci->li_bchannel_id - 1);
  j = plci->li_write_channel;
  p = plci->internal_req_buffer;
  if (j != 0)
  {
    if ((Rc != OK) && (Rc != OK_FC))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: LI write coefs failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
      return (FALSE);
    }
  }
  if (li_config_table[i].adapter->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)
  {
    r = 0;
    s = 0;
    if (j < li_total_channels)
    {
      if (li_config_table[i].channel & LI_CHANNEL_ADDRESSES_SET)
      {
        s = ((li_config_table[i].send_b.card_address.low | li_config_table[i].send_b.card_address.high) ?
            (LI_COEF_CH_CH | LI_COEF_CH_PC | LI_COEF_PC_CH | LI_COEF_PC_PC) : (LI_COEF_CH_PC | LI_COEF_PC_PC)) &
          ((li_config_table[i].send_pc.card_address.low | li_config_table[i].send_pc.card_address.high) ?
            (LI_COEF_CH_CH | LI_COEF_CH_PC | LI_COEF_PC_CH | LI_COEF_PC_PC) : (LI_COEF_CH_CH | LI_COEF_PC_CH));
      }
      r = ((li_config_table[i].coef_table[j] & 0xf) ^ (li_config_table[i].coef_table[j] >> 4));
      while ((j < li_total_channels)
        && ((r == 0)
         || (!(li_config_table[j].channel & LI_CHANNEL_ADDRESSES_SET))
         || (!li_config_table[j].adapter->li_pri
          && (j >= li_config_table[j].adapter->li_base + MIXER_BCHANNELS_BRI))
         || (((li_config_table[j].send_b.card_address.low != li_config_table[i].send_b.card_address.low)
           || (li_config_table[j].send_b.card_address.high != li_config_table[i].send_b.card_address.high))
          && (!(a->manufacturer_features & MANUFACTURER_FEATURE_DMACONNECT)
           || !(li_config_table[j].adapter->manufacturer_features & MANUFACTURER_FEATURE_DMACONNECT)))
         || ((li_config_table[j].adapter->li_base != a->li_base)
          && !(r & s &
            ((li_config_table[j].send_b.card_address.low | li_config_table[j].send_b.card_address.high) ?
              (LI_COEF_CH_CH | LI_COEF_CH_PC | LI_COEF_PC_CH | LI_COEF_PC_PC) : (LI_COEF_PC_CH | LI_COEF_PC_PC)) &
            ((li_config_table[j].send_pc.card_address.low | li_config_table[j].send_pc.card_address.high) ?
              (LI_COEF_CH_CH | LI_COEF_CH_PC | LI_COEF_PC_CH | LI_COEF_PC_PC) : (LI_COEF_CH_CH | LI_COEF_CH_PC))))))
      {
        j++;
        if (j < li_total_channels)
          r = ((li_config_table[i].coef_table[j] & 0xf) ^ (li_config_table[i].coef_table[j] >> 4));
      }
    }
    if (j < li_total_channels)
    {
      plci->internal_command = plci->li_write_command;
      if (plci_nl_busy (plci))
        return (TRUE);
      to_ch = (a->li_pri) ? plci->li_bchannel_id - 1 : 0;
      *(p++) = UDATA_REQUEST_XCONNECT_TO;
      do
      {
        if (li_config_table[j].adapter->li_base != a->li_base)
        {
          r &= s &
            ((li_config_table[j].send_b.card_address.low | li_config_table[j].send_b.card_address.high) ?
              (LI_COEF_CH_CH | LI_COEF_CH_PC | LI_COEF_PC_CH | LI_COEF_PC_PC) : (LI_COEF_PC_CH | LI_COEF_PC_PC)) &
            ((li_config_table[j].send_pc.card_address.low | li_config_table[j].send_pc.card_address.high) ?
              (LI_COEF_CH_CH | LI_COEF_CH_PC | LI_COEF_PC_CH | LI_COEF_PC_PC) : (LI_COEF_CH_CH | LI_COEF_CH_PC));
        }
        n = 0;
        do
        {
          if (r & xconnect_write_prog[n].mask)
          {
            if (xconnect_write_prog[n].from_pc)
              transfer_address = &(li_config_table[j].send_pc);
            else
              transfer_address = &(li_config_table[j].send_b);
            d = transfer_address->card_address.low;
            *(p++) = (byte) d;
            *(p++) = (byte)(d >> 8);
            *(p++) = (byte)(d >> 16);
            *(p++) = (byte)(d >> 24);
            d = transfer_address->card_address.high;
            *(p++) = (byte) d;
            *(p++) = (byte)(d >> 8);
            *(p++) = (byte)(d >> 16);
            *(p++) = (byte)(d >> 24);
            d = transfer_address->offset;
            *(p++) = (byte) d;
            *(p++) = (byte)(d >> 8);
            *(p++) = (byte)(d >> 16);
            *(p++) = (byte)(d >> 24);
            w = xconnect_write_prog[n].to_pc ? to_ch | XCONNECT_CHANNEL_PORT_PC : to_ch;
            *(p++) = (byte) w;
            *(p++) = (byte)(w >> 8);
            w = ((li_config_table[i].coef_table[j] & xconnect_write_prog[n].mask) == 0) ? 0x01 :
              (li_config_table[i].adapter->u_law ?
                 (li_config_table[j].adapter->u_law ? 0x80 : 0x86) :
                 (li_config_table[j].adapter->u_law ? 0x7a : 0x80));
            *(p++) = (byte) w;
            *(p++) = (byte) 0;
            li_config_table[i].coef_table[j] ^= xconnect_write_prog[n].mask << 4;
          }
          n++;
        } while ((n < sizeof(xconnect_write_prog) / sizeof(xconnect_write_prog[0]))
          && ((p - plci->internal_req_buffer) + 16 < INTERNAL_REQ_BUFFER_SIZE));
        if (n == sizeof(xconnect_write_prog) / sizeof(xconnect_write_prog[0]))
        {
          do
          {
            j++;
            if (j < li_total_channels)
              r = ((li_config_table[i].coef_table[j] & 0xf) ^ (li_config_table[i].coef_table[j] >> 4));
          } while ((j < li_total_channels)
            && ((r == 0)
             || (!(li_config_table[j].channel & LI_CHANNEL_ADDRESSES_SET))
             || (!li_config_table[j].adapter->li_pri
              && (j >= li_config_table[j].adapter->li_base + MIXER_BCHANNELS_BRI))
             || (((li_config_table[j].send_b.card_address.low != li_config_table[i].send_b.card_address.low)
               || (li_config_table[j].send_b.card_address.high != li_config_table[i].send_b.card_address.high))
              && (!(a->manufacturer_features & MANUFACTURER_FEATURE_DMACONNECT)
               || !(li_config_table[j].adapter->manufacturer_features & MANUFACTURER_FEATURE_DMACONNECT)))
             || ((li_config_table[j].adapter->li_base != a->li_base)
              && !(r & s &
                ((li_config_table[j].send_b.card_address.low | li_config_table[j].send_b.card_address.high) ?
                  (LI_COEF_CH_CH | LI_COEF_CH_PC | LI_COEF_PC_CH | LI_COEF_PC_PC) : (LI_COEF_PC_CH | LI_COEF_PC_PC)) &
                ((li_config_table[j].send_pc.card_address.low | li_config_table[j].send_pc.card_address.high) ?
                  (LI_COEF_CH_CH | LI_COEF_CH_PC | LI_COEF_PC_CH | LI_COEF_PC_PC) : (LI_COEF_CH_CH | LI_COEF_CH_PC))))));
        }
      } while ((j < li_total_channels)
        && ((p - plci->internal_req_buffer) + 16 < INTERNAL_REQ_BUFFER_SIZE));
    }
    else if (j == li_total_channels)
    {
      plci->internal_command = plci->li_write_command;
      if (plci_nl_busy (plci))
        return (TRUE);
      if (a->li_pri)
      {
        *(p++) = UDATA_REQUEST_SET_MIXER_COEFS_PRI_SYNC;
        w = 0;
        if (li_config_table[i].channel & LI_CHANNEL_TX_DATA)
          w |= MIXER_FEATURE_ENABLE_TX_DATA;
        if (li_config_table[i].channel & LI_CHANNEL_RX_DATA)
          w |= MIXER_FEATURE_ENABLE_RX_DATA;
        *(p++) = (byte) w;
        *(p++) = (byte)(w >> 8);
      }
      else
      {
        *(p++) = UDATA_REQUEST_SET_MIXER_COEFS_BRI;
        w = 0;
        if ((plci->tel == ADV_VOICE) && (plci == a->AdvSignalPLCI)
         && (ADV_VOICE_NEW_COEF_BASE + sizeof(word) <= a->adv_voice_coef_length))
        {
          w = GET_WORD (a->adv_voice_coef_buffer + ADV_VOICE_NEW_COEF_BASE);
        }
        if (li_config_table[i].channel & LI_CHANNEL_TX_DATA)
          w |= MIXER_FEATURE_ENABLE_TX_DATA;
        if (li_config_table[i].channel & LI_CHANNEL_RX_DATA)
          w |= MIXER_FEATURE_ENABLE_RX_DATA;
        *(p++) = (byte) w;
        *(p++) = (byte)(w >> 8);
        for (j = 0; j < sizeof(ch_map); j += 2)
        {
          if (plci->li_bchannel_id == 2)
          {
            ch_map[j] = (byte)(j+1);
            ch_map[j+1] = (byte) j;
          }
          else
          {
            ch_map[j] = (byte) j;
            ch_map[j+1] = (byte)(j+1);
          }
        }
        for (n = 0; n < sizeof(mixer_write_prog_bri) / sizeof(mixer_write_prog_bri[0]); n++)
        {
          i = a->li_base + ch_map[mixer_write_prog_bri[n].to_ch];
          j = a->li_base + ch_map[mixer_write_prog_bri[n].from_ch];
          if (li_config_table[i].channel & li_config_table[j].channel & LI_CHANNEL_INVOLVED)
          {
            *p = (mixer_write_prog_bri[n].xconnect_override != 0) ?
              mixer_write_prog_bri[n].xconnect_override :
              ((li_config_table[i].coef_table[j] & mixer_write_prog_bri[n].mask) ? 0x80 : 0x01);
            if ((i >= a->li_base + MIXER_BCHANNELS_BRI) || (j >= a->li_base + MIXER_BCHANNELS_BRI))
            {
              w = ((li_config_table[i].coef_table[j] & 0xf) ^ (li_config_table[i].coef_table[j] >> 4));
              li_config_table[i].coef_table[j] ^= (w & mixer_write_prog_bri[n].mask) << 4;
            }
          }
          else
          {
            *p = 0x00;
            if ((a->AdvSignalPLCI != NULL) && (a->AdvSignalPLCI->tel == ADV_VOICE))
            {
              w = (plci == a->AdvSignalPLCI) ? n : mixer_swapped_index_bri[n];
              if (ADV_VOICE_NEW_COEF_BASE + sizeof(word) + w < a->adv_voice_coef_length)
                *p = a->adv_voice_coef_buffer[ADV_VOICE_NEW_COEF_BASE + sizeof(word) + w];
            }
          }
          p++;
        }
      }
      j = li_total_channels + 1;
    }
  }
  else
  {
    if (j <= li_total_channels)
    {
      plci->internal_command = plci->li_write_command;
      if (plci_nl_busy (plci))
        return (TRUE);
      if (j < a->li_base)
        j = a->li_base;
      if (a->li_pri)
      {
        *(p++) = UDATA_REQUEST_SET_MIXER_COEFS_PRI_SYNC;
        w = 0;
        if (li_config_table[i].channel & LI_CHANNEL_TX_DATA)
          w |= MIXER_FEATURE_ENABLE_TX_DATA;
        if (li_config_table[i].channel & LI_CHANNEL_RX_DATA)
          w |= MIXER_FEATURE_ENABLE_RX_DATA;
        *(p++) = (byte) w;
        *(p++) = (byte)(w >> 8);
        for (n = 0; n < sizeof(mixer_write_prog_pri) / sizeof(mixer_write_prog_pri[0]); n++)
        {
          *(p++) = (byte)((plci->li_bchannel_id - 1) | mixer_write_prog_pri[n].line_flags);
          for (j = a->li_base; j < a->li_base + MIXER_CHANNELS_PRI; j++)
          {
            w = ((li_config_table[i].coef_table[j] & 0xf) ^ (li_config_table[i].coef_table[j] >> 4));
            if (w & mixer_write_prog_pri[n].mask)
            {
              *(p++) = (li_config_table[i].coef_table[j] & mixer_write_prog_pri[n].mask) ? 0x80 : 0x01;
              li_config_table[i].coef_table[j] ^= mixer_write_prog_pri[n].mask << 4;
            }
            else
              *(p++) = 0x00;
          }
          *(p++) = (byte)((plci->li_bchannel_id - 1) | MIXER_COEF_LINE_ROW_FLAG | mixer_write_prog_pri[n].line_flags);
          for (j = a->li_base; j < a->li_base + MIXER_CHANNELS_PRI; j++)
          {
            w = ((li_config_table[j].coef_table[i] & 0xf) ^ (li_config_table[j].coef_table[i] >> 4));
            if (w & mixer_write_prog_pri[n].mask)
            {
              *(p++) = (li_config_table[j].coef_table[i] & mixer_write_prog_pri[n].mask) ? 0x80 : 0x01;
              li_config_table[j].coef_table[i] ^= mixer_write_prog_pri[n].mask << 4;
            }
            else
              *(p++) = 0x00;
          }
        }
      }
      else
      {
        *(p++) = UDATA_REQUEST_SET_MIXER_COEFS_BRI;
        w = 0;
        if ((plci->tel == ADV_VOICE) && (plci == a->AdvSignalPLCI)
         && (ADV_VOICE_NEW_COEF_BASE + sizeof(word) <= a->adv_voice_coef_length))
        {
          w = GET_WORD (a->adv_voice_coef_buffer + ADV_VOICE_NEW_COEF_BASE);
        }
        if (li_config_table[i].channel & LI_CHANNEL_TX_DATA)
          w |= MIXER_FEATURE_ENABLE_TX_DATA;
        if (li_config_table[i].channel & LI_CHANNEL_RX_DATA)
          w |= MIXER_FEATURE_ENABLE_RX_DATA;
        *(p++) = (byte) w;
        *(p++) = (byte)(w >> 8);
        for (j = 0; j < sizeof(ch_map); j += 2)
        {
          if (plci->li_bchannel_id == 2)
          {
            ch_map[j] = (byte)(j+1);
            ch_map[j+1] = (byte) j;
          }
          else
          {
            ch_map[j] = (byte) j;
            ch_map[j+1] = (byte)(j+1);
          }
        }
        for (n = 0; n < sizeof(mixer_write_prog_bri) / sizeof(mixer_write_prog_bri[0]); n++)
        {
          i = a->li_base + ch_map[mixer_write_prog_bri[n].to_ch];
          j = a->li_base + ch_map[mixer_write_prog_bri[n].from_ch];
          if (li_config_table[i].channel & li_config_table[j].channel & LI_CHANNEL_INVOLVED)
          {
            *p = ((li_config_table[i].coef_table[j] & mixer_write_prog_bri[n].mask) ? 0x80 : 0x01);
            w = ((li_config_table[i].coef_table[j] & 0xf) ^ (li_config_table[i].coef_table[j] >> 4));
            li_config_table[i].coef_table[j] ^= (w & mixer_write_prog_bri[n].mask) << 4;
          }
          else
          {
            *p = 0x00;
            if ((a->AdvSignalPLCI != NULL) && (a->AdvSignalPLCI->tel == ADV_VOICE))
            {
              w = (plci == a->AdvSignalPLCI) ? n : mixer_swapped_index_bri[n];
              if (ADV_VOICE_NEW_COEF_BASE + sizeof(word) + w < a->adv_voice_coef_length)
                *p = a->adv_voice_coef_buffer[ADV_VOICE_NEW_COEF_BASE + sizeof(word) + w];
            }
          }
          p++;
        }
      }
      j = li_total_channels + 1;
    }
  }
  plci->li_write_channel = j;
  if (p != plci->internal_req_buffer)
  {
    plci->NData[0].P = plci->internal_req_buffer;
    plci->NData[0].PLength = p - plci->internal_req_buffer;
    plci->NL.X = plci->NData;
    plci->NL.ReqCh = 0;
    plci->NL.Req = plci->nl_req = (byte) N_UDATA;
    plci->adapter->request (&plci->NL);
  }
  return (TRUE);
}


static void mixer_notify_update (PLCI   *plci, byte others)
{
  DIVA_CAPI_ADAPTER   *a;
  word i, w;
  PLCI   *notify_plci;
    byte msg[sizeof(CAPI_MSG_HEADER) + 6];

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_notify_update %d",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__, others));

  a = plci->adapter;
  if (a->profile.Global_Options & GL_LINE_INTERCONNECT_SUPPORTED)
  {
    if (others)
      plci->li_notify_update = TRUE;
    i = 0;
    do
    {
      notify_plci = NULL;
      if (others)
      {
        while ((i < li_total_channels) && (li_config_table[i].plci == NULL))
          i++;
        if (i < li_total_channels)
          notify_plci = li_config_table[i++].plci;
      }
      else
      {
        if ((plci->li_bchannel_id != 0)
         && (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == plci))
        {
          notify_plci = plci;
        }
      }
      if ((notify_plci != NULL)
       && !notify_plci->li_notify_update
       && (notify_plci->appl != NULL)
       && (notify_plci->State)
       && notify_plci->NL.Id && !notify_plci->nl_remove_id)
      {
        notify_plci->li_notify_update = TRUE;
        ((CAPI_MSG *) msg)->header.length = 18;
        ((CAPI_MSG *) msg)->header.appl_id = notify_plci->appl->Id;
        ((CAPI_MSG *) msg)->header.command = _FACILITY_R;
        ((CAPI_MSG *) msg)->header.number = 0;
        ((CAPI_MSG *) msg)->header.controller = notify_plci->adapter->Id;
        ((CAPI_MSG *) msg)->header.plci = notify_plci->Id;
        ((CAPI_MSG *) msg)->header.ncci = 0;
        ((CAPI_MSG *) msg)->info.facility_req.Selector = SELECTOR_LINE_INTERCONNECT;
        ((CAPI_MSG *) msg)->info.facility_req.structs[0] = 3;
        PUT_WORD (&(((CAPI_MSG *) msg)->info.facility_req.structs[1]), LI_REQ_SILENT_UPDATE);
        ((CAPI_MSG *) msg)->info.facility_req.structs[3] = 0;
        w = api_put (notify_plci->appl, (CAPI_MSG *) msg);
        if (w != _QUEUE_FULL)
        {
          if (w != 0)
          {
            dbug (1, dprintf ("[%06lx] %s,%d: Interconnect notify failed %06x %d",
              (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
              (char   *)(FILE_), __LINE__,
              (dword)((notify_plci->Id << 8) | UnMapController (notify_plci->adapter->Id)), w));
          }
          notify_plci->li_notify_update = FALSE;
        }
      }
    } while (others && (notify_plci != NULL));
    if (others)
      plci->li_notify_update = FALSE;
  }
}


static void mixer_clear_config (PLCI   *plci)
{
  DIVA_CAPI_ADAPTER   *a;
  word i, j;

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_clear_config",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  plci->li_notify_update = FALSE;
  plci->li_plci_b_write_pos = 0;
  plci->li_plci_b_read_pos = 0;
  plci->li_plci_b_req_pos = 0;
  a = plci->adapter;
  if ((plci->li_bchannel_id != 0)
   && (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == plci))
  {
    i = a->li_base + (plci->li_bchannel_id - 1);
    li_config_table[i].curchnl = 0;
    li_config_table[i].channel = 0;
    li_config_table[i].chflags = 0;
    for (j = 0; j < li_total_channels; j++)
    {
      li_config_table[j].flag_table[i] = 0;
      li_config_table[i].flag_table[j] = 0;
      li_config_table[i].coef_table[j] = 0;
      li_config_table[j].coef_table[i] = 0;
    }
    if (!a->li_pri)
    {
      li_config_table[i].coef_table[i] |= LI_COEF_CH_PC_SET | LI_COEF_PC_CH_SET;
      if ((plci->tel == ADV_VOICE) && (plci == a->AdvSignalPLCI))
      {
        i = a->li_base + MIXER_IC_CHANNEL_BASE + (plci->li_bchannel_id - 1);
        li_config_table[i].curchnl = 0;
        li_config_table[i].channel = 0;
        li_config_table[i].chflags = 0;
        for (j = 0; j < li_total_channels; j++)
        {
          li_config_table[i].flag_table[j] = 0;
          li_config_table[j].flag_table[i] = 0;
          li_config_table[i].coef_table[j] = 0;
          li_config_table[j].coef_table[i] = 0;
        }
        if (a->manufacturer_features & MANUFACTURER_FEATURE_SLAVE_CODEC)
        {
          i = a->li_base + MIXER_IC_CHANNEL_BASE + (2 - plci->li_bchannel_id);
          li_config_table[i].curchnl = 0;
          li_config_table[i].channel = 0;
          li_config_table[i].chflags = 0;
          for (j = 0; j < li_total_channels; j++)
          {
            li_config_table[i].flag_table[j] = 0;
            li_config_table[j].flag_table[i] = 0;
            li_config_table[i].coef_table[j] = 0;
            li_config_table[j].coef_table[i] = 0;
          }
        }
      }
    }
  }
}


static void mixer_prepare_switch (dword Id, PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_prepare_switch",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  do
  {
    mixer_indication_coefs_set (Id, plci);
  } while (plci->li_plci_b_read_pos != plci->li_plci_b_req_pos);
}


static word mixer_save_config (dword Id, PLCI   *plci, byte Rc)
{
  DIVA_CAPI_ADAPTER   *a;
  word i, j;

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_save_config %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  a = plci->adapter;
  if ((plci->li_bchannel_id != 0)
   && (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == plci))
  {
    i = a->li_base + (plci->li_bchannel_id - 1);
    for (j = 0; j < li_total_channels; j++)
    {
      li_config_table[i].coef_table[j] &= 0xf;
      li_config_table[j].coef_table[i] &= 0xf;
    }
    if (!a->li_pri)
      li_config_table[i].coef_table[i] |= LI_COEF_CH_PC_SET | LI_COEF_PC_CH_SET;
  }
  return (GOOD);
}


static word mixer_restore_config (dword Id, PLCI   *plci, byte Rc)
{
  DIVA_CAPI_ADAPTER   *a;
  word Info;

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_restore_config %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  Info = GOOD;
  a = plci->adapter;
  if ((plci->B1_facilities & B1_FACILITY_MIXER)
   && (plci->li_bchannel_id != 0)
   && (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == plci))
  {
    switch (plci->adjust_b_state)
    {
    case ADJUST_B_RESTORE_MIXER_1:
      if (a->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)
      {
        plci->internal_command = plci->adjust_b_command;
        if (plci_nl_busy (plci))
        {
          plci->adjust_b_state = ADJUST_B_RESTORE_MIXER_1;
          break;
        }
        xconnect_query_addresses (plci);
        plci->adjust_b_state = ADJUST_B_RESTORE_MIXER_2;
        break;
      }
      plci->adjust_b_state = ADJUST_B_RESTORE_MIXER_5;
      Rc = OK;
    case ADJUST_B_RESTORE_MIXER_2:
    case ADJUST_B_RESTORE_MIXER_3:
    case ADJUST_B_RESTORE_MIXER_4:
      if ((Rc != OK) && (Rc != OK_FC) && (Rc != 0))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Adjust B query addresses failed %02x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
        Info = _WRONG_STATE;
        break;
      }
      if (Rc == OK)
      {
        if (plci->adjust_b_state == ADJUST_B_RESTORE_MIXER_2)
          plci->adjust_b_state = ADJUST_B_RESTORE_MIXER_3;
        else if (plci->adjust_b_state == ADJUST_B_RESTORE_MIXER_4)
          plci->adjust_b_state = ADJUST_B_RESTORE_MIXER_5;
      }
      else if (Rc == 0)
      {
        if (plci->adjust_b_state == ADJUST_B_RESTORE_MIXER_2)
          plci->adjust_b_state = ADJUST_B_RESTORE_MIXER_4;
        else if (plci->adjust_b_state == ADJUST_B_RESTORE_MIXER_3)
          plci->adjust_b_state = ADJUST_B_RESTORE_MIXER_5;
      }
      if (plci->adjust_b_state != ADJUST_B_RESTORE_MIXER_5)
      {
        plci->internal_command = plci->adjust_b_command;
        break;
      }
    case ADJUST_B_RESTORE_MIXER_5:
      xconnect_write_coefs (plci, plci->adjust_b_command);
      plci->adjust_b_state = ADJUST_B_RESTORE_MIXER_6;
      Rc = OK;
    case ADJUST_B_RESTORE_MIXER_6:
      if (!xconnect_write_coefs_process (Id, plci, Rc))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Write mixer coefs failed",
          UnMapId (Id), (char   *)(FILE_), __LINE__));
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
      if (plci->internal_command)
        break;
      plci->adjust_b_state = ADJUST_B_RESTORE_MIXER_7;
    case ADJUST_B_RESTORE_MIXER_7:
      break;
    }
  }
  return (Info);
}


static void mixer_command (dword Id, PLCI   *plci, byte Rc)
{
  DIVA_CAPI_ADAPTER   *a;
  word i, internal_command, Info;

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_command %02x %04x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command,
    plci->li_cmd));

  Info = GOOD;
  a = plci->adapter;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (plci->li_cmd)
  {
  case LI_REQ_CONNECT:
  case LI_REQ_DISCONNECT:
  case LI_REQ_SILENT_UPDATE:
    switch (internal_command)
    {
    default:
      if (plci->li_channel_bits & LI_CHANNEL_INVOLVED)
      {
        adjust_b1_resource (Id, plci, NULL, (word)(plci->B1_facilities |
          B1_FACILITY_MIXER), MIXER_COMMAND_1);
      }
    case MIXER_COMMAND_1:
      if (plci->li_channel_bits & LI_CHANNEL_INVOLVED)
      {
        if (adjust_b_process (Id, plci, Rc) != GOOD)
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Load mixer failed",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _FACILITY_NOT_SUPPORTED;
          break;
        }
        if (plci->internal_command)
          return;
      }
      plci->li_plci_b_req_pos = plci->li_plci_b_write_pos;
      if ((plci->li_channel_bits & LI_CHANNEL_INVOLVED)
       || ((get_b1_facilities (plci, plci->B1_resource) & B1_FACILITY_MIXER)
        && (add_b1_facilities (plci, plci->B1_resource, (word)(plci->B1_facilities &
         ~B1_FACILITY_MIXER)) == plci->B1_resource)))
      {
        xconnect_write_coefs (plci, MIXER_COMMAND_2);
      }
      else
      {
        do
        {
          mixer_indication_coefs_set (Id, plci);
        } while (plci->li_plci_b_read_pos != plci->li_plci_b_req_pos);
      }
    case MIXER_COMMAND_2:
      if ((plci->li_channel_bits & LI_CHANNEL_INVOLVED)
       || ((get_b1_facilities (plci, plci->B1_resource) & B1_FACILITY_MIXER)
        && (add_b1_facilities (plci, plci->B1_resource, (word)(plci->B1_facilities &
         ~B1_FACILITY_MIXER)) == plci->B1_resource)))
      {
        if (!xconnect_write_coefs_process (Id, plci, Rc))
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Write mixer coefs failed",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          if (plci->li_plci_b_write_pos != plci->li_plci_b_req_pos)
          {
            do
            {
              plci->li_plci_b_write_pos = (plci->li_plci_b_write_pos == 0) ?
                LI_PLCI_B_QUEUE_ENTRIES-1 : plci->li_plci_b_write_pos - 1;
              i = (plci->li_plci_b_write_pos == 0) ?
                LI_PLCI_B_QUEUE_ENTRIES-1 : plci->li_plci_b_write_pos - 1;
            } while ((plci->li_plci_b_write_pos != plci->li_plci_b_req_pos)
              && !(plci->li_plci_b_queue[i] & LI_PLCI_B_LAST_FLAG));
          }
          Info = _FACILITY_NOT_SUPPORTED;
          break;
        }
        if (plci->internal_command)
          return;
      }
      if (!(plci->li_channel_bits & LI_CHANNEL_INVOLVED))
      {
        adjust_b1_resource (Id, plci, NULL, (word)(plci->B1_facilities &
          ~B1_FACILITY_MIXER), MIXER_COMMAND_3);
      }
    case MIXER_COMMAND_3:
      if (!(plci->li_channel_bits & LI_CHANNEL_INVOLVED))
      {
        if (adjust_b_process (Id, plci, Rc) != GOOD)
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Unload mixer failed",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _FACILITY_NOT_SUPPORTED;
          break;
        }
        if (plci->internal_command)
          return;
      }
      break;
    }
    break;
  }
  if ((plci->li_bchannel_id == 0)
   || (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci != plci))
  {
    dbug (1, dprintf ("[%06x] %s,%d: Channel id wiped out %d",
      UnMapId (Id), (char   *)(FILE_), __LINE__, (int)(plci->li_bchannel_id)));
  }
  else
  {
    i = a->li_base + (plci->li_bchannel_id - 1);
    li_config_table[i].curchnl = plci->li_channel_bits;
    if (!a->li_pri && (plci->tel == ADV_VOICE) && (plci == a->AdvSignalPLCI))
    {
      i = a->li_base + MIXER_IC_CHANNEL_BASE + (plci->li_bchannel_id - 1);
      li_config_table[i].curchnl = plci->li_channel_bits;
      if (a->manufacturer_features & MANUFACTURER_FEATURE_SLAVE_CODEC)
      {
        i = a->li_base + MIXER_IC_CHANNEL_BASE + (2 - plci->li_bchannel_id);
        li_config_table[i].curchnl = plci->li_channel_bits;
      }
    }
  }
}


static void li_update_connect (dword Id, DIVA_CAPI_ADAPTER   *a, PLCI   *plci,
  dword plci_b_id, byte connect, dword li_flags)
{
  word i, ch_a, ch_a_v, ch_a_s, ch_b, ch_b_v, ch_b_s;
  PLCI   *plci_b;
  DIVA_CAPI_ADAPTER   *a_b;

  a_b = &(adapter[MapController ((byte)(plci_b_id & 0x7f)) - 1]);
  plci_b = &(a_b->plci[((plci_b_id >> 8) & 0xff) - 1]);
  ch_a = a->li_base + (plci->li_bchannel_id - 1);
  if (!a->li_pri && (plci->tel == ADV_VOICE)
   && (plci == a->AdvSignalPLCI) && (Id & EXT_CONTROLLER))
  {
    ch_a_v = ch_a + MIXER_IC_CHANNEL_BASE;
    ch_a_s = (a->manufacturer_features & MANUFACTURER_FEATURE_SLAVE_CODEC) ?
      a->li_base + MIXER_IC_CHANNEL_BASE + (2 - plci->li_bchannel_id) : ch_a_v;
  }
  else
  {
    ch_a_v = ch_a;
    ch_a_s = ch_a;
  }
  ch_b = a_b->li_base + (plci_b->li_bchannel_id - 1);
  if (!a_b->li_pri && (plci_b->tel == ADV_VOICE)
   && (plci_b == a_b->AdvSignalPLCI) && (plci_b_id & EXT_CONTROLLER))
  {
    ch_b_v = ch_b + MIXER_IC_CHANNEL_BASE;
    ch_b_s = (a_b->manufacturer_features & MANUFACTURER_FEATURE_SLAVE_CODEC) ?
      a_b->li_base + MIXER_IC_CHANNEL_BASE + (2 - plci_b->li_bchannel_id) : ch_b_v;
  }
  else
  {
    ch_b_v = ch_b;
    ch_b_s = ch_b;
  }
  if (connect)
  {
    li_config_table[ch_a].flag_table[ch_a_v] &= ~LI_FLAG_MONITOR;
    li_config_table[ch_a].flag_table[ch_a_s] &= ~LI_FLAG_MONITOR;
    li_config_table[ch_a_v].flag_table[ch_a] &= ~(LI_FLAG_ANNOUNCEMENT | LI_FLAG_MIX);
    li_config_table[ch_a_s].flag_table[ch_a] &= ~(LI_FLAG_ANNOUNCEMENT | LI_FLAG_MIX);
  }
  li_config_table[ch_a].flag_table[ch_b_v] &= ~LI_FLAG_MONITOR;
  li_config_table[ch_a].flag_table[ch_b_s] &= ~LI_FLAG_MONITOR;
  li_config_table[ch_b_v].flag_table[ch_a] &= ~(LI_FLAG_ANNOUNCEMENT | LI_FLAG_MIX);
  li_config_table[ch_b_s].flag_table[ch_a] &= ~(LI_FLAG_ANNOUNCEMENT | LI_FLAG_MIX);
  if (ch_a_v == ch_b_v)
  {
    li_config_table[ch_a_v].flag_table[ch_b_v] &= ~LI_FLAG_CONFERENCE;
    li_config_table[ch_a_s].flag_table[ch_b_s] &= ~LI_FLAG_CONFERENCE;
  }
  else
  {
    if (li_config_table[ch_a_v].flag_table[ch_b_v] & LI_FLAG_CONFERENCE)
    {
      for (i = 0; i < li_total_channels; i++)
      {
        if (i != ch_a_v)
          li_config_table[ch_a_v].flag_table[i] &= ~LI_FLAG_CONFERENCE;
      }
    }
    if (li_config_table[ch_a_s].flag_table[ch_b_v] & LI_FLAG_CONFERENCE)
    {
      for (i = 0; i < li_total_channels; i++)
      {
        if (i != ch_a_s)
          li_config_table[ch_a_s].flag_table[i] &= ~LI_FLAG_CONFERENCE;
      }
    }
    if (li_config_table[ch_b_v].flag_table[ch_a_v] & LI_FLAG_CONFERENCE)
    {
      for (i = 0; i < li_total_channels; i++)
      {
        if (i != ch_a_v)
          li_config_table[i].flag_table[ch_a_v] &= ~LI_FLAG_CONFERENCE;
      }
    }
    if (li_config_table[ch_b_v].flag_table[ch_a_s] & LI_FLAG_CONFERENCE)
    {
      for (i = 0; i < li_total_channels; i++)
      {
        if (i != ch_a_s)
          li_config_table[i].flag_table[ch_a_s] &= ~LI_FLAG_CONFERENCE;
      }
    }
  }
  if (li_flags & LI_FLAG_CONFERENCE_A_B)
  {
    li_config_table[ch_b_v].flag_table[ch_a_v] |= LI_FLAG_CONFERENCE;
    li_config_table[ch_b_s].flag_table[ch_a_v] |= LI_FLAG_CONFERENCE;
    li_config_table[ch_b_v].flag_table[ch_a_s] |= LI_FLAG_CONFERENCE;
    li_config_table[ch_b_s].flag_table[ch_a_s] |= LI_FLAG_CONFERENCE;
  }
  if (li_flags & LI_FLAG_CONFERENCE_B_A)
  {
    li_config_table[ch_a_v].flag_table[ch_b_v] |= LI_FLAG_CONFERENCE;
    li_config_table[ch_a_v].flag_table[ch_b_s] |= LI_FLAG_CONFERENCE;
    li_config_table[ch_a_s].flag_table[ch_b_v] |= LI_FLAG_CONFERENCE;
    li_config_table[ch_a_s].flag_table[ch_b_s] |= LI_FLAG_CONFERENCE;
  }
  if (li_flags & LI_FLAG_MONITOR_A)
  {
    li_config_table[ch_a].flag_table[ch_a_v] |= LI_FLAG_MONITOR;
    li_config_table[ch_a].flag_table[ch_a_s] |= LI_FLAG_MONITOR;
  }
  if (li_flags & LI_FLAG_MONITOR_B)
  {
    li_config_table[ch_a].flag_table[ch_b_v] |= LI_FLAG_MONITOR;
    li_config_table[ch_a].flag_table[ch_b_s] |= LI_FLAG_MONITOR;
  }
  if (li_flags & LI_FLAG_ANNOUNCEMENT_A)
  {
    li_config_table[ch_a_v].flag_table[ch_a] |= LI_FLAG_ANNOUNCEMENT;
    li_config_table[ch_a_s].flag_table[ch_a] |= LI_FLAG_ANNOUNCEMENT;
  }
  if (li_flags & LI_FLAG_ANNOUNCEMENT_B)
  {
    li_config_table[ch_b_v].flag_table[ch_a] |= LI_FLAG_ANNOUNCEMENT;
    li_config_table[ch_b_s].flag_table[ch_a] |= LI_FLAG_ANNOUNCEMENT;
  }
  if (li_flags & LI_FLAG_MIX_A)
  {
    li_config_table[ch_a_v].flag_table[ch_a] |= LI_FLAG_MIX;
    li_config_table[ch_a_s].flag_table[ch_a] |= LI_FLAG_MIX;
  }
  if (li_flags & LI_FLAG_MIX_B)
  {
    li_config_table[ch_b_v].flag_table[ch_a] |= LI_FLAG_MIX;
    li_config_table[ch_b_s].flag_table[ch_a] |= LI_FLAG_MIX;
  }
  if (ch_a_v != ch_a_s)
  {
    li_config_table[ch_a_v].flag_table[ch_a_s] |= LI_FLAG_CONFERENCE;
    li_config_table[ch_a_s].flag_table[ch_a_v] |= LI_FLAG_CONFERENCE;
  }
  if (ch_b_v != ch_b_s)
  {
    li_config_table[ch_b_v].flag_table[ch_b_s] |= LI_FLAG_CONFERENCE;
    li_config_table[ch_b_s].flag_table[ch_b_v] |= LI_FLAG_CONFERENCE;
  }
}


static void li2_update_connect (dword Id, DIVA_CAPI_ADAPTER   *a, PLCI   *plci,
  dword plci_b_id, byte connect, dword li_flags)
{
  word ch_a, ch_a_v, ch_a_s, ch_b, ch_b_v, ch_b_s;
  PLCI   *plci_b;
  DIVA_CAPI_ADAPTER   *a_b;

  a_b = &(adapter[MapController ((byte)(plci_b_id & 0x7f)) - 1]);
  plci_b = &(a_b->plci[((plci_b_id >> 8) & 0xff) - 1]);
  ch_a = a->li_base + (plci->li_bchannel_id - 1);
  if (!a->li_pri && (plci->tel == ADV_VOICE)
   && (plci == a->AdvSignalPLCI) && (Id & EXT_CONTROLLER))
  {
    ch_a_v = ch_a + MIXER_IC_CHANNEL_BASE;
    ch_a_s = (a->manufacturer_features & MANUFACTURER_FEATURE_SLAVE_CODEC) ?
      a->li_base + MIXER_IC_CHANNEL_BASE + (2 - plci->li_bchannel_id) : ch_a_v;
  }
  else
  {
    ch_a_v = ch_a;
    ch_a_s = ch_a;
  }
  ch_b = a_b->li_base + (plci_b->li_bchannel_id - 1);
  if (!a_b->li_pri && (plci_b->tel == ADV_VOICE)
   && (plci_b == a_b->AdvSignalPLCI) && (plci_b_id & EXT_CONTROLLER))
  {
    ch_b_v = ch_b + MIXER_IC_CHANNEL_BASE;
    ch_b_s = (a_b->manufacturer_features & MANUFACTURER_FEATURE_SLAVE_CODEC) ?
      a_b->li_base + MIXER_IC_CHANNEL_BASE + (2 - plci_b->li_bchannel_id) : ch_b_v;
  }
  else
  {
    ch_b_v = ch_b;
    ch_b_s = ch_b;
  }
  if (connect)
  {
    li_config_table[ch_b].flag_table[ch_b_v] &= ~LI_FLAG_MONITOR;
    li_config_table[ch_b].flag_table[ch_b_s] &= ~LI_FLAG_MONITOR;
    li_config_table[ch_b_v].flag_table[ch_b] &= ~LI_FLAG_MIX;
    li_config_table[ch_b_s].flag_table[ch_b] &= ~LI_FLAG_MIX;
    li_config_table[ch_b].flag_table[ch_b] &= ~LI_FLAG_PCCONNECT;
    li_config_table[ch_b].chflags &= ~(LI_CHFLAG_MONITOR | LI_CHFLAG_MIX | LI_CHFLAG_LOOP);
  }
  li_config_table[ch_b_v].flag_table[ch_a_v] &= ~(LI_FLAG_INTERCONNECT | LI_FLAG_CONFERENCE);
  li_config_table[ch_b_s].flag_table[ch_a_v] &= ~(LI_FLAG_INTERCONNECT | LI_FLAG_CONFERENCE);
  li_config_table[ch_b_v].flag_table[ch_a_s] &= ~(LI_FLAG_INTERCONNECT | LI_FLAG_CONFERENCE);
  li_config_table[ch_b_s].flag_table[ch_a_s] &= ~(LI_FLAG_INTERCONNECT | LI_FLAG_CONFERENCE);
  li_config_table[ch_a_v].flag_table[ch_b_v] &= ~(LI_FLAG_INTERCONNECT | LI_FLAG_CONFERENCE);
  li_config_table[ch_a_v].flag_table[ch_b_s] &= ~(LI_FLAG_INTERCONNECT | LI_FLAG_CONFERENCE);
  li_config_table[ch_a_s].flag_table[ch_b_v] &= ~(LI_FLAG_INTERCONNECT | LI_FLAG_CONFERENCE);
  li_config_table[ch_a_s].flag_table[ch_b_s] &= ~(LI_FLAG_INTERCONNECT | LI_FLAG_CONFERENCE);
  if (li_flags & LI2_FLAG_INTERCONNECT_A_B)
  {
    li_config_table[ch_b_v].flag_table[ch_a_v] |= LI_FLAG_INTERCONNECT;
    li_config_table[ch_b_s].flag_table[ch_a_v] |= LI_FLAG_INTERCONNECT;
    li_config_table[ch_b_v].flag_table[ch_a_s] |= LI_FLAG_INTERCONNECT;
    li_config_table[ch_b_s].flag_table[ch_a_s] |= LI_FLAG_INTERCONNECT;
  }
  if (li_flags & LI2_FLAG_INTERCONNECT_B_A)
  {
    li_config_table[ch_a_v].flag_table[ch_b_v] |= LI_FLAG_INTERCONNECT;
    li_config_table[ch_a_v].flag_table[ch_b_s] |= LI_FLAG_INTERCONNECT;
    li_config_table[ch_a_s].flag_table[ch_b_v] |= LI_FLAG_INTERCONNECT;
    li_config_table[ch_a_s].flag_table[ch_b_s] |= LI_FLAG_INTERCONNECT;
  }
  if (li_flags & LI2_FLAG_MONITOR_B)
  {
    li_config_table[ch_b].flag_table[ch_b_v] |= LI_FLAG_MONITOR;
    li_config_table[ch_b].flag_table[ch_b_s] |= LI_FLAG_MONITOR;
  }
  if (li_flags & LI2_FLAG_MIX_B)
  {
    li_config_table[ch_b_v].flag_table[ch_b] |= LI_FLAG_MIX;
    li_config_table[ch_b_s].flag_table[ch_b] |= LI_FLAG_MIX;
  }
  if (li_flags & LI2_FLAG_MONITOR_X)
    li_config_table[ch_b].chflags |= LI_CHFLAG_MONITOR;
  if (li_flags & LI2_FLAG_MIX_X)
    li_config_table[ch_b].chflags |= LI_CHFLAG_MIX;
  if (li_flags & LI2_FLAG_LOOP_B)
  {
    li_config_table[ch_b_v].flag_table[ch_b_v] |= LI_FLAG_INTERCONNECT;
    li_config_table[ch_b_s].flag_table[ch_b_v] |= LI_FLAG_INTERCONNECT;
    li_config_table[ch_b_v].flag_table[ch_b_s] |= LI_FLAG_INTERCONNECT;
    li_config_table[ch_b_s].flag_table[ch_b_s] |= LI_FLAG_INTERCONNECT;
  }
  if (li_flags & LI2_FLAG_LOOP_PC)
    li_config_table[ch_b].flag_table[ch_b] |= LI_FLAG_PCCONNECT;
  if (li_flags & LI2_FLAG_LOOP_X)
    li_config_table[ch_b].chflags |= LI_CHFLAG_LOOP;
  if (li_flags & LI2_FLAG_PCCONNECT_A_B)
    li_config_table[ch_b_s].flag_table[ch_a_s] |= LI_FLAG_PCCONNECT;
  if (li_flags & LI2_FLAG_PCCONNECT_B_A)
    li_config_table[ch_a_s].flag_table[ch_b_s] |= LI_FLAG_PCCONNECT;
  if (ch_a_v != ch_a_s)
  {
    li_config_table[ch_a_v].flag_table[ch_a_s] |= LI_FLAG_CONFERENCE;
    li_config_table[ch_a_s].flag_table[ch_a_v] |= LI_FLAG_CONFERENCE;
  }
  if (ch_b_v != ch_b_s)
  {
    li_config_table[ch_b_v].flag_table[ch_b_s] |= LI_FLAG_CONFERENCE;
    li_config_table[ch_b_s].flag_table[ch_b_v] |= LI_FLAG_CONFERENCE;
  }
}


static word li_check_main_plci (dword Id, PLCI   *plci)
{
  if (plci == NULL)
  {
    dbug (1, dprintf ("[%06lx] %s,%d: Wrong PLCI",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    return (_WRONG_IDENTIFIER);
  }
  if (!plci->State
   || !plci->NL.Id || plci->nl_remove_id
   || (plci->li_bchannel_id == 0))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: Wrong state",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    return (_WRONG_STATE);
  }
  li_config_table[plci->adapter->li_base + (plci->li_bchannel_id - 1)].plci = plci;
  return (GOOD);
}


static PLCI   *li_check_plci_b (dword Id, PLCI   *plci,
  dword plci_b_id, word plci_b_write_pos, byte   *p_result)
{
  byte ctlr_b;
  PLCI   *plci_b;

  if (((plci->li_plci_b_read_pos > plci_b_write_pos) ? plci->li_plci_b_read_pos :
    LI_PLCI_B_QUEUE_ENTRIES + plci->li_plci_b_read_pos) - plci_b_write_pos - 1 < 2)
  {
    dbug (1, dprintf ("[%06lx] %s,%d: LI request overrun",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    PUT_WORD (p_result, _REQUEST_NOT_ALLOWED_IN_THIS_STATE);
    return (NULL);
  }
  ctlr_b = 0;
  if ((plci_b_id & 0x7f) != 0)
  {
    ctlr_b = MapController ((byte)(plci_b_id & 0x7f));
    if ((ctlr_b > max_adapter) || ((ctlr_b != 0) && (adapter[ctlr_b - 1].request == NULL)))
      ctlr_b = 0;
  }
  if ((ctlr_b == 0)
   || (((plci_b_id >> 8) & 0xff) == 0)
   || (((plci_b_id >> 8) & 0xff) > adapter[ctlr_b - 1].max_plci))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: LI invalid second PLCI %08lx",
      UnMapId (Id), (char   *)(FILE_), __LINE__, plci_b_id));
    PUT_WORD (p_result, _WRONG_IDENTIFIER);
    return (NULL);
  }
  plci_b = &(adapter[ctlr_b - 1].plci[((plci_b_id >> 8) & 0xff) - 1]);
  if (!plci_b->State
   || !plci_b->NL.Id || plci_b->nl_remove_id
   || (plci_b->li_bchannel_id == 0))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: LI peer in wrong state %08lx",
      UnMapId (Id), (char   *)(FILE_), __LINE__, plci_b_id));
    PUT_WORD (p_result, _REQUEST_NOT_ALLOWED_IN_THIS_STATE);
    return (NULL);
  }
  li_config_table[plci_b->adapter->li_base + (plci_b->li_bchannel_id - 1)].plci = plci_b;
  if (((byte)(plci_b_id & ~EXT_CONTROLLER)) !=
    ((byte)(UnMapController (plci->adapter->Id) & ~EXT_CONTROLLER))
   && (!(plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)
    || !(plci_b->adapter->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: LI not on same ctrl %08lx",
      UnMapId (Id), (char   *)(FILE_), __LINE__, plci_b_id));
    PUT_WORD (p_result, _WRONG_IDENTIFIER);
    return (NULL);
  }
  if (!(get_b1_facilities (plci_b, add_b1_facilities (plci_b, plci_b->B1_resource,
    (word)(plci_b->B1_facilities | B1_FACILITY_MIXER))) & B1_FACILITY_MIXER))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: Interconnect peer cannot mix %d",
      UnMapId (Id), (char   *)(FILE_), __LINE__, plci_b->B1_resource));
    PUT_WORD (p_result, _REQUEST_NOT_ALLOWED_IN_THIS_STATE);
    return (NULL);
  }
  return (plci_b);
}


static PLCI   *li2_check_plci_b (dword Id, PLCI   *plci,
  dword plci_b_id, word plci_b_write_pos, byte   *p_result)
{
  byte ctlr_b;
  PLCI   *plci_b;

  if (((plci->li_plci_b_read_pos > plci_b_write_pos) ? plci->li_plci_b_read_pos :
    LI_PLCI_B_QUEUE_ENTRIES + plci->li_plci_b_read_pos) - plci_b_write_pos - 1 < 2)
  {
    dbug (1, dprintf ("[%06lx] %s,%d: LI request overrun",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    PUT_WORD (p_result, _WRONG_STATE);
    return (NULL);
  }
  ctlr_b = 0;
  if ((plci_b_id & 0x7f) != 0)
  {
    ctlr_b = MapController ((byte)(plci_b_id & 0x7f));
    if ((ctlr_b > max_adapter) || ((ctlr_b != 0) && (adapter[ctlr_b - 1].request == NULL)))
      ctlr_b = 0;
  }
  if ((ctlr_b == 0)
   || (((plci_b_id >> 8) & 0xff) == 0)
   || (((plci_b_id >> 8) & 0xff) > adapter[ctlr_b - 1].max_plci))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: LI invalid second PLCI %08lx",
      UnMapId (Id), (char   *)(FILE_), __LINE__, plci_b_id));
    PUT_WORD (p_result, _WRONG_IDENTIFIER);
    return (NULL);
  }
  plci_b = &(adapter[ctlr_b - 1].plci[((plci_b_id >> 8) & 0xff) - 1]);
  if (!plci_b->State
   || !plci_b->NL.Id || plci_b->nl_remove_id
   || (plci_b->li_bchannel_id == 0)
   || (li_config_table[plci_b->adapter->li_base + (plci_b->li_bchannel_id - 1)].plci != plci_b))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: LI peer in wrong state %08lx",
      UnMapId (Id), (char   *)(FILE_), __LINE__, plci_b_id));
    PUT_WORD (p_result, _WRONG_STATE);
    return (NULL);
  }
  if (((byte)(plci_b_id & ~EXT_CONTROLLER)) !=
    ((byte)(UnMapController (plci->adapter->Id) & ~EXT_CONTROLLER))
   && (!(plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)
    || !(plci_b->adapter->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: LI not on same ctrl %08lx",
      UnMapId (Id), (char   *)(FILE_), __LINE__, plci_b_id));
    PUT_WORD (p_result, _WRONG_IDENTIFIER);
    return (NULL);
  }
  if (!(get_b1_facilities (plci_b, add_b1_facilities (plci_b, plci_b->B1_resource,
    (word)(plci_b->B1_facilities | B1_FACILITY_MIXER))) & B1_FACILITY_MIXER))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: Interconnect peer cannot mix %d",
      UnMapId (Id), (char   *)(FILE_), __LINE__, plci_b->B1_resource));
    PUT_WORD (p_result, _WRONG_STATE);
    return (NULL);
  }
  return (plci_b);
}


static byte mixer_request (dword Id, word Number, DIVA_CAPI_ADAPTER   *a, PLCI   *plci, APPL   *appl, API_PARSE *msg)
{
  word Info;
  word i;
  dword d, li_flags, plci_b_id;
  PLCI   *plci_b;
    API_PARSE li_parms[3];
    API_PARSE li_req_parms[3];
    API_PARSE li_participant_struct[2];
    API_PARSE li_participant_parms[3];
  word participant_parms_pos;
  byte result_buffer[32];
  byte   *result;
  word result_pos;
  word plci_b_write_pos;

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_request",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  Info = GOOD;
  result = result_buffer;
  result_buffer[0] = 0;
  if (!(a->profile.Global_Options & GL_LINE_INTERCONNECT_SUPPORTED))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: Facility not supported",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    Info = _FACILITY_NOT_SUPPORTED;
  }
  else if (api_parse (&msg[1].info[1], msg[1].length, "ws", li_parms))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    Info = _WRONG_MESSAGE_FORMAT;
  }
  else
  {
    result_buffer[0] = 3;
    PUT_WORD (&result_buffer[1], GET_WORD (li_parms[0].info));
    result_buffer[3] = 0;
    switch (GET_WORD (li_parms[0].info))
    {
    case LI_GET_SUPPORTED_SERVICES:
      if (appl->appl_flags & APPL_FLAG_OLD_LI_SPEC)
      {
        result_buffer[0] = 17;
        result_buffer[3] = 14;
        PUT_WORD (&result_buffer[4], GOOD);
        d = 0;
        if (a->manufacturer_features & MANUFACTURER_FEATURE_MIXER_CH_CH)
          d |= LI_CONFERENCING_SUPPORTED;
        if (a->manufacturer_features & MANUFACTURER_FEATURE_MIXER_CH_PC)
          d |= LI_MONITORING_SUPPORTED;
        if (a->manufacturer_features & MANUFACTURER_FEATURE_MIXER_PC_CH)
          d |= LI_ANNOUNCEMENTS_SUPPORTED | LI_MIXING_SUPPORTED;
        if (a->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)
          d |= LI_CROSS_CONTROLLER_SUPPORTED;
        PUT_DWORD (&result_buffer[6], d);
        if (a->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)
        {
          d = 0;
          for (i = 0; i < li_total_channels; i++)
          {
            if ((li_config_table[i].adapter->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)
             && (li_config_table[i].adapter->li_pri
              || (i < li_config_table[i].adapter->li_base + MIXER_BCHANNELS_BRI)))
            {
              d++;
            }
          }
        }
        else
        {
          d = a->li_pri ? a->li_channels : MIXER_BCHANNELS_BRI;
        }
        PUT_DWORD (&result_buffer[10], d / 2);
        PUT_DWORD (&result_buffer[14], d);
      }
      else
      {
        result_buffer[0] = 25;
        result_buffer[3] = 22;
        PUT_WORD (&result_buffer[4], GOOD);
        d = LI2_ASYMMETRIC_SUPPORTED | LI2_B_LOOPING_SUPPORTED | LI2_X_LOOPING_SUPPORTED;
        if (a->manufacturer_features & MANUFACTURER_FEATURE_MIXER_CH_PC)
          d |= LI2_MONITORING_SUPPORTED | LI2_REMOTE_MONITORING_SUPPORTED;
        if (a->manufacturer_features & MANUFACTURER_FEATURE_MIXER_PC_CH)
          d |= LI2_MIXING_SUPPORTED | LI2_REMOTE_MIXING_SUPPORTED;
        if (a->manufacturer_features & MANUFACTURER_FEATURE_MIXER_PC_PC)
          d |= LI2_PC_LOOPING_SUPPORTED;
        if (a->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)
          d |= LI2_CROSS_CONTROLLER_SUPPORTED;
        PUT_DWORD (&result_buffer[6], d);
        d = a->li_pri ? a->li_channels : MIXER_BCHANNELS_BRI;
        PUT_DWORD (&result_buffer[10], d / 2);
        PUT_DWORD (&result_buffer[14], d - 1);
        if (a->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)
        {
          d = 0;
          for (i = 0; i < li_total_channels; i++)
          {
            if ((li_config_table[i].adapter->manufacturer_features & MANUFACTURER_FEATURE_XCONNECT)
             && (li_config_table[i].adapter->li_pri
              || (i < li_config_table[i].adapter->li_base + MIXER_BCHANNELS_BRI)))
            {
              d++;
            }
          }
        }
        PUT_DWORD (&result_buffer[18], d / 2);
        PUT_DWORD (&result_buffer[22], d - 1);
      }
      break;

    case LI_REQ_CONNECT:
      if (li_parms[1].length == 8)
      {
        appl->appl_flags |= APPL_FLAG_OLD_LI_SPEC;
        if (api_parse (&li_parms[1].info[1], li_parms[1].length, "dd", li_req_parms))
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _WRONG_MESSAGE_FORMAT;
          break;
        }
        plci_b_id = GET_DWORD (li_req_parms[0].info) & 0xffff;
        li_flags = GET_DWORD (li_req_parms[1].info);
        Info = li_check_main_plci (Id, plci);
        result_buffer[0] = 9;
        result_buffer[3] = 6;
        PUT_DWORD (&result_buffer[4], plci_b_id);
        PUT_WORD (&result_buffer[8], GOOD);
        if (Info != GOOD)
          break;
        result = plci->saved_msg.info;
        for (i = 0; i <= result_buffer[0]; i++)
          result[i] = result_buffer[i];
        plci_b_write_pos = plci->li_plci_b_write_pos;
        plci_b = li_check_plci_b (Id, plci, plci_b_id, plci_b_write_pos, &result[8]);
        if (plci_b == NULL)
          break;
        li_update_connect (Id, a, plci, plci_b_id, TRUE, li_flags);
        plci->li_plci_b_queue[plci_b_write_pos] = plci_b_id | LI_PLCI_B_LAST_FLAG;
        plci_b_write_pos = (plci_b_write_pos == LI_PLCI_B_QUEUE_ENTRIES-1) ? 0 : plci_b_write_pos + 1;
        plci->li_plci_b_write_pos = plci_b_write_pos;
      }
      else
      {
        appl->appl_flags &= ~APPL_FLAG_OLD_LI_SPEC;
        if (api_parse (&li_parms[1].info[1], li_parms[1].length, "ds", li_req_parms))
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _WRONG_MESSAGE_FORMAT;
          break;
        }
        li_flags = GET_DWORD (li_req_parms[0].info) & ~(LI2_FLAG_INTERCONNECT_A_B | LI2_FLAG_INTERCONNECT_B_A);
        Info = li_check_main_plci (Id, plci);
        result_buffer[0] = 7;
        result_buffer[3] = 4;
        PUT_WORD (&result_buffer[4], Info);
        result_buffer[6] = 0;
        if (Info != GOOD)
          break;
        result = plci->saved_msg.info;
        for (i = 0; i <= result_buffer[0]; i++)
          result[i] = result_buffer[i];
        plci_b_write_pos = plci->li_plci_b_write_pos;
        participant_parms_pos = 0;
        result_pos = 7;
        li2_update_connect (Id, a, plci, UnMapId (Id), TRUE, li_flags);
        while (participant_parms_pos < li_req_parms[1].length)
        {
          result[result_pos] = 6;
          result_pos += 7;
          PUT_DWORD (&result[result_pos - 6], 0);
          PUT_WORD (&result[result_pos - 2], GOOD);
          if (api_parse (&li_req_parms[1].info[1 + participant_parms_pos],
            (word)(li_parms[1].length - participant_parms_pos), "s", li_participant_struct))
          {
            dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
              UnMapId (Id), (char   *)(FILE_), __LINE__));
            PUT_WORD (&result[result_pos - 2], _WRONG_MESSAGE_FORMAT);
            break;
          }
          if (api_parse (&li_participant_struct[0].info[1],
            li_participant_struct[0].length, "dd", li_participant_parms))
          {
            dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
              UnMapId (Id), (char   *)(FILE_), __LINE__));
            PUT_WORD (&result[result_pos - 2], _WRONG_MESSAGE_FORMAT);
            break;
          }
          plci_b_id = GET_DWORD (li_participant_parms[0].info) & 0xffff;
          li_flags = GET_DWORD (li_participant_parms[1].info);
          PUT_DWORD (&result[result_pos - 6], plci_b_id);
          if (sizeof(result) - result_pos < 7)
          {
            dbug (1, dprintf ("[%06lx] %s,%d: LI result overrun",
              UnMapId (Id), (char   *)(FILE_), __LINE__));
            PUT_WORD (&result[result_pos - 2], _WRONG_STATE);
            break;
          }
          plci_b = li2_check_plci_b (Id, plci, plci_b_id, plci_b_write_pos, &result[result_pos - 2]);
          if (plci_b != NULL)
          {
            li2_update_connect (Id, a, plci, plci_b_id, TRUE, li_flags);
            plci->li_plci_b_queue[plci_b_write_pos] = plci_b_id |
              ((li_flags & (LI2_FLAG_INTERCONNECT_A_B | LI2_FLAG_INTERCONNECT_B_A |
              LI2_FLAG_PCCONNECT_A_B | LI2_FLAG_PCCONNECT_B_A)) ? 0 : LI_PLCI_B_DISC_FLAG);
            plci_b_write_pos = (plci_b_write_pos == LI_PLCI_B_QUEUE_ENTRIES-1) ? 0 : plci_b_write_pos + 1;
          }
          participant_parms_pos = (word)((&li_participant_struct[0].info[1 + li_participant_struct[0].length]) -
            (&li_req_parms[1].info[1]));
        }
        result[0] = (byte)(result_pos - 1);
        result[3] = (byte)(result_pos - 4);
        result[6] = (byte)(result_pos - 7);
        i = (plci_b_write_pos == 0) ? LI_PLCI_B_QUEUE_ENTRIES-1 : plci_b_write_pos - 1;
        if ((plci_b_write_pos == plci->li_plci_b_read_pos)
         || (plci->li_plci_b_queue[i] & LI_PLCI_B_LAST_FLAG))
        {
          plci->li_plci_b_queue[plci_b_write_pos] = LI_PLCI_B_SKIP_FLAG | LI_PLCI_B_LAST_FLAG;
          plci_b_write_pos = (plci_b_write_pos == LI_PLCI_B_QUEUE_ENTRIES-1) ? 0 : plci_b_write_pos + 1;
        }
        else
          plci->li_plci_b_queue[i] |= LI_PLCI_B_LAST_FLAG;
        plci->li_plci_b_write_pos = plci_b_write_pos;
      }
      mixer_calculate_coefs (a);
      plci->li_channel_bits = li_config_table[a->li_base + (plci->li_bchannel_id - 1)].channel;
      mixer_notify_update (plci, TRUE);
      sendf (appl, _FACILITY_R | CONFIRM, Id & 0xffffL, Number,
        "wwS", Info, SELECTOR_LINE_INTERCONNECT, result);
      plci->command = 0;
      plci->li_cmd = GET_WORD (li_parms[0].info);
      start_internal_command (Id, plci, mixer_command);
      return (FALSE);

    case LI_REQ_DISCONNECT:
      if (li_parms[1].length == 4)
      {
        appl->appl_flags |= APPL_FLAG_OLD_LI_SPEC;
        if (api_parse (&li_parms[1].info[1], li_parms[1].length, "d", li_req_parms))
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _WRONG_MESSAGE_FORMAT;
          break;
        }
        plci_b_id = GET_DWORD (li_req_parms[0].info) & 0xffff;
        Info = li_check_main_plci (Id, plci);
        result_buffer[0] = 9;
        result_buffer[3] = 6;
        PUT_DWORD (&result_buffer[4], GET_DWORD (li_req_parms[0].info));
        PUT_WORD (&result_buffer[8], GOOD);
        if (Info != GOOD)
          break;
        result = plci->saved_msg.info;
        for (i = 0; i <= result_buffer[0]; i++)
          result[i] = result_buffer[i];
        plci_b_write_pos = plci->li_plci_b_write_pos;
        plci_b = li_check_plci_b (Id, plci, plci_b_id, plci_b_write_pos, &result[8]);
        if (plci_b == NULL)
          break;
        li_update_connect (Id, a, plci, plci_b_id, FALSE, 0);
        plci->li_plci_b_queue[plci_b_write_pos] = plci_b_id | LI_PLCI_B_DISC_FLAG | LI_PLCI_B_LAST_FLAG;
        plci_b_write_pos = (plci_b_write_pos == LI_PLCI_B_QUEUE_ENTRIES-1) ? 0 : plci_b_write_pos + 1;
        plci->li_plci_b_write_pos = plci_b_write_pos;
      }
      else
      {
        appl->appl_flags &= ~APPL_FLAG_OLD_LI_SPEC;
        if (api_parse (&li_parms[1].info[1], li_parms[1].length, "s", li_req_parms))
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _WRONG_MESSAGE_FORMAT;
          break;
        }
        Info = li_check_main_plci (Id, plci);
        result_buffer[0] = 7;
        result_buffer[3] = 4;
        PUT_WORD (&result_buffer[4], Info);
        result_buffer[6] = 0;
        if (Info != GOOD)
          break;
        result = plci->saved_msg.info;
        for (i = 0; i <= result_buffer[0]; i++)
          result[i] = result_buffer[i];
        plci_b_write_pos = plci->li_plci_b_write_pos;
        participant_parms_pos = 0;
        result_pos = 7;
        while (participant_parms_pos < li_req_parms[0].length)
        {
          result[result_pos] = 6;
          result_pos += 7;
          PUT_DWORD (&result[result_pos - 6], 0);
          PUT_WORD (&result[result_pos - 2], GOOD);
          if (api_parse (&li_req_parms[0].info[1 + participant_parms_pos],
            (word)(li_parms[1].length - participant_parms_pos), "s", li_participant_struct))
          {
            dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
              UnMapId (Id), (char   *)(FILE_), __LINE__));
            PUT_WORD (&result[result_pos - 2], _WRONG_MESSAGE_FORMAT);
            break;
          }
          if (api_parse (&li_participant_struct[0].info[1],
            li_participant_struct[0].length, "d", li_participant_parms))
          {
            dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
              UnMapId (Id), (char   *)(FILE_), __LINE__));
            PUT_WORD (&result[result_pos - 2], _WRONG_MESSAGE_FORMAT);
            break;
          }
          plci_b_id = GET_DWORD (li_participant_parms[0].info) & 0xffff;
          PUT_DWORD (&result[result_pos - 6], plci_b_id);
          if (sizeof(result) - result_pos < 7)
          {
            dbug (1, dprintf ("[%06lx] %s,%d: LI result overrun",
              UnMapId (Id), (char   *)(FILE_), __LINE__));
            PUT_WORD (&result[result_pos - 2], _WRONG_STATE);
            break;
          }
          plci_b = li2_check_plci_b (Id, plci, plci_b_id, plci_b_write_pos, &result[result_pos - 2]);
          if (plci_b != NULL)
          {
            li2_update_connect (Id, a, plci, plci_b_id, FALSE, 0);
            plci->li_plci_b_queue[plci_b_write_pos] = plci_b_id | LI_PLCI_B_DISC_FLAG;
            plci_b_write_pos = (plci_b_write_pos == LI_PLCI_B_QUEUE_ENTRIES-1) ? 0 : plci_b_write_pos + 1;
          }
          participant_parms_pos = (word)((&li_participant_struct[0].info[1 + li_participant_struct[0].length]) -
            (&li_req_parms[0].info[1]));
        }
        result[0] = (byte)(result_pos - 1);
        result[3] = (byte)(result_pos - 4);
        result[6] = (byte)(result_pos - 7);
        i = (plci_b_write_pos == 0) ? LI_PLCI_B_QUEUE_ENTRIES-1 : plci_b_write_pos - 1;
        if ((plci_b_write_pos == plci->li_plci_b_read_pos)
         || (plci->li_plci_b_queue[i] & LI_PLCI_B_LAST_FLAG))
        {
          plci->li_plci_b_queue[plci_b_write_pos] = LI_PLCI_B_SKIP_FLAG | LI_PLCI_B_LAST_FLAG;
          plci_b_write_pos = (plci_b_write_pos == LI_PLCI_B_QUEUE_ENTRIES-1) ? 0 : plci_b_write_pos + 1;
        }
        else
          plci->li_plci_b_queue[i] |= LI_PLCI_B_LAST_FLAG;
        plci->li_plci_b_write_pos = plci_b_write_pos;
      }
      mixer_calculate_coefs (a);
      plci->li_channel_bits = li_config_table[a->li_base + (plci->li_bchannel_id - 1)].channel;
      mixer_notify_update (plci, TRUE);
      sendf (appl, _FACILITY_R | CONFIRM, Id & 0xffffL, Number,
        "wwS", Info, SELECTOR_LINE_INTERCONNECT, result);
      plci->command = 0;
      plci->li_cmd = GET_WORD (li_parms[0].info);
      start_internal_command (Id, plci, mixer_command);
      return (FALSE);

    case LI_REQ_SILENT_UPDATE:
      if (!plci || !plci->State
       || !plci->NL.Id || plci->nl_remove_id
       || (plci->li_bchannel_id == 0)
       || (li_config_table[plci->adapter->li_base + (plci->li_bchannel_id - 1)].plci != plci))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Wrong state",
          UnMapId (Id), (char   *)(FILE_), __LINE__));
        return (FALSE);
      }
      plci_b_write_pos = plci->li_plci_b_write_pos;
      if (((plci->li_plci_b_read_pos > plci_b_write_pos) ? plci->li_plci_b_read_pos :
        LI_PLCI_B_QUEUE_ENTRIES + plci->li_plci_b_read_pos) - plci_b_write_pos - 1 < 2)
      {
        dbug (1, dprintf ("[%06lx] %s,%d: LI request overrun",
          UnMapId (Id), (char   *)(FILE_), __LINE__));
        return (FALSE);
      }
      i = (plci_b_write_pos == 0) ? LI_PLCI_B_QUEUE_ENTRIES-1 : plci_b_write_pos - 1;
      if ((plci_b_write_pos == plci->li_plci_b_read_pos)
       || (plci->li_plci_b_queue[i] & LI_PLCI_B_LAST_FLAG))
      {
        plci->li_plci_b_queue[plci_b_write_pos] = LI_PLCI_B_SKIP_FLAG | LI_PLCI_B_LAST_FLAG;
        plci_b_write_pos = (plci_b_write_pos == LI_PLCI_B_QUEUE_ENTRIES-1) ? 0 : plci_b_write_pos + 1;
      }
      else
        plci->li_plci_b_queue[i] |= LI_PLCI_B_LAST_FLAG;
      plci->li_plci_b_write_pos = plci_b_write_pos;
      plci->li_channel_bits = li_config_table[a->li_base + (plci->li_bchannel_id - 1)].channel;
      plci->command = 0;
      plci->li_cmd = GET_WORD (li_parms[0].info);
      start_internal_command (Id, plci, mixer_command);
      return (FALSE);

    default:
      dbug (1, dprintf ("[%06lx] %s,%d: LI unknown request %04x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, GET_WORD (li_parms[0].info)));
      Info = _FACILITY_NOT_SUPPORTED;
    }
  }
  sendf (appl, _FACILITY_R | CONFIRM, Id & 0xffffL, Number,
    "wwS", Info, SELECTOR_LINE_INTERCONNECT, result);
  return (FALSE);
}


static void mixer_indication_coefs_set (dword Id, PLCI   *plci)
{
  dword d;
  DIVA_CAPI_ADAPTER   *a;
    byte result[12];

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_indication_coefs_set",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  a = plci->adapter;
  if (plci->li_plci_b_read_pos != plci->li_plci_b_req_pos)
  {
    do
    {
      d = plci->li_plci_b_queue[plci->li_plci_b_read_pos];
      if (!(d & LI_PLCI_B_SKIP_FLAG))
      {
        if (plci->appl->appl_flags & APPL_FLAG_OLD_LI_SPEC)
        {
          if (d & LI_PLCI_B_DISC_FLAG)
          {
            result[0] = 5;
            PUT_WORD (&result[1], LI_IND_DISCONNECT);
            result[3] = 2;
            PUT_WORD (&result[4], _LI_USER_INITIATED);
          }
          else
          {
            result[0] = 7;
            PUT_WORD (&result[1], LI_IND_CONNECT_ACTIVE);
            result[3] = 4;
            PUT_DWORD (&result[4], d & ~LI_PLCI_B_FLAG_MASK);
          }
        }
        else
        {
          if (d & LI_PLCI_B_DISC_FLAG)
          {
            result[0] = 9;
            PUT_WORD (&result[1], LI_IND_DISCONNECT);
            result[3] = 6;
            PUT_DWORD (&result[4], d & ~LI_PLCI_B_FLAG_MASK);
            PUT_WORD (&result[8], _LI_USER_INITIATED);
          }
          else
          {
            result[0] = 7;
            PUT_WORD (&result[1], LI_IND_CONNECT_ACTIVE);
            result[3] = 4;
            PUT_DWORD (&result[4], d & ~LI_PLCI_B_FLAG_MASK);
          }
        }
        sendf (plci->appl, _FACILITY_I, Id & 0xffffL, 0,
          "ws", SELECTOR_LINE_INTERCONNECT, result);
      }
      plci->li_plci_b_read_pos = (plci->li_plci_b_read_pos == LI_PLCI_B_QUEUE_ENTRIES-1) ?
        0 : plci->li_plci_b_read_pos + 1;
    } while (!(d & LI_PLCI_B_LAST_FLAG) && (plci->li_plci_b_read_pos != plci->li_plci_b_req_pos));
  }
}


static void mixer_indication_xconnect_from (dword Id, PLCI   *plci, byte   *msg, word length)
{
  word i, j, ch;
  struct xconnect_transfer_address_s s,   *p;
  DIVA_CAPI_ADAPTER   *a;

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_indication_xconnect_from %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, (int) length));

  a = plci->adapter;
  i = 1;
  for (i = 1; i < length; i += 16)
  {
    s.card_address.low = msg[i] | (msg[i+1] << 8) | (((dword)(msg[i+2])) << 16) | (((dword)(msg[i+3])) << 24);
    s.card_address.high = msg[i+4] | (msg[i+5] << 8) | (((dword)(msg[i+6])) << 16) | (((dword)(msg[i+7])) << 24);
    s.offset = msg[i+8] | (msg[i+9] << 8) | (((dword)(msg[i+10])) << 16) | (((dword)(msg[i+11])) << 24);
    ch = msg[i+12] | (msg[i+13] << 8);
    j = ch & XCONNECT_CHANNEL_NUMBER_MASK;
    if (!a->li_pri && (plci->li_bchannel_id == 2))
      j = 1 - j;
    j += a->li_base;
    if (ch & XCONNECT_CHANNEL_PORT_PC)
      p = &(li_config_table[j].send_pc);
    else
      p = &(li_config_table[j].send_b);
    p->card_address.low = s.card_address.low;
    p->card_address.high = s.card_address.high;
    p->offset = s.offset;
    li_config_table[j].channel |= LI_CHANNEL_ADDRESSES_SET;
  }
  if (plci->internal_command_queue[0]
   && ((plci->adjust_b_state == ADJUST_B_RESTORE_MIXER_2)
    || (plci->adjust_b_state == ADJUST_B_RESTORE_MIXER_3)
    || (plci->adjust_b_state == ADJUST_B_RESTORE_MIXER_4)))
  {
    (*(plci->internal_command_queue[0]))(Id, plci, 0);
    if (!plci->internal_command)
      next_internal_command (Id, plci);
  }
  mixer_notify_update (plci, TRUE);
}


static void mixer_indication_xconnect_to (dword Id, PLCI   *plci, byte   *msg, word length)
{

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_indication_xconnect_to %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, (int) length));

}


static byte mixer_notify_source_removed (PLCI   *plci, dword plci_b_id)
{
  word plci_b_write_pos;

  plci_b_write_pos = plci->li_plci_b_write_pos;
  if (((plci->li_plci_b_read_pos > plci_b_write_pos) ? plci->li_plci_b_read_pos :
    LI_PLCI_B_QUEUE_ENTRIES + plci->li_plci_b_read_pos) - plci_b_write_pos - 1 < 1)
  {
    dbug (1, dprintf ("[%06lx] %s,%d: LI request overrun",
      (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
      (char   *)(FILE_), __LINE__));
    return (FALSE);
  }
  plci->li_plci_b_queue[plci_b_write_pos] = plci_b_id | LI_PLCI_B_DISC_FLAG;
  plci_b_write_pos = (plci_b_write_pos == LI_PLCI_B_QUEUE_ENTRIES-1) ? 0 : plci_b_write_pos + 1;
  plci->li_plci_b_write_pos = plci_b_write_pos;
  return (TRUE);
}


static void mixer_remove (PLCI   *plci)
{
  DIVA_CAPI_ADAPTER   *a;
  PLCI   *notify_plci;
  dword plci_b_id;
  word i, j;

  dbug (1, dprintf ("[%06lx] %s,%d: mixer_remove",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  a = plci->adapter;
  plci_b_id = (plci->Id << 8) | UnMapController (plci->adapter->Id);
  if (a->profile.Global_Options & GL_LINE_INTERCONNECT_SUPPORTED)
  {
    if ((plci->li_bchannel_id != 0)
     && (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == plci))
    {
      i = a->li_base + (plci->li_bchannel_id - 1);
      if ((li_config_table[i].curchnl | li_config_table[i].channel) & LI_CHANNEL_INVOLVED)
      {
        for (j = 0; j < li_total_channels; j++)
        {
          if ((li_config_table[i].flag_table[j] & LI_FLAG_INTERCONNECT)
           || (li_config_table[j].flag_table[i] & LI_FLAG_INTERCONNECT))
          {
            notify_plci = li_config_table[j].plci;
            if ((notify_plci != NULL)
             && (notify_plci != plci)
             && (notify_plci->appl != NULL)
             && !(notify_plci->appl->appl_flags & APPL_FLAG_OLD_LI_SPEC)
             && (notify_plci->State)
             && notify_plci->NL.Id && !notify_plci->nl_remove_id)
            {
              mixer_notify_source_removed (notify_plci, plci_b_id);
            }
          }
        }
        mixer_clear_config (plci);
        mixer_calculate_coefs (a);
        mixer_notify_update (plci, TRUE);
      }
      li_config_table[i].plci = NULL;
      plci->li_bchannel_id = 0;
    }
  }
}


/*------------------------------------------------------------------*/
/* Echo canceller facilities                                        */
/*------------------------------------------------------------------*/


static void ec_write_parameters (PLCI   *plci)
{
  word w;
    byte parameter_buffer[6];

  dbug (1, dprintf ("[%06lx] %s,%d: ec_write_parameters",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  parameter_buffer[0] = 5;
  parameter_buffer[1] = DSP_CTRL_SET_LEC_PARAMETERS;
  PUT_WORD (&parameter_buffer[2], plci->ec_idi_options);
  plci->ec_idi_options &= ~LEC_RESET_COEFFICIENTS;
  w = (plci->ec_tail_length == 0) ? 128 : plci->ec_tail_length;
  PUT_WORD (&parameter_buffer[4], w);
  add_p (plci, FTY, parameter_buffer);
  sig_req (plci, TEL_CTRL, 0);
  send_req (plci);
}


static void ec_clear_config (PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: ec_clear_config",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  plci->ec_idi_options = LEC_ENABLE_ECHO_CANCELLER |
    LEC_MANUAL_DISABLE | LEC_ENABLE_NONLINEAR_PROCESSING;
  plci->ec_tail_length = 0;
}


static void ec_prepare_switch (dword Id, PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: ec_prepare_switch",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

}


static word ec_save_config (dword Id, PLCI   *plci, byte Rc)
{

  dbug (1, dprintf ("[%06lx] %s,%d: ec_save_config %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  return (GOOD);
}


static word ec_restore_config (dword Id, PLCI   *plci, byte Rc)
{
  word Info;

  dbug (1, dprintf ("[%06lx] %s,%d: ec_restore_config %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  Info = GOOD;
  if (plci->B1_facilities & B1_FACILITY_EC)
  {
    switch (plci->adjust_b_state)
    {
    case ADJUST_B_RESTORE_EC_1:
      plci->internal_command = plci->adjust_b_command;
      if (plci->sig_req)
      {
        plci->adjust_b_state = ADJUST_B_RESTORE_EC_1;
        break;
      }
      ec_write_parameters (plci);
      plci->adjust_b_state = ADJUST_B_RESTORE_EC_2;
      break;
    case ADJUST_B_RESTORE_EC_2:
      if ((Rc != OK) && (Rc != OK_FC))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Restore EC failed %02x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
        Info = _WRONG_STATE;
        break;
      }
      break;
    }
  }
  return (Info);
}


static void ec_command (dword Id, PLCI   *plci, byte Rc)
{
  word internal_command, Info;
    byte result[8];

  dbug (1, dprintf ("[%06lx] %s,%d: ec_command %02x %04x %04x %04x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command,
    plci->ec_cmd, plci->ec_idi_options, plci->ec_tail_length));

  Info = GOOD;
  if (plci->appl->appl_flags & APPL_FLAG_PRIV_EC_SPEC)
  {
    result[0] = 2;
    PUT_WORD (&result[1], EC_SUCCESS);
  }
  else
  {
    result[0] = 5;
    PUT_WORD (&result[1], plci->ec_cmd);
    result[3] = 2;
    PUT_WORD (&result[4], GOOD);
  }
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (plci->ec_cmd)
  {
  case EC_ENABLE_OPERATION:
  case EC_FREEZE_COEFFICIENTS:
  case EC_RESUME_COEFFICIENT_UPDATE:
  case EC_RESET_COEFFICIENTS:
    switch (internal_command)
    {
    default:
      adjust_b1_resource (Id, plci, NULL, (word)(plci->B1_facilities |
        B1_FACILITY_EC), EC_COMMAND_1);
    case EC_COMMAND_1:
      if (adjust_b_process (Id, plci, Rc) != GOOD)
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Load EC failed",
          UnMapId (Id), (char   *)(FILE_), __LINE__));
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
      if (plci->internal_command)
        return;
    case EC_COMMAND_2:
      if (plci->sig_req)
      {
        plci->internal_command = EC_COMMAND_2;
        return;
      }
      plci->internal_command = EC_COMMAND_3;
      ec_write_parameters (plci);
      return;
    case EC_COMMAND_3:
      if ((Rc != OK) && (Rc != OK_FC))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Enable EC failed %02x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
      break;
    }
    break;

  case EC_DISABLE_OPERATION:
    switch (internal_command)
    {
    default:
    case EC_COMMAND_1:
      if (plci->B1_facilities & B1_FACILITY_EC)
      {
        if (plci->sig_req)
        {
          plci->internal_command = EC_COMMAND_1;
          return;
        }
        plci->internal_command = EC_COMMAND_2;
        ec_write_parameters (plci);
        return;
      }
      Rc = OK;
    case EC_COMMAND_2:
      if ((Rc != OK) && (Rc != OK_FC))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Disable EC failed %02x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
      adjust_b1_resource (Id, plci, NULL, (word)(plci->B1_facilities &
        ~B1_FACILITY_EC), EC_COMMAND_3);
    case EC_COMMAND_3:
      if (adjust_b_process (Id, plci, Rc) != GOOD)
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Unload EC failed",
          UnMapId (Id), (char   *)(FILE_), __LINE__));
        Info = _FACILITY_NOT_SUPPORTED;
        break;
      }
      if (plci->internal_command)
        return;
      break;
    }
    break;
  }
  sendf (plci->appl, _FACILITY_R | CONFIRM, Id & 0xffffL, plci->number,
    "wws", Info, (plci->appl->appl_flags & APPL_FLAG_PRIV_EC_SPEC) ?
    PRIV_SELECTOR_ECHO_CANCELLER : SELECTOR_ECHO_CANCELLER, result);
}


static byte ec_request (dword Id, word Number, DIVA_CAPI_ADAPTER   *a, PLCI   *plci, APPL   *appl, API_PARSE *msg)
{
  word Info;
  word opt;
    API_PARSE ec_parms[3];
    byte result[16];

  dbug (1, dprintf ("[%06lx] %s,%d: ec_request",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  Info = GOOD;
  result[0] = 0;
  if (!(a->man_profile.private_options & (1L << PRIVATE_ECHO_CANCELLER)))
  {
    dbug (1, dprintf ("[%06lx] %s,%d: Facility not supported",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
    Info = _FACILITY_NOT_SUPPORTED;
  }
  else
  {
    if (appl->appl_flags & APPL_FLAG_PRIV_EC_SPEC)
    {
      if (api_parse (&msg[1].info[1], msg[1].length, "w", ec_parms))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
          UnMapId (Id), (char   *)(FILE_), __LINE__));
        Info = _WRONG_MESSAGE_FORMAT;
      }
      else
      {
        if (plci == NULL)
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Wrong PLCI",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _WRONG_IDENTIFIER;
        }
        else if (!plci->State || !plci->NL.Id || plci->nl_remove_id)
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Wrong state",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _WRONG_STATE;
        }
        else
        {
          plci->command = 0;
          plci->ec_cmd = GET_WORD (ec_parms[0].info);
          plci->ec_idi_options &= ~(LEC_MANUAL_DISABLE | LEC_RESET_COEFFICIENTS);
          result[0] = 2;
          PUT_WORD (&result[1], EC_SUCCESS);
          if (msg[1].length >= 4)
          {
            opt = GET_WORD (&ec_parms[0].info[2]);
            plci->ec_idi_options &= ~(LEC_ENABLE_NONLINEAR_PROCESSING |
              LEC_ENABLE_2100HZ_DETECTOR | LEC_REQUIRE_2100HZ_REVERSALS);
            if (!(opt & EC_DISABLE_NON_LINEAR_PROCESSING))
              plci->ec_idi_options |= LEC_ENABLE_NONLINEAR_PROCESSING;
            if (opt & EC_DETECT_DISABLE_TONE)
              plci->ec_idi_options |= LEC_ENABLE_2100HZ_DETECTOR;
            if (!(opt & EC_DO_NOT_REQUIRE_REVERSALS))
              plci->ec_idi_options |= LEC_REQUIRE_2100HZ_REVERSALS;
            if (msg[1].length >= 6)
            {
              plci->ec_tail_length = GET_WORD (&ec_parms[0].info[4]);
            }
          }
          switch (plci->ec_cmd)
          {
          case EC_ENABLE_OPERATION:
            plci->ec_idi_options &= ~LEC_FREEZE_COEFFICIENTS;
            start_internal_command (Id, plci, ec_command);
            return (FALSE);

          case EC_DISABLE_OPERATION:
            plci->ec_idi_options = LEC_ENABLE_ECHO_CANCELLER |
              LEC_MANUAL_DISABLE | LEC_ENABLE_NONLINEAR_PROCESSING |
              LEC_RESET_COEFFICIENTS;
            start_internal_command (Id, plci, ec_command);
            return (FALSE);

          case EC_FREEZE_COEFFICIENTS:
            plci->ec_idi_options |= LEC_FREEZE_COEFFICIENTS;
            start_internal_command (Id, plci, ec_command);
            return (FALSE);

          case EC_RESUME_COEFFICIENT_UPDATE:
            plci->ec_idi_options &= ~LEC_FREEZE_COEFFICIENTS;
            start_internal_command (Id, plci, ec_command);
            return (FALSE);

          case EC_RESET_COEFFICIENTS:
            plci->ec_idi_options |= LEC_RESET_COEFFICIENTS;
            start_internal_command (Id, plci, ec_command);
            return (FALSE);

          default:
            dbug (1, dprintf ("[%06lx] %s,%d: EC unknown request %04x",
              UnMapId (Id), (char   *)(FILE_), __LINE__, plci->ec_cmd));
            PUT_WORD (&result[1], EC_UNSUPPORTED_OPERATION);
          }
        }
      }
    }
    else
    {
      if (api_parse (&msg[1].info[1], msg[1].length, "ws", ec_parms))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Wrong message format",
          UnMapId (Id), (char   *)(FILE_), __LINE__));
        Info = _WRONG_MESSAGE_FORMAT;
      }
      else
      {
        if (GET_WORD (ec_parms[0].info) == EC_GET_SUPPORTED_SERVICES)
        {
          result[0] = 11;
          PUT_WORD (&result[1], EC_GET_SUPPORTED_SERVICES);
          result[3] = 8;
          PUT_WORD (&result[4], GOOD);
          PUT_WORD (&result[6], 0x0007);
          PUT_WORD (&result[8], LEC_MAX_SUPPORTED_TAIL_LENGTH);
          PUT_WORD (&result[10], 0);
        }
        else if (plci == NULL)
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Wrong PLCI",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _WRONG_IDENTIFIER;
        }
        else if (!plci->State || !plci->NL.Id || plci->nl_remove_id)
        {
          dbug (1, dprintf ("[%06lx] %s,%d: Wrong state",
            UnMapId (Id), (char   *)(FILE_), __LINE__));
          Info = _WRONG_STATE;
        }
        else
        {
          plci->command = 0;
          plci->ec_cmd = GET_WORD (ec_parms[0].info);
          plci->ec_idi_options &= ~(LEC_MANUAL_DISABLE | LEC_RESET_COEFFICIENTS);
          result[0] = 5;
          PUT_WORD (&result[1], plci->ec_cmd);
          result[3] = 2;
          PUT_WORD (&result[4], GOOD);
          plci->ec_idi_options &= ~(LEC_ENABLE_NONLINEAR_PROCESSING |
            LEC_ENABLE_2100HZ_DETECTOR | LEC_REQUIRE_2100HZ_REVERSALS);
          plci->ec_tail_length = 0;
          if (ec_parms[1].length >= 2)
          {
            opt = GET_WORD (&ec_parms[1].info[1]);
            if (opt & EC_ENABLE_NON_LINEAR_PROCESSING)
              plci->ec_idi_options |= LEC_ENABLE_NONLINEAR_PROCESSING;
            if (opt & EC_DETECT_DISABLE_TONE)
              plci->ec_idi_options |= LEC_ENABLE_2100HZ_DETECTOR;
            if (!(opt & EC_DO_NOT_REQUIRE_REVERSALS))
              plci->ec_idi_options |= LEC_REQUIRE_2100HZ_REVERSALS;
            if (ec_parms[1].length >= 4)
            {
              plci->ec_tail_length = GET_WORD (&ec_parms[1].info[3]);
            }
          }
          switch (plci->ec_cmd)
          {
          case EC_ENABLE_OPERATION:
            plci->ec_idi_options &= ~LEC_FREEZE_COEFFICIENTS;
            start_internal_command (Id, plci, ec_command);
            return (FALSE);

          case EC_DISABLE_OPERATION:
            plci->ec_idi_options = LEC_ENABLE_ECHO_CANCELLER |
              LEC_MANUAL_DISABLE | LEC_ENABLE_NONLINEAR_PROCESSING |
              LEC_RESET_COEFFICIENTS;
            start_internal_command (Id, plci, ec_command);
            return (FALSE);

          default:
            dbug (1, dprintf ("[%06lx] %s,%d: EC unknown request %04x",
              UnMapId (Id), (char   *)(FILE_), __LINE__, plci->ec_cmd));
            PUT_WORD (&result[4], _FACILITY_SPECIFIC_FUNCTION_NOT_SUPP);
          }
        }
      }
    }
  }
  sendf (appl, _FACILITY_R | CONFIRM, Id & 0xffffL, Number,
    "wws", Info, (appl->appl_flags & APPL_FLAG_PRIV_EC_SPEC) ?
    PRIV_SELECTOR_ECHO_CANCELLER : SELECTOR_ECHO_CANCELLER, result);
  return (FALSE);
}


static void ec_indication (dword Id, PLCI   *plci, byte   *msg, word length)
{
    byte result[8];

  dbug (1, dprintf ("[%06lx] %s,%d: ec_indication",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

  if (!(plci->ec_idi_options & LEC_MANUAL_DISABLE))
  {
    if (plci->appl->appl_flags & APPL_FLAG_PRIV_EC_SPEC)
    {
      result[0] = 2;
      PUT_WORD (&result[1], 0);
      switch (msg[1])
      {
      case LEC_DISABLE_TYPE_CONTIGNUOUS_2100HZ:
        PUT_WORD (&result[1], EC_BYPASS_DUE_TO_CONTINUOUS_2100HZ);
        break;
      case LEC_DISABLE_TYPE_REVERSED_2100HZ:
        PUT_WORD (&result[1], EC_BYPASS_DUE_TO_REVERSED_2100HZ);
        break;
      case LEC_DISABLE_RELEASED:
        PUT_WORD (&result[1], EC_BYPASS_RELEASED);
        break;
      }
    }
    else
    {
      result[0] = 5;
      PUT_WORD (&result[1], EC_BYPASS_INDICATION);
      result[3] = 2;
      PUT_WORD (&result[4], 0);
      switch (msg[1])
      {
      case LEC_DISABLE_TYPE_CONTIGNUOUS_2100HZ:
        PUT_WORD (&result[4], EC_BYPASS_DUE_TO_CONTINUOUS_2100HZ);
        break;
      case LEC_DISABLE_TYPE_REVERSED_2100HZ:
        PUT_WORD (&result[4], EC_BYPASS_DUE_TO_REVERSED_2100HZ);
        break;
      case LEC_DISABLE_RELEASED:
        PUT_WORD (&result[4], EC_BYPASS_RELEASED);
        break;
      }
    }
    sendf (plci->appl, _FACILITY_I, Id & 0xffffL, 0, "ws", (plci->appl->appl_flags & APPL_FLAG_PRIV_EC_SPEC) ?
      PRIV_SELECTOR_ECHO_CANCELLER : SELECTOR_ECHO_CANCELLER, result);
  }
}



/*------------------------------------------------------------------*/
/* Advanced voice                                                   */
/*------------------------------------------------------------------*/

static void adv_voice_write_coefs (PLCI   *plci, word write_command)
{
  DIVA_CAPI_ADAPTER   *a;
  word i;
  byte *p;

  word w, n, j, k;
  byte ch_map[MIXER_CHANNELS_BRI];

    byte coef_buffer[ADV_VOICE_COEF_BUFFER_SIZE + 2];

  dbug (1, dprintf ("[%06lx] %s,%d: adv_voice_write_coefs %d",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__, write_command));

  a = plci->adapter;
  p = coef_buffer + 1;
  *(p++) = DSP_CTRL_OLD_SET_MIXER_COEFFICIENTS;
  i = 0;
  while (i + sizeof(word) <= a->adv_voice_coef_length)
  {
    PUT_WORD (p, GET_WORD (a->adv_voice_coef_buffer + i));
    p += 2;
    i += 2;
  }
  while (i < ADV_VOICE_OLD_COEF_COUNT * sizeof(word))
  {
    PUT_WORD (p, 0x8000);
    p += 2;
    i += 2;
  }

  if (!a->li_pri && (plci->li_bchannel_id == 0))
  {
    if ((li_config_table[a->li_base].plci == NULL) && (li_config_table[a->li_base + 1].plci != NULL))
    {
      plci->li_bchannel_id = 1;
      li_config_table[a->li_base].plci = plci;
      dbug (1, dprintf ("[%06lx] %s,%d: adv_voice_set_bchannel_id %d",
        (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
        (char   *)(FILE_), __LINE__, plci->li_bchannel_id));
    }
    else if ((li_config_table[a->li_base].plci != NULL) && (li_config_table[a->li_base + 1].plci == NULL))
    {
      plci->li_bchannel_id = 2;
      li_config_table[a->li_base + 1].plci = plci;
      dbug (1, dprintf ("[%06lx] %s,%d: adv_voice_set_bchannel_id %d",
        (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
        (char   *)(FILE_), __LINE__, plci->li_bchannel_id));
    }
  }
  if (!a->li_pri && (plci->li_bchannel_id != 0)
   && (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == plci))
  {
    i = a->li_base + (plci->li_bchannel_id - 1);
    switch (write_command)
    {
    case ADV_VOICE_WRITE_ACTIVATION:
      j = a->li_base + MIXER_IC_CHANNEL_BASE + (plci->li_bchannel_id - 1);
      k = a->li_base + MIXER_IC_CHANNEL_BASE + (2 - plci->li_bchannel_id);
      if (!(plci->B1_facilities & B1_FACILITY_MIXER))
      {
        li_config_table[j].flag_table[i] |= LI_FLAG_CONFERENCE | LI_FLAG_MIX;
        li_config_table[i].flag_table[j] |= LI_FLAG_CONFERENCE | LI_FLAG_MONITOR;
      }
      if (a->manufacturer_features & MANUFACTURER_FEATURE_SLAVE_CODEC)
      {
        li_config_table[k].flag_table[i] |= LI_FLAG_CONFERENCE | LI_FLAG_MIX;
        li_config_table[i].flag_table[k] |= LI_FLAG_CONFERENCE | LI_FLAG_MONITOR;
        li_config_table[k].flag_table[j] |= LI_FLAG_CONFERENCE;
        li_config_table[j].flag_table[k] |= LI_FLAG_CONFERENCE;
      }
      mixer_calculate_coefs (a);
      li_config_table[i].curchnl = li_config_table[i].channel;
      li_config_table[j].curchnl = li_config_table[j].channel;
      if (a->manufacturer_features & MANUFACTURER_FEATURE_SLAVE_CODEC)
        li_config_table[k].curchnl = li_config_table[k].channel;
      break;

    case ADV_VOICE_WRITE_DEACTIVATION:
      for (j = 0; j < li_total_channels; j++)
      {
        li_config_table[i].flag_table[j] = 0;
        li_config_table[j].flag_table[i] = 0;
      }
      k = a->li_base + MIXER_IC_CHANNEL_BASE + (plci->li_bchannel_id - 1);
      for (j = 0; j < li_total_channels; j++)
      {
        li_config_table[k].flag_table[j] = 0;
        li_config_table[j].flag_table[k] = 0;
      }
      if (a->manufacturer_features & MANUFACTURER_FEATURE_SLAVE_CODEC)
      {
        k = a->li_base + MIXER_IC_CHANNEL_BASE + (2 - plci->li_bchannel_id);
        for (j = 0; j < li_total_channels; j++)
        {
          li_config_table[k].flag_table[j] = 0;
          li_config_table[j].flag_table[k] = 0;
        }
      }
      mixer_calculate_coefs (a);
      break;
    }
    if (plci->B1_facilities & B1_FACILITY_MIXER)
    {
      w = 0;
      if (ADV_VOICE_NEW_COEF_BASE + sizeof(word) <= a->adv_voice_coef_length)
        w = GET_WORD (a->adv_voice_coef_buffer + ADV_VOICE_NEW_COEF_BASE);
      if (li_config_table[i].channel & LI_CHANNEL_TX_DATA)
        w |= MIXER_FEATURE_ENABLE_TX_DATA;
      if (li_config_table[i].channel & LI_CHANNEL_RX_DATA)
        w |= MIXER_FEATURE_ENABLE_RX_DATA;
      *(p++) = (byte) w;
      *(p++) = (byte)(w >> 8);
      for (j = 0; j < sizeof(ch_map); j += 2)
      {
        ch_map[j] = (byte)(j + (plci->li_bchannel_id - 1));
        ch_map[j+1] = (byte)(j + (2 - plci->li_bchannel_id));
      }
      for (n = 0; n < sizeof(mixer_write_prog_bri) / sizeof(mixer_write_prog_bri[0]); n++)
      {
        i = a->li_base + ch_map[mixer_write_prog_bri[n].to_ch];
        j = a->li_base + ch_map[mixer_write_prog_bri[n].from_ch];
        if (li_config_table[i].channel & li_config_table[j].channel & LI_CHANNEL_INVOLVED)
        {
          *(p++) = ((li_config_table[i].coef_table[j] & mixer_write_prog_bri[n].mask) ? 0x80 : 0x01);
          w = ((li_config_table[i].coef_table[j] & 0xf) ^ (li_config_table[i].coef_table[j] >> 4));
          li_config_table[i].coef_table[j] ^= (w & mixer_write_prog_bri[n].mask) << 4;
        }
        else
        {
          *(p++) = (ADV_VOICE_NEW_COEF_BASE + sizeof(word) + n < a->adv_voice_coef_length) ?
            a->adv_voice_coef_buffer[ADV_VOICE_NEW_COEF_BASE + sizeof(word) + n] : 0x00;
        }
      }
    }
    else
    {
      for (i = ADV_VOICE_NEW_COEF_BASE; i < a->adv_voice_coef_length; i++)
        *(p++) = a->adv_voice_coef_buffer[i];
    }
  }
  else

  {
    for (i = ADV_VOICE_NEW_COEF_BASE; i < a->adv_voice_coef_length; i++)
      *(p++) = a->adv_voice_coef_buffer[i];
  }
  coef_buffer[0] = (p - coef_buffer) - 1;
  add_p (plci, FTY, coef_buffer);
  sig_req (plci, TEL_CTRL, 0);
  send_req (plci);
}


static void adv_voice_clear_config (PLCI   *plci)
{
  DIVA_CAPI_ADAPTER   *a;

  word i, j;


  dbug (1, dprintf ("[%06lx] %s,%d: adv_voice_clear_config",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  a = plci->adapter;
  if ((plci->tel == ADV_VOICE) && (plci == a->AdvSignalPLCI))
  {
    a->adv_voice_coef_length = 0;

    if (!a->li_pri && (plci->li_bchannel_id != 0)
     && (li_config_table[a->li_base + (plci->li_bchannel_id - 1)].plci == plci))
    {
      i = a->li_base + (plci->li_bchannel_id - 1);
      li_config_table[i].curchnl = 0;
      li_config_table[i].channel = 0;
      li_config_table[i].chflags = 0;
      for (j = 0; j < li_total_channels; j++)
      {
        li_config_table[i].flag_table[j] = 0;
        li_config_table[j].flag_table[i] = 0;
        li_config_table[i].coef_table[j] = 0;
        li_config_table[j].coef_table[i] = 0;
      }
      li_config_table[i].coef_table[i] |= LI_COEF_CH_PC_SET | LI_COEF_PC_CH_SET;
      i = a->li_base + MIXER_IC_CHANNEL_BASE + (plci->li_bchannel_id - 1);
      li_config_table[i].curchnl = 0;
      li_config_table[i].channel = 0;
      li_config_table[i].chflags = 0;
      for (j = 0; j < li_total_channels; j++)
      {
        li_config_table[i].flag_table[j] = 0;
        li_config_table[j].flag_table[i] = 0;
        li_config_table[i].coef_table[j] = 0;
        li_config_table[j].coef_table[i] = 0;
      }
      if (a->manufacturer_features & MANUFACTURER_FEATURE_SLAVE_CODEC)
      {
        i = a->li_base + MIXER_IC_CHANNEL_BASE + (2 - plci->li_bchannel_id);
        li_config_table[i].curchnl = 0;
        li_config_table[i].channel = 0;
        li_config_table[i].chflags = 0;
        for (j = 0; j < li_total_channels; j++)
        {
          li_config_table[i].flag_table[j] = 0;
          li_config_table[j].flag_table[i] = 0;
          li_config_table[i].coef_table[j] = 0;
          li_config_table[j].coef_table[i] = 0;
        }
      }
    }

  }
}


static void adv_voice_prepare_switch (dword Id, PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: adv_voice_prepare_switch",
    UnMapId (Id), (char   *)(FILE_), __LINE__));

}


static word adv_voice_save_config (dword Id, PLCI   *plci, byte Rc)
{

  dbug (1, dprintf ("[%06lx] %s,%d: adv_voice_save_config %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  return (GOOD);
}


static word adv_voice_restore_config (dword Id, PLCI   *plci, byte Rc)
{
  DIVA_CAPI_ADAPTER   *a;
  word Info;

  dbug (1, dprintf ("[%06lx] %s,%d: adv_voice_restore_config %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  Info = GOOD;
  a = plci->adapter;
  if ((plci->B1_facilities & B1_FACILITY_VOICE)
   && (plci->tel == ADV_VOICE) && (plci == a->AdvSignalPLCI))
  {
    switch (plci->adjust_b_state)
    {
    case ADJUST_B_RESTORE_VOICE_1:
      plci->internal_command = plci->adjust_b_command;
      if (plci->sig_req)
      {
        plci->adjust_b_state = ADJUST_B_RESTORE_VOICE_1;
        break;
      }
      adv_voice_write_coefs (plci, ADV_VOICE_WRITE_UPDATE);
      plci->adjust_b_state = ADJUST_B_RESTORE_VOICE_2;
      break;
    case ADJUST_B_RESTORE_VOICE_2:
      if ((Rc != OK) && (Rc != OK_FC))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Restore voice config failed %02x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
        Info = _WRONG_STATE;
        break;
      }
      break;
    }
  }
  return (Info);
}




/*------------------------------------------------------------------*/
/* B1 resource switching                                            */
/*------------------------------------------------------------------*/

static byte b1_facilities_table[] =
{
  0x00,  /* 0  No bchannel resources      */
  0x00,  /* 1  Codec (automatic law)      */
  0x00,  /* 2  Codec (A-law)              */
  0x00,  /* 3  Codec (y-law)              */
  0x00,  /* 4  HDLC for X.21              */
  0x00,  /* 5  HDLC                       */
  0x00,  /* 6  External Device 0          */
  0x00,  /* 7  External Device 1          */
  0x00,  /* 8  HDLC 56k                   */
  0x00,  /* 9  Transparent                */
  0x00,  /* 10 Loopback to network        */
  0x00,  /* 11 Test pattern to net        */
  0x00,  /* 12 Rate adaptation sync       */
  0x00,  /* 13 Rate adaptation async      */
  0x00,  /* 14 R-Interface                */
  0x00,  /* 15 HDLC 128k leased line      */
  0x00,  /* 16 FAX                        */
  0x00,  /* 17 Modem async                */
  0x00,  /* 18 Modem sync HDLC            */
  0x00,  /* 19 V.110 async HDLC           */
  0x12,  /* 20 Adv voice (Trans,mixer)    */
  0x00,  /* 21 Codec connected to IC      */
  0x0c,  /* 22 Trans,DTMF                 */
  0x1e,  /* 23 Trans,DTMF+mixer           */
  0x1f,  /* 24 Trans,DTMF+mixer+local     */
  0x13,  /* 25 Trans,mixer+local          */
  0x12,  /* 26 HDLC,mixer                 */
  0x12,  /* 27 HDLC 56k,mixer             */
  0x2c,  /* 28 Trans,LEC+DTMF             */
  0x3e,  /* 29 Trans,LEC+DTMF+mixer       */
  0x3f,  /* 30 Trans,LEC+DTMF+mixer+local */
  0x2c,  /* 31 RTP,LEC+DTMF               */
  0x3e,  /* 32 RTP,LEC+DTMF+mixer         */
  0x3f,  /* 33 RTP,LEC+DTMF+mixer+local   */
  0x00,  /* 34 Signaling task             */
  0x00,  /* 35 PIAFS                      */
  0x0c,  /* 36 Trans,DTMF+TONE            */
  0x1e,  /* 37 Trans,DTMF+TONE+mixer      */
  0x1f   /* 38 Trans,DTMF+TONE+mixer+local*/
};


static word get_b1_facilities (PLCI   * plci, byte b1_resource)
{
  word b1_facilities;

  b1_facilities = b1_facilities_table[b1_resource];
  if ((b1_resource == 9) || (b1_resource == 20) || (b1_resource == 25))
  {

    if (!(((plci->requested_options_conn | plci->requested_options) & (1L << PRIVATE_DTMF_TONE))
       || (plci->appl && (plci->adapter->requested_options_table[plci->appl->Id-1] & (1L << PRIVATE_DTMF_TONE)))))

    {
      if (plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_SOFTDTMF_SEND)
        b1_facilities |= B1_FACILITY_DTMFX;
      if (plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_SOFTDTMF_RECEIVE)
        b1_facilities |= B1_FACILITY_DTMFR;
    }
  }
  if ((b1_resource == 17) || (b1_resource == 18))
  {
    if (plci->adapter->manufacturer_features & (MANUFACTURER_FEATURE_V18 | MANUFACTURER_FEATURE_VOWN))
      b1_facilities |= B1_FACILITY_DTMFX | B1_FACILITY_DTMFR;
  }
/*
  dbug (1, dprintf ("[%06lx] %s,%d: get_b1_facilities %d %04x",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char far *)(FILE_), __LINE__, b1_resource, b1_facilites));
*/
  return (b1_facilities);
}


static byte add_b1_facilities (PLCI   * plci, byte b1_resource, word b1_facilities)
{
  byte b;

  switch (b1_resource)
  {
  case 5:
  case 26:
    if (b1_facilities & (B1_FACILITY_MIXER | B1_FACILITY_VOICE))
      b = 26;
    else
      b = 5;
    break;

  case 8:
  case 27:
    if (b1_facilities & (B1_FACILITY_MIXER | B1_FACILITY_VOICE))
      b = 27;
    else
      b = 8;
    break;

  case 9:
  case 20:
  case 22:
  case 23:
  case 24:
  case 25:
  case 28:
  case 29:
  case 30:
  case 36:
  case 37:
  case 38:
    if (b1_facilities & B1_FACILITY_EC)
    {
      if (b1_facilities & B1_FACILITY_LOCAL)
        b = 30;
      else if (b1_facilities & (B1_FACILITY_MIXER | B1_FACILITY_VOICE))
        b = 29;
      else
        b = 28;
    }

    else if ((b1_facilities & (B1_FACILITY_DTMFX | B1_FACILITY_DTMFR | B1_FACILITY_MIXER))
      && (((plci->requested_options_conn | plci->requested_options) & (1L << PRIVATE_DTMF_TONE))
       || (plci->appl && (plci->adapter->requested_options_table[plci->appl->Id-1] & (1L << PRIVATE_DTMF_TONE)))))
    {
      if (b1_facilities & B1_FACILITY_LOCAL)
        b = 38;
      else if (b1_facilities & (B1_FACILITY_MIXER | B1_FACILITY_VOICE))
        b = 37;
      else
        b = 36;
    }

    else if (((plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_HARDDTMF)
      && !(plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_SOFTDTMF_RECEIVE))
     || ((b1_facilities & B1_FACILITY_DTMFR)
      && ((b1_facilities & B1_FACILITY_MIXER)
       || !(plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_SOFTDTMF_RECEIVE)))
     || ((b1_facilities & B1_FACILITY_DTMFX)
      && ((b1_facilities & B1_FACILITY_MIXER)
       || !(plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_SOFTDTMF_SEND))))
    {
      if (b1_facilities & B1_FACILITY_LOCAL)
        b = 24;
      else if (b1_facilities & (B1_FACILITY_MIXER | B1_FACILITY_VOICE))
        b = 23;
      else
        b = 22;
    }
    else
    {
      if (b1_facilities & B1_FACILITY_LOCAL)
        b = 25;
      else if (b1_facilities & (B1_FACILITY_MIXER | B1_FACILITY_VOICE))
        b = 20;
      else
        b = 9;
    }
    break;

  case 31:
  case 32:
  case 33:
    if (b1_facilities & B1_FACILITY_LOCAL)
      b = 33;
    else if (b1_facilities & (B1_FACILITY_MIXER | B1_FACILITY_VOICE))
      b = 32;
    else
      b = 31;
    break;

  default:
    b = b1_resource;
  }
  dbug (1, dprintf ("[%06lx] %s,%d: add_b1_facilities %d %04x %d %04x",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__,
    b1_resource, b1_facilities, b, get_b1_facilities (plci, b)));
  return (b);
}


static void adjust_b1_facilities (PLCI   *plci, byte new_b1_resource, word new_b1_facilities)
{
  word removed_facilities;

  dbug (1, dprintf ("[%06lx] %s,%d: adjust_b1_facilities %d %04x %04x",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__, new_b1_resource, new_b1_facilities,
    new_b1_facilities & get_b1_facilities (plci, new_b1_resource)));

  new_b1_facilities &= get_b1_facilities (plci, new_b1_resource);
  removed_facilities = plci->B1_facilities & ~new_b1_facilities;

  if (removed_facilities & B1_FACILITY_EC)
    ec_clear_config (plci);


  if (removed_facilities & B1_FACILITY_DTMFR)
  {
    dtmf_rec_clear_config (plci);
    dtmf_parameter_clear_config (plci);
  }
  if (removed_facilities & B1_FACILITY_DTMFX)
    dtmf_send_clear_config (plci);


  if (removed_facilities & B1_FACILITY_MIXER)
    mixer_clear_config (plci);

  if (removed_facilities & B1_FACILITY_VOICE)
    adv_voice_clear_config (plci);
  plci->B1_facilities = new_b1_facilities;
}


static void adjust_b_clear (PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: adjust_b_clear",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  plci->adjust_b_restore = FALSE;
}


static word adjust_b_process (dword Id, PLCI   *plci, byte Rc)
{
  word Info;
  byte b1_resource;
  NCCI   * ncci_ptr;
    API_PARSE bp[2];

  dbug (1, dprintf ("[%06lx] %s,%d: adjust_b_process %02x %d",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->adjust_b_state));

  Info = GOOD;
  switch (plci->adjust_b_state)
  {
  case ADJUST_B_START:
    if ((plci->adjust_b_parms_msg == NULL)
     && (plci->adjust_b_mode & ADJUST_B_MODE_SWITCH_L1)
     && ((plci->adjust_b_mode & ~(ADJUST_B_MODE_SAVE | ADJUST_B_MODE_SWITCH_L1 |
      ADJUST_B_MODE_NO_RESOURCE | ADJUST_B_MODE_RESTORE)) == 0))
    {
      b1_resource = (plci->adjust_b_mode == ADJUST_B_MODE_NO_RESOURCE) ?
        0 : add_b1_facilities (plci, plci->B1_resource, plci->adjust_b_facilities);
      if (b1_resource == plci->B1_resource)
      {
        adjust_b1_facilities (plci, b1_resource, plci->adjust_b_facilities);
        break;
      }
      if (plci->adjust_b_facilities & ~get_b1_facilities (plci, b1_resource))
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Adjust B nonsupported facilities %d %d %04x",
          UnMapId (Id), (char   *)(FILE_), __LINE__,
          plci->B1_resource, b1_resource, plci->adjust_b_facilities));
        Info = _WRONG_STATE;
        break;
      }
    }
    if (plci->adjust_b_mode & ADJUST_B_MODE_SAVE)
    {

      mixer_prepare_switch (Id, plci);


      dtmf_prepare_switch (Id, plci);
      dtmf_parameter_prepare_switch (Id, plci);


      ec_prepare_switch (Id, plci);

      adv_voice_prepare_switch (Id, plci);
    }
    plci->adjust_b_state = ADJUST_B_SAVE_MIXER_1;
    Rc = OK;
  case ADJUST_B_SAVE_MIXER_1:
    if (plci->adjust_b_mode & ADJUST_B_MODE_SAVE)
    {

      Info = mixer_save_config (Id, plci, Rc);
      if ((Info != GOOD) || plci->internal_command)
        break;

    }
    plci->adjust_b_state = ADJUST_B_SAVE_DTMF_1;
    Rc = OK;
  case ADJUST_B_SAVE_DTMF_1:
    if (plci->adjust_b_mode & ADJUST_B_MODE_SAVE)
    {

      Info = dtmf_save_config (Id, plci, Rc);
      if ((Info != GOOD) || plci->internal_command)
        break;

    }
    plci->adjust_b_state = ADJUST_B_REMOVE_L23_1;
  case ADJUST_B_REMOVE_L23_1:
    if ((plci->adjust_b_mode & ADJUST_B_MODE_REMOVE_L23)
     && plci->NL.Id && !plci->nl_remove_id)
    {
      plci->internal_command = plci->adjust_b_command;
      if (plci->adjust_b_ncci != 0)
      {
        ncci_ptr = &(plci->adapter->ncci[plci->adjust_b_ncci]);
        while (ncci_ptr->data_pending)
        {
          plci->data_sent_ptr = ncci_ptr->DBuffer[ncci_ptr->data_out].P;
          data_rc (plci, plci->adapter->ncci_ch[plci->adjust_b_ncci]);
        }
        while (ncci_ptr->data_ack_pending)
          data_ack (plci, plci->adapter->ncci_ch[plci->adjust_b_ncci]);
      }
      nl_req_ncci (plci, REMOVE,
        (byte)((plci->adjust_b_mode & ADJUST_B_MODE_CONNECT) ? plci->adjust_b_ncci : 0));
      send_req (plci);
      plci->adjust_b_state = ADJUST_B_REMOVE_L23_2;
      break;
    }
    plci->adjust_b_state = ADJUST_B_REMOVE_L23_2;
    Rc = OK;
  case ADJUST_B_REMOVE_L23_2:
    if ((Rc != OK) && (Rc != OK_FC))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: Adjust B remove failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
      Info = _WRONG_STATE;
      break;
    }
    if (plci->adjust_b_mode & ADJUST_B_MODE_REMOVE_L23)
    {
      if (plci_nl_busy (plci))
      {
        plci->internal_command = plci->adjust_b_command;
        break;
      }
    }
    plci->adjust_b_state = ADJUST_B_SAVE_EC_1;
    Rc = OK;
  case ADJUST_B_SAVE_EC_1:
    if (plci->adjust_b_mode & ADJUST_B_MODE_SAVE)
    {

      Info = ec_save_config (Id, plci, Rc);
      if ((Info != GOOD) || plci->internal_command)
        break;

    }
    plci->adjust_b_state = ADJUST_B_SAVE_DTMF_PARAMETER_1;
    Rc = OK;
  case ADJUST_B_SAVE_DTMF_PARAMETER_1:
    if (plci->adjust_b_mode & ADJUST_B_MODE_SAVE)
    {

      Info = dtmf_parameter_save_config (Id, plci, Rc);
      if ((Info != GOOD) || plci->internal_command)
        break;

    }
    plci->adjust_b_state = ADJUST_B_SAVE_VOICE_1;
    Rc = OK;
  case ADJUST_B_SAVE_VOICE_1:
    if (plci->adjust_b_mode & ADJUST_B_MODE_SAVE)
    {
      Info = adv_voice_save_config (Id, plci, Rc);
      if ((Info != GOOD) || plci->internal_command)
        break;
    }
    plci->adjust_b_state = ADJUST_B_SWITCH_L1_1;
  case ADJUST_B_SWITCH_L1_1:
    if (plci->adjust_b_mode & ADJUST_B_MODE_SWITCH_L1)
    {
      if (plci->sig_req)
      {
        plci->internal_command = plci->adjust_b_command;
        break;
      }
      if (plci->adjust_b_parms_msg != NULL)
        api_load_msg (plci->adjust_b_parms_msg, bp);
      else
        api_load_msg (&plci->B_protocol, bp);
      Info = add_b1 (plci, bp,
        (word)((plci->adjust_b_mode & ADJUST_B_MODE_NO_RESOURCE) ? 2 : 0),
        plci->adjust_b_facilities);
      if (Info != GOOD)
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Adjust B invalid L1 parameters %d %04x",
          UnMapId (Id), (char   *)(FILE_), __LINE__,
          plci->B1_resource, plci->adjust_b_facilities));
        break;
      }
      plci->internal_command = plci->adjust_b_command;
      sig_req (plci, RESOURCES, 0);
      send_req (plci);
      plci->adjust_b_state = ADJUST_B_SWITCH_L1_2;
      break;
    }
    plci->adjust_b_state = ADJUST_B_SWITCH_L1_2;
    Rc = OK;
  case ADJUST_B_SWITCH_L1_2:
    if ((Rc != OK) && (Rc != OK_FC))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: Adjust B switch failed %02x %d %04x",
        UnMapId (Id), (char   *)(FILE_), __LINE__,
        Rc, plci->B1_resource, plci->adjust_b_facilities));
      Info = _WRONG_STATE;
      break;
    }
    plci->adjust_b_state = ADJUST_B_RESTORE_VOICE_1;
    Rc = OK;
  case ADJUST_B_RESTORE_VOICE_1:
  case ADJUST_B_RESTORE_VOICE_2:
    if (plci->adjust_b_mode & ADJUST_B_MODE_RESTORE)
    {
      Info = adv_voice_restore_config (Id, plci, Rc);
      if ((Info != GOOD) || plci->internal_command)
        break;
    }
    plci->adjust_b_state = ADJUST_B_RESTORE_DTMF_PARAMETER_1;
    Rc = OK;
  case ADJUST_B_RESTORE_DTMF_PARAMETER_1:
  case ADJUST_B_RESTORE_DTMF_PARAMETER_2:
    if (plci->adjust_b_mode & ADJUST_B_MODE_RESTORE)
    {

      Info = dtmf_parameter_restore_config (Id, plci, Rc);
      if ((Info != GOOD) || plci->internal_command)
        break;

    }
    plci->adjust_b_state = ADJUST_B_RESTORE_EC_1;
    Rc = OK;
  case ADJUST_B_RESTORE_EC_1:
  case ADJUST_B_RESTORE_EC_2:
    if (plci->adjust_b_mode & ADJUST_B_MODE_RESTORE)
    {

      Info = ec_restore_config (Id, plci, Rc);
      if ((Info != GOOD) || plci->internal_command)
        break;

    }
    plci->adjust_b_state = ADJUST_B_ASSIGN_L23_1;
  case ADJUST_B_ASSIGN_L23_1:
    if (plci->adjust_b_mode & ADJUST_B_MODE_ASSIGN_L23)
    {
      if (plci_nl_busy (plci))
      {
        plci->internal_command = plci->adjust_b_command;
        break;
      }
      if (plci->adjust_b_mode & ADJUST_B_MODE_CONNECT)
        plci->call_dir |= CALL_DIR_FORCE_OUTG_NL;
      if (plci->adjust_b_parms_msg != NULL)
        api_load_msg (plci->adjust_b_parms_msg, bp);
      else
        api_load_msg (&plci->B_protocol, bp);
      Info = add_b23 (plci, bp);
      if (Info != GOOD)
      {
        dbug (1, dprintf ("[%06lx] %s,%d: Adjust B invalid L23 parameters %04x",
          UnMapId (Id), (char   *)(FILE_), __LINE__, Info));
        break;
      }
      plci->internal_command = plci->adjust_b_command;
      nl_req_ncci (plci, ASSIGN, 0);
      send_req (plci);
      plci->adjust_b_state = ADJUST_B_ASSIGN_L23_2;
      break;
    }
    plci->adjust_b_state = ADJUST_B_ASSIGN_L23_2;
    Rc = ASSIGN_OK;
  case ADJUST_B_ASSIGN_L23_2:
    if ((Rc != OK) && (Rc != OK_FC) && (Rc != ASSIGN_OK))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: Adjust B assign failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
      Info = _WRONG_STATE;
      break;
    }
    if (plci->adjust_b_mode & ADJUST_B_MODE_ASSIGN_L23)
    {
      if (Rc != ASSIGN_OK)
      {
        plci->internal_command = plci->adjust_b_command;
        break;
      }
    }
    if (plci->adjust_b_mode & ADJUST_B_MODE_USER_CONNECT)
    {
      plci->adjust_b_restore = TRUE;
      break;
    }
    plci->adjust_b_state = ADJUST_B_CONNECT_1;
  case ADJUST_B_CONNECT_1:
    if (plci->adjust_b_mode & ADJUST_B_MODE_CONNECT)
    {
      plci->internal_command = plci->adjust_b_command;
      if (plci_nl_busy (plci))
        break;
      nl_req_ncci (plci, N_CONNECT, 0);
      send_req (plci);
      plci->adjust_b_state = ADJUST_B_CONNECT_2;
      break;
    }
    plci->adjust_b_state = ADJUST_B_RESTORE_DTMF_1;
    Rc = OK;
  case ADJUST_B_CONNECT_2:
  case ADJUST_B_CONNECT_3:
  case ADJUST_B_CONNECT_4:
    if ((Rc != OK) && (Rc != OK_FC) && (Rc != 0))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: Adjust B connect failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
      Info = _WRONG_STATE;
      break;
    }
    if (Rc == OK)
    {
      if (plci->adjust_b_mode & ADJUST_B_MODE_CONNECT)
      {
        get_ncci (plci, (byte)(Id >> 16), plci->adjust_b_ncci);
        Id = (Id & 0xffff) | (((dword)(plci->adjust_b_ncci)) << 16);
      }
      if (plci->adjust_b_state == ADJUST_B_CONNECT_2)
        plci->adjust_b_state = ADJUST_B_CONNECT_3;
      else if (plci->adjust_b_state == ADJUST_B_CONNECT_4)
        plci->adjust_b_state = ADJUST_B_RESTORE_DTMF_1;
    }
    else if (Rc == 0)
    {
      if (plci->adjust_b_state == ADJUST_B_CONNECT_2)
        plci->adjust_b_state = ADJUST_B_CONNECT_4;
      else if (plci->adjust_b_state == ADJUST_B_CONNECT_3)
        plci->adjust_b_state = ADJUST_B_RESTORE_DTMF_1;
    }
    if (plci->adjust_b_state != ADJUST_B_RESTORE_DTMF_1)
    {
      plci->internal_command = plci->adjust_b_command;
      break;
    }
    Rc = OK;
  case ADJUST_B_RESTORE_DTMF_1:
  case ADJUST_B_RESTORE_DTMF_2:
    if (plci->adjust_b_mode & ADJUST_B_MODE_RESTORE)
    {

      Info = dtmf_restore_config (Id, plci, Rc);
      if ((Info != GOOD) || plci->internal_command)
        break;

    }
    plci->adjust_b_state = ADJUST_B_RESTORE_MIXER_1;
    Rc = OK;
  case ADJUST_B_RESTORE_MIXER_1:
  case ADJUST_B_RESTORE_MIXER_2:
  case ADJUST_B_RESTORE_MIXER_3:
  case ADJUST_B_RESTORE_MIXER_4:
  case ADJUST_B_RESTORE_MIXER_5:
  case ADJUST_B_RESTORE_MIXER_6:
  case ADJUST_B_RESTORE_MIXER_7:
    if (plci->adjust_b_mode & ADJUST_B_MODE_RESTORE)
    {

      Info = mixer_restore_config (Id, plci, Rc);
      if ((Info != GOOD) || plci->internal_command)
        break;

    }
    plci->adjust_b_state = ADJUST_B_END;
  case ADJUST_B_END:
    break;
  }
  return (Info);
}


static void adjust_b1_resource (dword Id, PLCI   *plci, API_SAVE   *bp_msg, word b1_facilities, word internal_command)
{

  dbug (1, dprintf ("[%06lx] %s,%d: adjust_b1_resource %d %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__,
    plci->B1_resource, b1_facilities));

  plci->adjust_b_parms_msg = bp_msg;
  plci->adjust_b_facilities = b1_facilities;
  plci->adjust_b_command = internal_command;
  plci->adjust_b_ncci = (word)(Id >> 16);
  if ((bp_msg == NULL) && (plci->B1_resource == 0))
    plci->adjust_b_mode = ADJUST_B_MODE_SAVE | ADJUST_B_MODE_NO_RESOURCE | ADJUST_B_MODE_SWITCH_L1;
  else
    plci->adjust_b_mode = ADJUST_B_MODE_SAVE | ADJUST_B_MODE_SWITCH_L1 | ADJUST_B_MODE_RESTORE;
  plci->adjust_b_state = ADJUST_B_START;
  dbug (1, dprintf ("[%06lx] %s,%d: Adjust B1 resource %d %04x...",
    UnMapId (Id), (char   *)(FILE_), __LINE__,
    plci->B1_resource, b1_facilities));
}


static void adjust_b_restore (dword Id, PLCI   *plci, byte Rc)
{
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: adjust_b_restore %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
    if (plci->req_in != 0)
    {
      plci->internal_command = ADJUST_B_RESTORE_1;
      break;
    }
    Rc = OK;
  case ADJUST_B_RESTORE_1:
    if ((Rc != OK) && (Rc != OK_FC))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: Adjust B enqueued failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
    }
    plci->adjust_b_parms_msg = NULL;
    plci->adjust_b_facilities = plci->B1_facilities;
    plci->adjust_b_command = ADJUST_B_RESTORE_2;
    plci->adjust_b_ncci = (word)(Id >> 16);
    plci->adjust_b_mode = ADJUST_B_MODE_RESTORE;
    plci->adjust_b_state = ADJUST_B_START;
    dbug (1, dprintf ("[%06lx] %s,%d: Adjust B restore...",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
  case ADJUST_B_RESTORE_2:
    if (adjust_b_process (Id, plci, Rc) != GOOD)
    {
      dbug (1, dprintf ("[%06lx] %s,%d: Adjust B restore failed",
        UnMapId (Id), (char   *)(FILE_), __LINE__));
    }
    if (plci->internal_command)
      break;
    break;
  }
}


static void reset_b3_command (dword Id, PLCI   *plci, byte Rc)
{
  word Info;
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: reset_b3_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  Info = GOOD;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
    plci->adjust_b_parms_msg = NULL;
    plci->adjust_b_facilities = plci->B1_facilities;
    plci->adjust_b_command = RESET_B3_COMMAND_1;
    plci->adjust_b_ncci = (word)(Id >> 16);
    plci->adjust_b_mode = ADJUST_B_MODE_REMOVE_L23 | ADJUST_B_MODE_ASSIGN_L23 | ADJUST_B_MODE_CONNECT;
    plci->adjust_b_state = ADJUST_B_START;
    dbug (1, dprintf ("[%06lx] %s,%d: Reset B3...",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
  case RESET_B3_COMMAND_1:
    Info = adjust_b_process (Id, plci, Rc);
    if (Info != GOOD)
    {
      dbug (1, dprintf ("[%06lx] %s,%d: Reset failed",
        UnMapId (Id), (char   *)(FILE_), __LINE__));
      break;
    }
    if (plci->internal_command)
      return;
    break;
  }
/*  sendf (plci->appl, _RESET_B3_R | CONFIRM, Id, plci->number, "w", Info);*/
  sendf(plci->appl,_RESET_B3_I,Id,0,"s","");
}


static void select_b_command (dword Id, PLCI   *plci, byte Rc)
{
  word Info;
  word internal_command;
  byte esc_chi[3];

  dbug (1, dprintf ("[%06lx] %s,%d: select_b_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  Info = GOOD;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
    plci->adjust_b_parms_msg = &plci->saved_msg;
    if ((plci->tel == ADV_VOICE) && (plci == plci->adapter->AdvSignalPLCI))
      plci->adjust_b_facilities = plci->B1_facilities | B1_FACILITY_VOICE;
    else
      plci->adjust_b_facilities = plci->B1_facilities & ~B1_FACILITY_VOICE;
    plci->adjust_b_command = SELECT_B_COMMAND_1;
    plci->adjust_b_ncci = (word)(Id >> 16);
    if (plci->saved_msg.parms[0].length == 0)
    {
      plci->adjust_b_mode = ADJUST_B_MODE_SAVE | ADJUST_B_MODE_REMOVE_L23 | ADJUST_B_MODE_SWITCH_L1 |
        ADJUST_B_MODE_NO_RESOURCE;
    }
    else
    {
      plci->adjust_b_mode = ADJUST_B_MODE_SAVE | ADJUST_B_MODE_REMOVE_L23 | ADJUST_B_MODE_SWITCH_L1 |
        ADJUST_B_MODE_ASSIGN_L23 | ADJUST_B_MODE_USER_CONNECT | ADJUST_B_MODE_RESTORE;
    }
    plci->adjust_b_state = ADJUST_B_START;
    dbug (1, dprintf ("[%06lx] %s,%d: Select B protocol...",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
  case SELECT_B_COMMAND_1:
    Info = adjust_b_process (Id, plci, Rc);
    if (Info != GOOD)
    {
      dbug (1, dprintf ("[%06lx] %s,%d: Select B protocol failed",
        UnMapId (Id), (char   *)(FILE_), __LINE__));
      break;
    }
    if (plci->internal_command)
      return;
    if (plci->tel == ADV_VOICE)
    {
      esc_chi[0] = 0x02;
      esc_chi[1] = 0x18;
      esc_chi[2] = plci->b_channel;
      SetVoiceChannel (plci->adapter->AdvCodecPLCI, esc_chi, plci->adapter);
    }
    break;
  }
  sendf (plci->appl, _SELECT_B_REQ | CONFIRM, Id, plci->number, "w", Info);
}


static void fax_connect_ack_command (dword Id, PLCI   *plci, byte Rc)
{
  word Info;
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: fax_connect_ack_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  Info = GOOD;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
  case FAX_CONNECT_ACK_COMMAND_1:
    if (plci_nl_busy (plci))
    {
      plci->internal_command = FAX_CONNECT_ACK_COMMAND_1;
      return;
    }
    plci->internal_command = FAX_CONNECT_ACK_COMMAND_2;
    plci->NData[0].P = plci->fax_connect_info_buffer;
    plci->NData[0].PLength = plci->fax_connect_info_length;
    plci->NL.X = plci->NData;
    plci->NL.ReqCh = 0;
    plci->NL.Req = plci->nl_req = (byte) N_CONNECT_ACK;
    plci->adapter->request (&plci->NL);
    return;
  case FAX_CONNECT_ACK_COMMAND_2:
    if ((Rc != OK) && (Rc != OK_FC))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: FAX issue CONNECT ACK failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
      break;
    }
  }
  if ((plci->ncpi_state & NCPI_VALID_CONNECT_B3_ACT)
   && !(plci->ncpi_state & NCPI_CONNECT_B3_ACT_SENT))
  {
    if (plci->B3_prot == 4)
      sendf(plci->appl,_CONNECT_B3_ACTIVE_I,Id,0,"s","");
    else
      sendf(plci->appl,_CONNECT_B3_ACTIVE_I,Id,0,"S",plci->ncpi_buffer);
    plci->ncpi_state |= NCPI_CONNECT_B3_ACT_SENT;
  }
}


static void fax_edata_ack_command (dword Id, PLCI   *plci, byte Rc)
{
  word Info;
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: fax_edata_ack_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  Info = GOOD;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
  case FAX_EDATA_ACK_COMMAND_1:
    if (plci_nl_busy (plci))
    {
      plci->internal_command = FAX_EDATA_ACK_COMMAND_1;
      return;
    }
    plci->internal_command = FAX_EDATA_ACK_COMMAND_2;
    plci->NData[0].P = plci->fax_connect_info_buffer;
    plci->NData[0].PLength = plci->fax_edata_ack_length;
    plci->NL.X = plci->NData;
    plci->NL.ReqCh = 0;
    plci->NL.Req = plci->nl_req = (byte) N_EDATA;
    plci->adapter->request (&plci->NL);
    return;
  case FAX_EDATA_ACK_COMMAND_2:
    if ((Rc != OK) && (Rc != OK_FC))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: FAX issue EDATA ACK failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
      break;
    }
  }
}


static void fax_connect_info_command (dword Id, PLCI   *plci, byte Rc)
{
  word Info;
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: fax_connect_info_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  Info = GOOD;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
  case FAX_CONNECT_INFO_COMMAND_1:
    if (plci_nl_busy (plci))
    {
      plci->internal_command = FAX_CONNECT_INFO_COMMAND_1;
      return;
    }
    plci->internal_command = FAX_CONNECT_INFO_COMMAND_2;
    plci->NData[0].P = plci->fax_connect_info_buffer;
    plci->NData[0].PLength = plci->fax_connect_info_length;
    plci->NL.X = plci->NData;
    plci->NL.ReqCh = 0;
    plci->NL.Req = plci->nl_req = (byte) N_EDATA;
    plci->adapter->request (&plci->NL);
    return;
  case FAX_CONNECT_INFO_COMMAND_2:
    if ((Rc != OK) && (Rc != OK_FC))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: FAX setting connect info failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
      Info = _WRONG_STATE;
      break;
    }
    if (plci_nl_busy (plci))
    {
      plci->internal_command = FAX_CONNECT_INFO_COMMAND_2;
      return;
    }
    plci->command = _CONNECT_B3_R;
    nl_req_ncci (plci, N_CONNECT, 0);
    send_req (plci);
    return;
  }
  sendf (plci->appl, _CONNECT_B3_R | CONFIRM, Id, plci->number, "w", Info);
}


static void fax_adjust_b23_command (dword Id, PLCI   *plci, byte Rc)
{
  word Info;
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: fax_adjust_b23_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  Info = GOOD;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
    plci->adjust_b_parms_msg = NULL;
    plci->adjust_b_facilities = plci->B1_facilities;
    plci->adjust_b_command = FAX_ADJUST_B23_COMMAND_1;
    plci->adjust_b_ncci = (word)(Id >> 16);
    plci->adjust_b_mode = ADJUST_B_MODE_REMOVE_L23 | ADJUST_B_MODE_ASSIGN_L23;
    plci->adjust_b_state = ADJUST_B_START;
    dbug (1, dprintf ("[%06lx] %s,%d: FAX adjust B23...",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
  case FAX_ADJUST_B23_COMMAND_1:
    Info = adjust_b_process (Id, plci, Rc);
    if (Info != GOOD)
    {
      dbug (1, dprintf ("[%06lx] %s,%d: FAX adjust failed",
        UnMapId (Id), (char   *)(FILE_), __LINE__));
      break;
    }
    if (plci->internal_command)
      return;
  case FAX_ADJUST_B23_COMMAND_2:
    if (plci_nl_busy (plci))
    {
      plci->internal_command = FAX_ADJUST_B23_COMMAND_2;
      return;
    }
    plci->command = _CONNECT_B3_R;
    nl_req_ncci (plci, N_CONNECT, 0);
    send_req (plci);
    return;
  }
  sendf (plci->appl, _CONNECT_B3_R | CONFIRM, Id, plci->number, "w", Info);
}


static void fax_disconnect_command (dword Id, PLCI   *plci, byte Rc)
{
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: fax_disconnect_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
    plci->internal_command = FAX_DISCONNECT_COMMAND_1;
    return;
  case FAX_DISCONNECT_COMMAND_1:
  case FAX_DISCONNECT_COMMAND_2:
  case FAX_DISCONNECT_COMMAND_3:
    if ((Rc != OK) && (Rc != OK_FC) && (Rc != 0))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: FAX disconnect EDATA failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
      break;
    }
    if (Rc == OK)
    {
      if ((internal_command == FAX_DISCONNECT_COMMAND_1)
       || (internal_command == FAX_DISCONNECT_COMMAND_2))
      {
        plci->internal_command = FAX_DISCONNECT_COMMAND_2;
      }
    }
    else if (Rc == 0)
    {
      if (internal_command == FAX_DISCONNECT_COMMAND_1)
        plci->internal_command = FAX_DISCONNECT_COMMAND_3;
    }
    return;
  }
}



static void rtp_connect_b3_req_command (dword Id, PLCI   *plci, byte Rc)
{
  word Info;
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: rtp_connect_b3_req_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  Info = GOOD;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
  case RTP_CONNECT_B3_REQ_COMMAND_1:
    if (plci_nl_busy (plci))
    {
      plci->internal_command = RTP_CONNECT_B3_REQ_COMMAND_1;
      return;
    }
    plci->internal_command = RTP_CONNECT_B3_REQ_COMMAND_2;
    nl_req_ncci (plci, N_CONNECT, 0);
    send_req (plci);
    return;
  case RTP_CONNECT_B3_REQ_COMMAND_2:
    if ((Rc != OK) && (Rc != OK_FC))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: RTP setting connect info failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
      Info = _WRONG_STATE;
      break;
    }
    if (plci_nl_busy (plci))
    {
      plci->internal_command = RTP_CONNECT_B3_REQ_COMMAND_2;
      return;
    }
    plci->internal_command = RTP_CONNECT_B3_REQ_COMMAND_3;
    plci->NData[0].PLength = plci->internal_req_buffer[0];
    plci->NData[0].P = plci->internal_req_buffer + 1;
    plci->NL.X = plci->NData;
    plci->NL.ReqCh = 0;
    plci->NL.Req = plci->nl_req = (byte) N_UDATA;
    plci->adapter->request (&plci->NL);
    break;
  case RTP_CONNECT_B3_REQ_COMMAND_3:
    return;
  }
  sendf (plci->appl, _CONNECT_B3_R | CONFIRM, Id, plci->number, "w", Info);
}


static void rtp_connect_b3_res_command (dword Id, PLCI   *plci, byte Rc)
{
  word Info;
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: rtp_connect_b3_res_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  Info = GOOD;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
  case RTP_CONNECT_B3_RES_COMMAND_1:
    if (plci_nl_busy (plci))
    {
      plci->internal_command = RTP_CONNECT_B3_RES_COMMAND_1;
      return;
    }
    plci->internal_command = RTP_CONNECT_B3_RES_COMMAND_2;
    nl_req_ncci (plci, N_CONNECT_ACK, (byte)(Id >> 16));
    send_req (plci);
    return;
  case RTP_CONNECT_B3_RES_COMMAND_2:
    if ((Rc != OK) && (Rc != OK_FC))
    {
      dbug (1, dprintf ("[%06lx] %s,%d: RTP setting connect resp info failed %02x",
        UnMapId (Id), (char   *)(FILE_), __LINE__, Rc));
      Info = _WRONG_STATE;
      break;
    }
    if (plci_nl_busy (plci))
    {
      plci->internal_command = RTP_CONNECT_B3_RES_COMMAND_2;
      return;
    }
    sendf (plci->appl, _CONNECT_B3_ACTIVE_I, Id, 0, "s", "");
    plci->internal_command = RTP_CONNECT_B3_RES_COMMAND_3;
    plci->NData[0].PLength = plci->internal_req_buffer[0];
    plci->NData[0].P = plci->internal_req_buffer + 1;
    plci->NL.X = plci->NData;
    plci->NL.ReqCh = 0;
    plci->NL.Req = plci->nl_req = (byte) N_UDATA;
    plci->adapter->request (&plci->NL);
    return;
  case RTP_CONNECT_B3_RES_COMMAND_3:
    return;
  }
}



static void hold_save_command (dword Id, PLCI   *plci, byte Rc)
{
    byte SS_Ind[] = "\x05\x02\x00\x02\x00\x00"; /* Hold_Ind struct*/
  word Info;
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: hold_save_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  Info = GOOD;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    if (!plci->NL.Id)
      break;
    plci->command = 0;
    plci->adjust_b_parms_msg = NULL;
    plci->adjust_b_facilities = plci->B1_facilities;
    plci->adjust_b_command = HOLD_SAVE_COMMAND_1;
    plci->adjust_b_ncci = (word)(Id >> 16);
    plci->adjust_b_mode = ADJUST_B_MODE_SAVE | ADJUST_B_MODE_REMOVE_L23;
    plci->adjust_b_state = ADJUST_B_START;
    dbug (1, dprintf ("[%06lx] %s,%d: HOLD save...",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
  case HOLD_SAVE_COMMAND_1:
    Info = adjust_b_process (Id, plci, Rc);
    if (Info != GOOD)
    {
      dbug (1, dprintf ("[%06lx] %s,%d: HOLD save failed",
        UnMapId (Id), (char   *)(FILE_), __LINE__));
      break;
    }
    if (plci->internal_command)
      return;
  }
  sendf (plci->appl, _FACILITY_I, Id & 0xffffL, 0, "ws", 3, SS_Ind);
}


static void retrieve_restore_command (dword Id, PLCI   *plci, byte Rc)
{
    byte SS_Ind[] = "\x05\x03\x00\x02\x00\x00"; /* Retrieve_Ind struct*/
  word Info;
  word internal_command;

  dbug (1, dprintf ("[%06lx] %s,%d: retrieve_restore_command %02x %04x",
    UnMapId (Id), (char   *)(FILE_), __LINE__, Rc, plci->internal_command));

  Info = GOOD;
  internal_command = plci->internal_command;
  plci->internal_command = 0;
  switch (internal_command)
  {
  default:
    plci->command = 0;
    plci->adjust_b_parms_msg = NULL;
    plci->adjust_b_facilities = plci->B1_facilities;
    plci->adjust_b_command = RETRIEVE_RESTORE_COMMAND_1;
    plci->adjust_b_ncci = (word)(Id >> 16);
    plci->adjust_b_mode = ADJUST_B_MODE_ASSIGN_L23 | ADJUST_B_MODE_USER_CONNECT | ADJUST_B_MODE_RESTORE;
    plci->adjust_b_state = ADJUST_B_START;
    dbug (1, dprintf ("[%06lx] %s,%d: RETRIEVE restore...",
      UnMapId (Id), (char   *)(FILE_), __LINE__));
  case RETRIEVE_RESTORE_COMMAND_1:
    Info = adjust_b_process (Id, plci, Rc);
    if (Info != GOOD)
    {
      dbug (1, dprintf ("[%06lx] %s,%d: RETRIEVE restore failed",
        UnMapId (Id), (char   *)(FILE_), __LINE__));
      break;
    }
    if (plci->internal_command)
      return;
  }
  sendf (plci->appl, _FACILITY_I, Id & 0xffffL, 0, "ws", 3, SS_Ind);
}


static void init_b1_config (PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: init_b1_config",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  plci->B1_resource = 0;
  plci->B1_facilities = 0;

  plci->li_bchannel_id = 0;
  mixer_clear_config (plci);


  ec_clear_config (plci);


  dtmf_rec_clear_config (plci);
  dtmf_send_clear_config (plci);
  dtmf_parameter_clear_config (plci);

  adv_voice_clear_config (plci);
  adjust_b_clear (plci);
}


static void clear_b1_config (PLCI   *plci)
{

  dbug (1, dprintf ("[%06lx] %s,%d: clear_b1_config",
    (dword)((plci->Id << 8) | UnMapController (plci->adapter->Id)),
    (char   *)(FILE_), __LINE__));

  adv_voice_clear_config (plci);
  adjust_b_clear (plci);

  ec_clear_config (plci);


  dtmf_rec_clear_config (plci);
  dtmf_send_clear_config (plci);
  dtmf_parameter_clear_config (plci);


  if ((plci->li_bchannel_id != 0)
   && (li_config_table[plci->adapter->li_base + (plci->li_bchannel_id - 1)].plci == plci))
  {
    mixer_clear_config (plci);
    li_config_table[plci->adapter->li_base + (plci->li_bchannel_id - 1)].plci = NULL;
    plci->li_bchannel_id = 0;
  }

  plci->B1_resource = 0;
  plci->B1_facilities = 0;
}


/* -----------------------------------------------------------------
                XON protocol local helpers
   ----------------------------------------------------------------- */
static void channel_flow_control_remove (PLCI   * plci) {
  DIVA_CAPI_ADAPTER   * a = plci->adapter;
  word i;
  for(i=1;i<MAX_NL_CHANNEL+1;i++) {
    if (a->ch_flow_plci[i] == plci->Id) {
      a->ch_flow_plci[i] = 0;
      a->ch_flow_control[i] = 0;
    }
  }
}

static void channel_x_on (PLCI   * plci, byte ch) {
  DIVA_CAPI_ADAPTER   * a = plci->adapter;
  if (a->ch_flow_control[ch] & N_XON_SENT) {
    a->ch_flow_control[ch] &= ~N_XON_SENT;
  }
}

static void channel_x_off (PLCI   * plci, byte ch, byte flag) {
  DIVA_CAPI_ADAPTER   * a = plci->adapter;
  if ((a->ch_flow_control[ch] & N_RX_FLOW_CONTROL_MASK) == 0) {
    a->ch_flow_control[ch] |= (N_CH_XOFF | flag);
    a->ch_flow_plci[ch] = plci->Id;
    a->ch_flow_control_pending++;
  }
}

static void channel_request_xon (PLCI   * plci, byte ch) {
  DIVA_CAPI_ADAPTER   * a = plci->adapter;

  if (a->ch_flow_control[ch] & N_CH_XOFF) {
    a->ch_flow_control[ch] |= N_XON_REQ;
    a->ch_flow_control[ch] &= ~N_CH_XOFF;
    a->ch_flow_control[ch] &= ~N_XON_CONNECT_IND;
  }
}

static void channel_xmit_extended_xon (PLCI   * plci) {
  DIVA_CAPI_ADAPTER   * a;
  int max_ch = sizeof(a->ch_flow_control)/sizeof(a->ch_flow_control[0]);
  int i, one_requested = 0;

  if ((!plci) || (!plci->Id) || ((a = plci->adapter) == 0)) {
    return;
  }

  for (i = 0; i < max_ch; i++) {
    if ((a->ch_flow_control[i] & N_CH_XOFF) &&
        (a->ch_flow_control[i] & N_XON_CONNECT_IND) &&
        (plci->Id == a->ch_flow_plci[i])) {
      channel_request_xon (plci, (byte)i);
      one_requested = 1;
    }
  }

  if (one_requested) {
    channel_xmit_xon (plci);
  }
}

/*
  Try to xmit next X_ON
  */
static int find_channel_with_pending_x_on (DIVA_CAPI_ADAPTER   * a, PLCI   * plci) {
  int max_ch = sizeof(a->ch_flow_control)/sizeof(a->ch_flow_control[0]);
  int i;

  if (!(plci->adapter->manufacturer_features & MANUFACTURER_FEATURE_XONOFF_FLOW_CONTROL)) {
    return (0);
  }

  if (a->last_flow_control_ch >= max_ch) {
    a->last_flow_control_ch = 1;
  }
  for (i=a->last_flow_control_ch; i < max_ch; i++) {
    if ((a->ch_flow_control[i] & N_XON_REQ) &&
        (plci->Id == a->ch_flow_plci[i])) {
      a->last_flow_control_ch = i+1;
      return (i);
    }
  }

  for (i = 1; i < a->last_flow_control_ch; i++) {
    if ((a->ch_flow_control[i] & N_XON_REQ) &&
        (plci->Id == a->ch_flow_plci[i])) {
      a->last_flow_control_ch = i+1;
      return (i);
    }
  }

  return (0);
}

static void channel_xmit_xon (PLCI   * plci) {
  DIVA_CAPI_ADAPTER   * a = plci->adapter;
  byte ch;

  if (plci->nl_req || !plci->NL.Id || plci->nl_remove_id) {
    return;
  }
  if ((ch = (byte)find_channel_with_pending_x_on (a, plci)) == 0) {
    return;
  }
  a->ch_flow_control[ch] &= ~N_XON_REQ;
  a->ch_flow_control[ch] |= N_XON_SENT;

  plci->NL.Req = plci->nl_req = (byte)N_XON;
  plci->NL.ReqCh         = ch;
  plci->NL.X             = plci->NData;
  plci->NL.XNum          = 1;
  plci->NData[0].P       = &plci->RBuffer[0];
  plci->NData[0].PLength = 0;

  plci->adapter->request(&plci->NL);
}

static int channel_can_xon (PLCI   * plci, byte ch) {
  APPL   * APPLptr;
  DIVA_CAPI_ADAPTER   * a;
  word NCCIcode;
  dword count;
  word Num;
  word i;

  APPLptr = plci->appl;
  a = plci->adapter;

  if (!APPLptr)
    return (0);

  NCCIcode = a->ch_ncci[ch] | (((word) a->Id) << 8);

                /* count all buffers within the Application pool    */
                /* belonging to the same NCCI. XON if a first is    */
                /* used.                                            */
  count = 0;
  Num = 0xffff;
  for(i=0; i<APPLptr->MaxBuffer; i++) {
    if(NCCIcode==APPLptr->DataNCCI[i]) count++;
    if(!APPLptr->DataNCCI[i] && Num==0xffff) Num = i;
  }
  if ((count > 2) || (Num == 0xffff)) {
    return (0);
  }
  return (1);
}


/*------------------------------------------------------------------*/

static word CPN_filter_ok(byte   *cpn,DIVA_CAPI_ADAPTER   * a,word offset)
{
  return 1;
}



/**********************************************************************************/
/* function groups the listening applications according to the CIP mask and the   */
/* Info_Mask. Each group gets just one Connect_Ind. Some application manufacturer */
/* are not multi-instance capable, so they start e.g. 30 applications what causes */
/* big problems on application level (one call, 30 Connect_Ind, ect). The         */
/* function must be enabled by setting "a->group_optimization_enabled" from the   */
/* OS specific part (per adapter).                                                */
/**********************************************************************************/
static void group_optimization(DIVA_CAPI_ADAPTER   * a, PLCI   * plci)
{
  word i,j,k,busy,group_found;
  dword info_mask_group[MAX_CIP_TYPES];
  dword cip_mask_group[MAX_CIP_TYPES];
  word appl_number_group_type[MAX_APPL];
  PLCI   *auxplci;

  set_group_ind_mask (plci); /* all APPLs within this inc. call are allowed to dial in */

  if(!a->group_optimization_enabled)
  {
    dbug(1,dprintf("No group optimization"));
    return;
  }

  dbug(1,dprintf("Group optimization = 0x%x...", a->group_optimization_enabled));

  for(i=0;i<MAX_CIP_TYPES;i++)
  {
    info_mask_group[i] = 0;
    cip_mask_group [i] = 0;
  }
  for(i=0;i<MAX_APPL;i++)
  {
    appl_number_group_type[i] = 0;
  }
  for(i=0; i<max_appl; i++) /* check if any multi instance capable application is present */
  {  /* group_optimization set to 1 means not to optimize multi-instance capable applications (default) */
    if(application[i].Id && (application[i].MaxNCCI) > 1 && (a->CIP_Mask[i])  && (a->group_optimization_enabled ==1) )
    {
      dbug(1,dprintf("Multi-Instance capable, no optimization required"));
      return; /* allow good application unfiltered access */
    }
  }
  for(i=0; i<max_appl; i++) /* Build CIP Groups */
  {
    if(application[i].Id && a->CIP_Mask[i] )
    {
      for(k=0,busy=FALSE; k<a->max_plci; k++)
      {
        if(a->plci[k].Id) 
        {
          auxplci = &a->plci[k];
          if(auxplci->appl == &application[i]) /* application has a busy PLCI */
          {
            busy = TRUE;
            dbug(1,dprintf("Appl 0x%x is busy",i+1));
          }
          else if(test_c_ind_mask_bit (auxplci, i)) /* application has an incoming call pending */
          {
            busy = TRUE;
            dbug(1,dprintf("Appl 0x%x has inc. call pending",i+1));
          }
        }
      }

      for(j=0,group_found=0; j<=(MAX_CIP_TYPES) && !busy &&!group_found; j++)     /* build groups with free applications only */
      {
        if(j==MAX_CIP_TYPES)       /* all groups are in use but group still not found */
        {                           /* the MAX_CIP_TYPES group enables all calls because of field overflow */
          appl_number_group_type[i] = MAX_CIP_TYPES;
          group_found=TRUE;
          dbug(1,dprintf("Field overflow appl 0x%x",i+1));
        }
        else if( (info_mask_group[j]==a->CIP_Mask[i]) && (cip_mask_group[j]==a->Info_Mask[i]) )  
        {                                      /* is group already present ?                  */
          appl_number_group_type[i] = j|0x80;  /* store the group number for each application */
          group_found=TRUE;
          dbug(1,dprintf("Group 0x%x found with appl 0x%x, CIP=0x%lx",appl_number_group_type[i],i+1,info_mask_group[j]));
        }
        else if(!info_mask_group[j])
        {                                      /* establish a new group                       */
          appl_number_group_type[i] = j|0x80;  /* store the group number for each application */
          info_mask_group[j] = a->CIP_Mask[i]; /* store the new CIP mask for the new group    */
          cip_mask_group[j] = a->Info_Mask[i]; /* store the new Info_Mask for this new group  */
          group_found=TRUE;
          dbug(1,dprintf("New Group 0x%x established with appl 0x%x, CIP=0x%lx",appl_number_group_type[i],i+1,info_mask_group[j]));
        }
      }
    }
  }
        
  for(i=0; i<max_appl; i++) /* Build group_optimization_mask_table */
  {
    if(appl_number_group_type[i]) /* application is free, has listens and is member of a group */
    {
      if(appl_number_group_type[i] == MAX_CIP_TYPES)
      {
        dbug(1,dprintf("OverflowGroup 0x%x, valid appl = 0x%x, call enabled",appl_number_group_type[i],i+1));
      }
      else
      {
        dbug(1,dprintf("Group 0x%x, valid appl = 0x%x",appl_number_group_type[i],i+1));
        for(j=i+1; j<max_appl; j++)   /* search other group members and mark them as busy        */
        {
          if(appl_number_group_type[i] == appl_number_group_type[j]) 
          {
            dbug(1,dprintf("Appl 0x%x is member of group 0x%x, no call",j+1,appl_number_group_type[j]));
            clear_group_ind_mask_bit (plci, j);           /* disable call on other group members */
            appl_number_group_type[j] = 0;       /* remove disabled group member from group list */
          }
        }
      }
    }
    else                                                 /* application should not get a call */
    {
      clear_group_ind_mask_bit (plci, i);
    }
  }

}



/* OS notifies the driver about a application Capi_Register */
word CapiRegister(word id)
{
  word i,j,appls_found;

  PLCI   *plci;
  DIVA_CAPI_ADAPTER   *a;

  for(i=0,appls_found=0; i<max_appl; i++)
  {
    if( application[i].Id && (application[i].Id!=id) )
    {
      appls_found++;                       /* an application has been found */
    }
  }

  if(appls_found) return TRUE;
  for(i=0; i<max_adapter; i++)                   /* scan all adapters...    */
  {
    a = &adapter[i];
    if(a->request)
    {
      if(a->flag_dynamic_l1_down)  /* remove adapter from L1 tristate (Huntgroup) */
      {
        if(!appls_found)           /* first application does a capi register   */
        {
          if((j=get_plci(a)))                    /* activate L1 of all adapters */
          {
            plci = &a->plci[j-1];
            plci->command = 0;
            add_p(plci,OAD,"\x01\xfd");
            add_p(plci,CAI,"\x01\x80");
            add_p(plci,UID,"\x06\x43\x61\x70\x69\x32\x30");
            add_p(plci,SHIFT|6,NULL);
            add_p(plci,SIN,"\x02\x00\x00");
            plci->internal_command = START_L1_SIG_ASSIGN_PEND;
            sig_req(plci,ASSIGN,DSIG_ID);
            add_p(plci,FTY,"\x02\xff\x07"); /* l1 start */
            sig_req(plci,SIG_CTRL,0);
            send_req(plci);
          }
        }
      }
    }
  }
  return FALSE;
}

/*------------------------------------------------------------------*/

/* Functions for virtual Switching e.g. Transfer by join, Conference */

static void VSwitchReqInd(PLCI   *plci, dword Id, byte   **parms)
{
 word i;
 /* Format of vswitch_t:
 0 byte length
 1 byte VSWITCHIE
 2 byte VSWITCH_REQ/VSWITCH_IND
 3 byte reserved
 4 word VSwitchcommand
 6 word returnerror
 8... Params
 */
 if(!plci ||
  !plci->appl ||
  !plci->State ||
  plci->Sig.Ind==NCR_FACILITY
  )
  return;
 
 for(i=0;i<MAX_MULTI_IE;i++)
 {
        if(!parms[i][0]) continue;
  if(parms[i][0]<7)
  {
   parms[i][0]=0; /* kill it */
   continue;
  }
  dbug(1,dprintf("VSwitchReqInd(%d)",parms[i][4]));
  switch(parms[i][4])
  {
  case VSJOIN:
   if(!plci->relatedPTYPLCI ||
    (plci->ptyState!=S_ECT && plci->relatedPTYPLCI->ptyState!=S_ECT))
   { /* Error */
    break;
   }
   /* remember all necessary informations */
   if(parms[i][0]!=11 || parms[i][8]!=3) /* Length Test */
   {
    break;
   }
   if(parms[i][2]==VSWITCH_IND && parms[i][9]==1)
   {   /* first indication after ECT-Request on Consultation Call */
    plci->vswitchstate=parms[i][9];
    parms[i][9]=2; /* State */
    /* now ask first Call to join */
   }
   else if(parms[i][2]==VSWITCH_REQ && parms[i][9]==3)
   { /* Answer of VSWITCH_REQ from first Call */
    plci->vswitchstate=parms[i][9];
    /* tell consultation call to join
    and the protocol capabilities of the first call */
   }
   else
   { /* Error */
    break;
   }    
   plci->vsprot=parms[i][10]; /* protocol */
   plci->vsprotdialect=parms[i][11]; /* protocoldialect */
   /* send join request to related PLCI */
   parms[i][1]=VSWITCHIE;
   parms[i][2]=VSWITCH_REQ;
   
   plci->relatedPTYPLCI->command = 0;
   plci->relatedPTYPLCI->internal_command = VSWITCH_REQ_PEND;
   add_p(plci->relatedPTYPLCI,ESC,&parms[i][0]);
   sig_req(plci->relatedPTYPLCI,VSWITCH_REQ,0);
   send_req(plci->relatedPTYPLCI);
   break;
  case VSTRANSPORT:
  default:
   if(plci->relatedPTYPLCI &&
    plci->vswitchstate==3 &&
    plci->relatedPTYPLCI->vswitchstate==3)
   {
    add_p(plci->relatedPTYPLCI,ESC,&parms[i][0]);
    sig_req(plci->relatedPTYPLCI,VSWITCH_REQ,0);
    send_req(plci->relatedPTYPLCI);
   }
   break;
  }  
  parms[i][0]=0; /* kill it */
 }
}


/*------------------------------------------------------------------*/

static int diva_get_dma_descriptor (PLCI   *plci, dword   *dma_magic) {
  ENTITY e;
  IDI_SYNC_REQ* pReq = (IDI_SYNC_REQ*)&e;

  if (!(diva_xdi_extended_features & DIVA_CAPI_XDI_PROVIDES_RX_DMA)) {
    return (-1);
  }

  pReq->xdi_dma_descriptor_operation.Req = 0;
  pReq->xdi_dma_descriptor_operation.Rc = IDI_SYNC_REQ_DMA_DESCRIPTOR_OPERATION;

  pReq->xdi_dma_descriptor_operation.info.operation =     IDI_SYNC_REQ_DMA_DESCRIPTOR_ALLOC;
  pReq->xdi_dma_descriptor_operation.info.descriptor_number  = -1;
  pReq->xdi_dma_descriptor_operation.info.descriptor_address = NULL;
  pReq->xdi_dma_descriptor_operation.info.descriptor_magic   = 0;

  e.user[0] = plci->adapter->Id - 1;
  plci->adapter->request((ENTITY*)pReq);

  if (!pReq->xdi_dma_descriptor_operation.info.operation &&
      (pReq->xdi_dma_descriptor_operation.info.descriptor_number >= 0) &&
      pReq->xdi_dma_descriptor_operation.info.descriptor_magic) {
    *dma_magic = pReq->xdi_dma_descriptor_operation.info.descriptor_magic;
    dbug(3,dprintf("dma_alloc, a:%d (%d-%08x)",
         plci->adapter->Id,
         pReq->xdi_dma_descriptor_operation.info.descriptor_number,
         *dma_magic));
    return (pReq->xdi_dma_descriptor_operation.info.descriptor_number);
  } else {
    dbug(1,dprintf("dma_alloc failed"));
    return (-1);
  }
}

static void diva_free_dma_descriptor (PLCI   *plci, int nr) {
  ENTITY e;
  IDI_SYNC_REQ* pReq = (IDI_SYNC_REQ*)&e;

  if (nr < 0) {
    return;
  }

  pReq->xdi_dma_descriptor_operation.Req = 0;
  pReq->xdi_dma_descriptor_operation.Rc = IDI_SYNC_REQ_DMA_DESCRIPTOR_OPERATION;

  pReq->xdi_dma_descriptor_operation.info.operation =                                                IDI_SYNC_REQ_DMA_DESCRIPTOR_FREE;
  pReq->xdi_dma_descriptor_operation.info.descriptor_number  = nr;
  pReq->xdi_dma_descriptor_operation.info.descriptor_address = NULL;
  pReq->xdi_dma_descriptor_operation.info.descriptor_magic   = 0;

  e.user[0] = plci->adapter->Id - 1;
  plci->adapter->request((ENTITY*)pReq);

  if (!pReq->xdi_dma_descriptor_operation.info.operation) {
    dbug(1,dprintf("dma_free(%d)", nr));
  } else {
    dbug(1,dprintf("dma_free failed (%d)", nr));
  }
}

/*------------------------------------------------------------------*/
