523 lines
15 KiB
C
523 lines
15 KiB
C
/************************************************************************/
|
|
/* SISCO SOFTWARE MODULE HEADER *****************************************/
|
|
/************************************************************************/
|
|
/* (c) Copyright Systems Integration Specialists Company, Inc., */
|
|
/* 2003 - 2003, All Rights Reserved */
|
|
/* */
|
|
/* MODULE NAME : acse2dib.c */
|
|
/* PRODUCT(S) : MMS-LITE */
|
|
/* */
|
|
/* MODULE DESCRIPTION : Address matching functions. */
|
|
/* */
|
|
/* NOTE: !!! If changes are made to this file the same changes */
|
|
/* have to be made in the marb_dib.c (MMS-EASE). */
|
|
/* */
|
|
/* GLOBAL FUNCTIONS DEFINED IN THIS MODULE : */
|
|
/* */
|
|
/* MODIFICATION LOG : */
|
|
/* Date Who Rev Comments */
|
|
/* -------- --- ------ ------------------------------------------- */
|
|
/* 03/28/05 JRB 03 Del suicacse header. */
|
|
/* 06/16/03 EJV 02 Renamed m_match.c to acse2dib.c */
|
|
/* 06/02/03 MDE 01 Created */
|
|
/************************************************************************/
|
|
|
|
#include "glbtypes.h"
|
|
#include "sysincs.h"
|
|
|
|
#include "acse2.h"
|
|
|
|
|
|
/************************************************************************/
|
|
/* For debug version, use a static pointer to avoid duplication of */
|
|
/* __FILE__ strings. */
|
|
/************************************************************************/
|
|
|
|
#ifdef DEBUG_SISCO
|
|
static ST_CHAR *thisFileName = __FILE__;
|
|
#endif
|
|
|
|
|
|
/************************************************************************/
|
|
/* Internal Functions */
|
|
|
|
static ST_VOID _dib_match_ap_title (DIB_MATCH_CTRL *matchCtrl,
|
|
ST_INT *matchLevel,
|
|
ST_BOOLEAN ind_pres, MMS_OBJ_ID *ind_apTitle,
|
|
ST_BOOLEAN dib_pres, MMS_OBJ_ID *dib_apTitle);
|
|
static ST_VOID _dib_match_ae_int (DIB_MATCH_CTRL *matchCtrl,
|
|
ST_INT *matchLevel,
|
|
ST_BOOLEAN ind_pres, ST_INT32 ind_val,
|
|
ST_BOOLEAN dib_pres, ST_INT32 dib_val,
|
|
ST_CHAR *itemText);
|
|
static ST_VOID _dib_match_mem (ST_INT *matchLevel,
|
|
ST_INT ind_sel_len, ST_UCHAR *ind_sel,
|
|
ST_INT dib_sel_len, ST_UCHAR *dib_sel,
|
|
ST_CHAR *sel_text);
|
|
static ST_VOID _dib_match_ae_present_flag (DIB_MATCH_CTRL *matchCtrl,
|
|
ST_INT *matchLevelIo,
|
|
ST_CHAR *aeElText,
|
|
ST_BOOLEAN dibPres,
|
|
ST_BOOLEAN remotePres,
|
|
ST_BOOLEAN *doCompareOut);
|
|
|
|
/************************************************************************/
|
|
/* ml_match_remote_ar */
|
|
/************************************************************************/
|
|
|
|
ST_RET dib_match_remote_ar (DIB_MATCH_CTRL *matchCtrl,
|
|
AARQ_APDU *aarq, DIB_ENTRY **dib_entry_out)
|
|
{
|
|
ST_INT i;
|
|
DIB_ENTRY *de;
|
|
DIB_ENTRY *closeDe;
|
|
ST_INT remMatch;
|
|
|
|
ACSELOG_DIB0 ("Matching Remote AR");
|
|
closeDe = NULL;
|
|
for (i = 0; i < num_rem_dib_entries; ++i)
|
|
{
|
|
de = &rem_dib_table[i];
|
|
ACSELOG_DIB1C (" Remote AR '%s'", de->name);
|
|
remMatch = dib_cmp_remote_addr (matchCtrl, aarq, de);
|
|
if (remMatch == DIB_MATCH_EXACT)
|
|
{
|
|
*dib_entry_out = de;
|
|
ACSELOG_DIB1C ("Exact Match: '%s'", de->name);
|
|
return (SD_SUCCESS);
|
|
}
|
|
if (remMatch == DIB_MATCH_CLOSE && closeDe == NULL)
|
|
closeDe = de;
|
|
}
|
|
|
|
if (closeDe != NULL)
|
|
{
|
|
*dib_entry_out = closeDe;
|
|
ACSELOG_DIB1C ("Close Match: '%s'", closeDe->name);
|
|
return (SD_SUCCESS);
|
|
}
|
|
|
|
return (SD_FAILURE);
|
|
}
|
|
|
|
/************************************************************************/
|
|
/* dib_match_local_ar */
|
|
/************************************************************************/
|
|
|
|
ST_RET dib_match_local_ar (DIB_MATCH_CTRL *matchCtrl,
|
|
AARQ_APDU *aarq, DIB_ENTRY **dib_entry_out)
|
|
{
|
|
ST_INT i;
|
|
DIB_ENTRY *de;
|
|
DIB_ENTRY *closeDe;
|
|
ST_INT locMatch;
|
|
|
|
ACSELOG_DIB0 ("Matching Local AR");
|
|
closeDe = NULL;
|
|
for (i = 0; i < num_loc_dib_entries; ++i)
|
|
{
|
|
de = &loc_dib_table[i];
|
|
ACSELOG_DIB1C (" Local AR '%s'", de->name);
|
|
locMatch = dib_cmp_local_addr (matchCtrl,aarq, de);
|
|
if (locMatch == DIB_MATCH_EXACT)
|
|
{
|
|
ACSELOG_DIB1C ("Exact Match: '%s'", de->name);
|
|
*dib_entry_out = de;
|
|
return (SD_SUCCESS);
|
|
}
|
|
|
|
if (locMatch == DIB_MATCH_CLOSE && closeDe == NULL)
|
|
closeDe = de;
|
|
}
|
|
|
|
if (closeDe != NULL)
|
|
{
|
|
ACSELOG_DIB1C ("Close Match: '%s'", de->name);
|
|
*dib_entry_out = closeDe;
|
|
return (SD_SUCCESS);
|
|
}
|
|
|
|
return (SD_FAILURE);
|
|
}
|
|
|
|
|
|
/************************************************************************/
|
|
/************************************************************************/
|
|
/* dib_cmp_local_addr */
|
|
/************************************************************************/
|
|
|
|
ST_INT dib_cmp_local_addr (DIB_MATCH_CTRL *matchCtrl,
|
|
AARQ_APDU *aarq, DIB_ENTRY *dib_entry)
|
|
{
|
|
ST_INT matchLevel;
|
|
|
|
/* The best we can do ... */
|
|
matchLevel = DIB_MATCH_EXACT;
|
|
|
|
/* Compare local network address with dib entry */
|
|
#if 0
|
|
if (matchCtrl->match_net_addr)
|
|
{
|
|
if (aarq->transport == TCP)
|
|
{
|
|
_dib_match_mem (&matchLevel,
|
|
strlen (aarq->ip_addr), aarq->ip_addr,
|
|
strlen (dib_entry->ip_addr), dib_entry->ip_addr,
|
|
"Local IP Address");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
else if (aarq->transport == TP4)
|
|
{
|
|
_dib_match_mem (&matchLevel,
|
|
aarq->net_addr_len,aarq->net_addr,
|
|
dib_entry->net_addr_len, dib_entry->net_addr,
|
|
"Local Network Address");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
else
|
|
{
|
|
ACSELOG_ERR1 ("Transport type problem: %d", aarq->transport);
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
}
|
|
#endif
|
|
|
|
|
|
/* Compare selectors with dib entry */
|
|
/* PSEL */
|
|
if (matchCtrl->match_psel)
|
|
{
|
|
_dib_match_mem (&matchLevel, aarq->called_paddr.psel_len, aarq->called_paddr.psel,
|
|
dib_entry->pres_addr.psel_len, dib_entry->pres_addr.psel,
|
|
"PSEL");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* SSEL */
|
|
if (matchCtrl->match_ssel)
|
|
{
|
|
_dib_match_mem (&matchLevel, aarq->called_paddr.ssel_len, aarq->called_paddr.ssel,
|
|
dib_entry->pres_addr.ssel_len, dib_entry->pres_addr.ssel,
|
|
"SSEL");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* TSEL */
|
|
if (matchCtrl->match_tsel)
|
|
{
|
|
_dib_match_mem (&matchLevel, aarq->called_paddr.tsel_len, aarq->called_paddr.tsel,
|
|
dib_entry->pres_addr.tsel_len, dib_entry->pres_addr.tsel,
|
|
"TSEL");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* Now compare AE Titles */
|
|
/* AP Title */
|
|
if (matchCtrl->match_ap_title)
|
|
{
|
|
_dib_match_ap_title (matchCtrl,&matchLevel,
|
|
aarq->called_ae_title.AP_title_pres, &aarq->called_ae_title.AP_title,
|
|
dib_entry->AP_title_pres, &dib_entry->AP_title);
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* AE Qualifier */
|
|
if (matchCtrl->match_ae_qualifier)
|
|
{
|
|
_dib_match_ae_int (matchCtrl, &matchLevel,
|
|
aarq->called_ae_title.AE_qual_pres, aarq->called_ae_title.AE_qual,
|
|
dib_entry->AE_qual_pres, dib_entry->AE_qual,
|
|
"AE Qualifier");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* AP Invoke ID */
|
|
if (matchCtrl->match_ap_invoke)
|
|
{
|
|
_dib_match_ae_int (matchCtrl, &matchLevel,
|
|
aarq->called_ae_title.AP_inv_id_pres, aarq->called_ae_title.AP_inv_id,
|
|
dib_entry->AP_inv_id_pres, dib_entry->AP_invoke_id,
|
|
"AP invoke ID");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* AE Invoke ID */
|
|
if (matchCtrl->match_ae_invoke)
|
|
{
|
|
_dib_match_ae_int (matchCtrl, &matchLevel,
|
|
aarq->called_ae_title.AE_inv_id_pres, aarq->called_ae_title.AE_inv_id,
|
|
dib_entry->AE_inv_id_pres, dib_entry->AE_invoke_id,
|
|
"AE invoke ID");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
return (matchLevel); /* exact */
|
|
}
|
|
|
|
|
|
/************************************************************************/
|
|
/* dib_cmp_remote_addr */
|
|
/************************************************************************/
|
|
|
|
ST_INT dib_cmp_remote_addr (DIB_MATCH_CTRL *matchCtrl,
|
|
AARQ_APDU *aarq, DIB_ENTRY *dib_entry)
|
|
{
|
|
ST_INT matchLevel;
|
|
|
|
/* The best we can do ... */
|
|
matchLevel = DIB_MATCH_EXACT;
|
|
|
|
/* Compare partner network address with dib entry */
|
|
#if 0
|
|
if (matchCtrl->match_net_addr)
|
|
{
|
|
if (aarq->transport == TCP)
|
|
{
|
|
_dib_match_mem (&matchLevel,
|
|
strlen (aarq->part_ip_addr), aarq->part_ip_addr,
|
|
strlen (dib_entry->ip_addr), dib_entry->ip_addr,
|
|
"Remote IP Address");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
else if (aarq->transport == TP4)
|
|
{
|
|
_dib_match_mem (&matchLevel,
|
|
aarq->part_net_addr_len,aarq->part_net_addr,
|
|
dib_entry->net_addr_len, dib_entry->net_addr,
|
|
"Remote Network Address");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
else
|
|
{
|
|
ACSELOG_ERR1 ("Transport type problem: %d", aarq->transport);
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
}
|
|
#endif
|
|
|
|
/* Compare selectors with dib entry */
|
|
/* PSEL */
|
|
if (matchCtrl->match_psel)
|
|
{
|
|
_dib_match_mem (&matchLevel, aarq->calling_paddr.psel_len, aarq->calling_paddr.psel,
|
|
dib_entry->pres_addr.psel_len, dib_entry->pres_addr.psel,
|
|
"PSEL");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* SSEL */
|
|
if (matchCtrl->match_ssel)
|
|
{
|
|
_dib_match_mem (&matchLevel, aarq->calling_paddr.ssel_len, aarq->calling_paddr.ssel,
|
|
dib_entry->pres_addr.ssel_len, dib_entry->pres_addr.ssel,
|
|
"SSEL");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* TSEL */
|
|
if (matchCtrl->match_tsel)
|
|
{
|
|
_dib_match_mem (&matchLevel, aarq->calling_paddr.tsel_len, aarq->calling_paddr.tsel,
|
|
dib_entry->pres_addr.tsel_len, dib_entry->pres_addr.tsel,
|
|
"TSEL");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* Now compare AE Titles */
|
|
/* AP Title */
|
|
if (matchCtrl->match_ap_title)
|
|
{
|
|
_dib_match_ap_title (matchCtrl, &matchLevel,
|
|
aarq->calling_ae_title.AP_title_pres, &aarq->calling_ae_title.AP_title,
|
|
dib_entry->AP_title_pres, &dib_entry->AP_title);
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* AE Qualifier */
|
|
if (matchCtrl->match_ae_qualifier)
|
|
{
|
|
_dib_match_ae_int (matchCtrl, &matchLevel,
|
|
aarq->calling_ae_title.AE_qual_pres, aarq->calling_ae_title.AE_qual,
|
|
dib_entry->AE_qual_pres, dib_entry->AE_qual,
|
|
"AE Qualifier");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* AP Invoke ID */
|
|
if (matchCtrl->match_ap_invoke)
|
|
{
|
|
_dib_match_ae_int (matchCtrl, &matchLevel,
|
|
aarq->calling_ae_title.AP_inv_id_pres, aarq->calling_ae_title.AP_inv_id,
|
|
dib_entry->AP_inv_id_pres, dib_entry->AP_invoke_id,
|
|
"AP invoke ID");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
/* AE Invoke ID */
|
|
if (matchCtrl->match_ae_invoke)
|
|
{
|
|
_dib_match_ae_int (matchCtrl, &matchLevel,
|
|
aarq->calling_ae_title.AE_inv_id_pres, aarq->calling_ae_title.AE_inv_id,
|
|
dib_entry->AE_inv_id_pres, dib_entry->AE_invoke_id,
|
|
"AE invoke ID");
|
|
if (matchLevel == DIB_MATCH_NOT)
|
|
return (DIB_MATCH_NOT);
|
|
}
|
|
|
|
return (matchLevel);
|
|
}
|
|
|
|
/************************************************************************/
|
|
/* _dib_match_ap_title */
|
|
/************************************************************************/
|
|
|
|
/* Set match level to DIB_MATCH_NOT, or leave alone */
|
|
|
|
static ST_VOID _dib_match_ap_title (DIB_MATCH_CTRL *matchCtrl,
|
|
ST_INT *matchLevel,
|
|
ST_BOOLEAN ind_pres, MMS_OBJ_ID *ind_apTitle,
|
|
ST_BOOLEAN dib_pres, MMS_OBJ_ID *dib_apTitle)
|
|
{
|
|
ST_CHAR *itemText = "AP Title";
|
|
ST_BOOLEAN doCompare;
|
|
|
|
_dib_match_ae_present_flag (matchCtrl, matchLevel, itemText, dib_pres,
|
|
ind_pres, &doCompare);
|
|
/* See if we need to compare */
|
|
if (doCompare)
|
|
{
|
|
if (asn1_objidcmp (ind_apTitle, dib_apTitle))
|
|
{
|
|
ACSELOG_DIB1C (" %s mismatch", itemText);
|
|
*matchLevel = DIB_MATCH_NOT;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
|
|
/************************************************************************/
|
|
/* _dib_match_ae_int */
|
|
/************************************************************************/
|
|
|
|
/* Set match level to DIB_MATCH_NOT, or leave alone */
|
|
|
|
static ST_VOID _dib_match_ae_int (DIB_MATCH_CTRL *matchCtrl, ST_INT *matchLevel,
|
|
ST_BOOLEAN ind_pres, ST_INT32 ind_val,
|
|
ST_BOOLEAN dib_pres, ST_INT32 dib_val,
|
|
ST_CHAR *itemText)
|
|
{
|
|
ST_BOOLEAN doCompare;
|
|
|
|
_dib_match_ae_present_flag (matchCtrl, matchLevel, itemText, dib_pres,
|
|
ind_pres, &doCompare);
|
|
|
|
/* OK, we matched, see if we need to compare */
|
|
if (doCompare)
|
|
{
|
|
if (ind_val != dib_val)
|
|
{
|
|
ACSELOG_DIB1C (" %s mismatch", itemText);
|
|
*matchLevel = DIB_MATCH_NOT;
|
|
return;
|
|
}
|
|
}
|
|
}
|
|
|
|
/************************************************************************/
|
|
/* _dib_match_mem */
|
|
/************************************************************************/
|
|
|
|
/* Set match level to DIB_MATCH_NOT, or leave alone */
|
|
|
|
static ST_VOID _dib_match_mem (ST_INT *matchLevel,
|
|
ST_INT ind_sel_len, ST_UCHAR *ind_sel,
|
|
ST_INT dib_sel_len, ST_UCHAR *dib_sel,
|
|
ST_CHAR *sel_text)
|
|
{
|
|
/* See if the selectors match */
|
|
if (ind_sel_len == dib_sel_len &&
|
|
!memcmp (ind_sel, dib_sel, ind_sel_len))
|
|
{
|
|
return;
|
|
}
|
|
|
|
ACSELOG_DIB1C (" %s mismatch", sel_text);
|
|
*matchLevel = DIB_MATCH_NOT;
|
|
return;
|
|
}
|
|
|
|
/************************************************************************/
|
|
/* _dib_match_ae_present_flag */
|
|
/************************************************************************/
|
|
|
|
/* Set match level to DIB_MATCH_CLOSE or DIB_MATCH_NOT, or leave alone */
|
|
|
|
static ST_VOID _dib_match_ae_present_flag (DIB_MATCH_CTRL *matchCtrl,
|
|
ST_INT *matchLevelIo,
|
|
ST_CHAR *aeElText,
|
|
ST_BOOLEAN dibPres,
|
|
ST_BOOLEAN remotePres,
|
|
ST_BOOLEAN *doCompareOut)
|
|
{
|
|
|
|
/* If the remote sent the parameter and it is in the DIB, SUCCESS */
|
|
if (dibPres == remotePres)
|
|
{
|
|
*doCompareOut = dibPres; /* If it is present, then compare it */
|
|
return;
|
|
}
|
|
*doCompareOut = SD_FALSE; /* Can't compare */
|
|
|
|
/* OK, this is more complicated. We need to find out what the mismatch */
|
|
/* is and what the user wants to do about it. */
|
|
|
|
if (!remotePres)
|
|
{
|
|
if (matchCtrl->match_allow_missing_ae_elements)
|
|
{
|
|
ACSELOG_DIB1C (" Remote did not send: %s, ignoring", aeElText);
|
|
if (*matchLevelIo == DIB_MATCH_EXACT)
|
|
*matchLevelIo = DIB_MATCH_CLOSE;
|
|
}
|
|
else
|
|
{
|
|
ACSELOG_DIB1C (" Remote did not send required: %s", aeElText);
|
|
*matchLevelIo = DIB_MATCH_NOT;
|
|
}
|
|
}
|
|
|
|
if (remotePres)
|
|
{
|
|
if (matchCtrl->match_allow_extra_ae_elements)
|
|
{
|
|
ACSELOG_DIB1C (" Remote sent unexpected: %s, ignoring", aeElText);
|
|
if (*matchLevelIo == DIB_MATCH_EXACT)
|
|
*matchLevelIo = DIB_MATCH_CLOSE;
|
|
}
|
|
else
|
|
{
|
|
ACSELOG_DIB1C (" Remote sent unexpected: %s", aeElText);
|
|
*matchLevelIo = DIB_MATCH_NOT;
|
|
}
|
|
}
|
|
}
|
|
|
|
|
|
|