1223 lines
37 KiB
C
1223 lines
37 KiB
C
|
|
/************************************************************************/
|
||
|
|
/* SISCO SOFTWARE MODULE HEADER *****************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/* (c) Copyright Systems Integration Specialists Company, Inc., */
|
||
|
|
/* 1986 - 2002, All Rights Reserved. */
|
||
|
|
/* */
|
||
|
|
/* PROPRIETARY AND CONFIDENTIAL */
|
||
|
|
/* */
|
||
|
|
/* MODULE NAME : mms_rtaa.c */
|
||
|
|
/* PRODUCT(S) : MMSEASE */
|
||
|
|
/* */
|
||
|
|
/* MODULE DESCRIPTION : */
|
||
|
|
/* Function to decode ASN.1 type definitions into Runtime typedefs */
|
||
|
|
/* */
|
||
|
|
/* GLOBAL FUNCTIONS DEFINED IN THIS MODULE : */
|
||
|
|
/* _ms_mk_rt_aa_all */
|
||
|
|
/* _ms_mk_rt_aa */
|
||
|
|
/* _ms_get_rtaa_data_size */
|
||
|
|
/* _ms_log_runtime_aa */
|
||
|
|
/* */
|
||
|
|
/* MODIFICATION LOG : */
|
||
|
|
/* Date Who Rev Comments */
|
||
|
|
/* -------- --- ------ ------------------------------------------- */
|
||
|
|
/* 07/27/05 MDE 06 if m_max_rt_aa_cltr == 0 calc required size */
|
||
|
|
/* 05/11/05 MDE 05 Added _ms_calc_rt_aa_size */
|
||
|
|
/* 02/22/05 JRB 04 Make "sp" local to avoid VXWORKS conflict. */
|
||
|
|
/* 04/02/03 JRB 03 Add UTF8string support (see RT_UTF8_STRING). */
|
||
|
|
/* 03/04/02 JRB 02 Add more "SD_CONST RUNTIME_TYPE *". */
|
||
|
|
/* Make sure str_end_rtaa, arr_end_rtaa init'd. */
|
||
|
|
/* 02/06/02 JRB 01 New. Code from mms_alta.c moved here. */
|
||
|
|
/************************************************************************/
|
||
|
|
|
||
|
|
#include "glbtypes.h"
|
||
|
|
#include "sysincs.h"
|
||
|
|
#include "glbsem.h"
|
||
|
|
|
||
|
|
#include "mmsdefs.h"
|
||
|
|
#include "mms_pvar.h"
|
||
|
|
#include "mms_vvar.h"
|
||
|
|
#include "asn1defs.h"
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/* For debug version, use a static pointer to avoid duplication of */
|
||
|
|
/* __FILE__ strings. */
|
||
|
|
|
||
|
|
#ifdef DEBUG_SISCO
|
||
|
|
SD_CONST static ST_CHAR *SD_CONST thisFileName = __FILE__;
|
||
|
|
#endif
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
|
||
|
|
#define COPY_RTAA(dest,src) { dest->rt = src->rt;\
|
||
|
|
dest->offset_to_data = src->offset_to_data; }
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/* This code is required for handling real alternate access data */
|
||
|
|
/* conversion via mmsdataa, and for using the ARB DATA handlers. */
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/* Runtime AA (RTAA) Handling */
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
static ST_VOID _ms_calc_rt_aa_size (SD_CONST RUNTIME_TYPE *rt_head, ST_INT rt_num,
|
||
|
|
ST_INT *num_aa_out);
|
||
|
|
|
||
|
|
static ST_RET get_struct_comps (AA_APPLY_CTRL *aa_app, RT_AA_CTRL *w_rtaa);
|
||
|
|
static ST_RET get_arr_elmnts (AA_APPLY_CTRL *aa_app, RT_AA_CTRL *w_rtaa);
|
||
|
|
static ST_INT count_num_comp (AA_APPLY_CTRL *aa_app,
|
||
|
|
ALT_ACC_EL *aa,
|
||
|
|
ST_INT *count_out);
|
||
|
|
|
||
|
|
static RT_AA_CTRL *find_end_rtaa (AA_APPLY_CTRL *aa_app,
|
||
|
|
RT_AA_CTRL *start_rtaa);
|
||
|
|
|
||
|
|
static RT_AA_CTRL *find_named_comp (AA_APPLY_CTRL *aa_app,
|
||
|
|
ST_CHAR *name,
|
||
|
|
RT_AA_CTRL *w_rtaa);
|
||
|
|
|
||
|
|
static ST_RET get_component_elmnts (AA_APPLY_CTRL *aa_app,
|
||
|
|
RT_AA_CTRL *rtaa);
|
||
|
|
|
||
|
|
static RT_AA_CTRL *find_arr_el (AA_APPLY_CTRL *aa_app,
|
||
|
|
RT_AA_CTRL *w_rtaa,
|
||
|
|
ST_INT el_index);
|
||
|
|
static ST_VOID ms_rtaa_el_size_calc (RT_AA_CTRL *runtime_aa, ST_INT num_rt_aa);
|
||
|
|
|
||
|
|
static ST_INT arr_loop_level;
|
||
|
|
static ST_INT *arr_loops;
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/* Create a RTAA with all elements for the specified RT type */
|
||
|
|
/* This table is allocated via chk_calloc, and is sized for the max */
|
||
|
|
/* possible AA size. If desired, this may be realloc'd to the correct */
|
||
|
|
/* size by the caller. */
|
||
|
|
|
||
|
|
ST_RET _ms_mk_rt_aa_all (SD_CONST RUNTIME_TYPE *rt_head, ST_INT rt_num,
|
||
|
|
RT_AA_CTRL **rt_aa_out, ST_INT *num_aa_out)
|
||
|
|
{
|
||
|
|
RT_AA_CTRL *rtaa;
|
||
|
|
ST_INT data_offset;
|
||
|
|
SD_CONST RUNTIME_TYPE *rt_end;
|
||
|
|
SD_CONST RUNTIME_TYPE *rt;
|
||
|
|
ST_INT arr_loop_buf[ASN1_MAX_LEVEL];
|
||
|
|
ST_INT _max_rt_aa_ctrl;
|
||
|
|
|
||
|
|
S_LOCK_COMMON_RESOURCES ();
|
||
|
|
|
||
|
|
arr_loop_level = 0;
|
||
|
|
arr_loops = arr_loop_buf;
|
||
|
|
|
||
|
|
/* Allocate the output array for max size */
|
||
|
|
_max_rt_aa_ctrl = m_max_rt_aa_ctrl;
|
||
|
|
if (_max_rt_aa_ctrl == 0)
|
||
|
|
_ms_calc_rt_aa_size (rt_head, rt_num, &_max_rt_aa_ctrl);
|
||
|
|
|
||
|
|
rtaa = (RT_AA_CTRL *) chk_calloc (_max_rt_aa_ctrl, sizeof (RT_AA_CTRL));
|
||
|
|
*rt_aa_out = rtaa;
|
||
|
|
*num_aa_out = 0;
|
||
|
|
|
||
|
|
rt = rt_head; /* set runtime ptr */
|
||
|
|
rt_end = rt_head + rt_num; /* end block */
|
||
|
|
data_offset = 0;
|
||
|
|
|
||
|
|
/* Traverse the RT type as though we were doing a ASN.1 to LOCAL, and */
|
||
|
|
/* set the RTAA RT pointer and offset as each element is encountered. */
|
||
|
|
|
||
|
|
while (rt < rt_end)
|
||
|
|
{
|
||
|
|
if (rt->el_tag == RT_ARR_END) /* treat case of array ending */
|
||
|
|
{
|
||
|
|
if (--arr_loops[arr_loop_level] > 0) /* if need to do next ar elmnt */
|
||
|
|
{
|
||
|
|
rt -= rt->u.arr.num_rt_blks; /* mv rt to start of arr */
|
||
|
|
continue;
|
||
|
|
}
|
||
|
|
else
|
||
|
|
--arr_loop_level;
|
||
|
|
}
|
||
|
|
|
||
|
|
(*num_aa_out)++; /* Count this one */
|
||
|
|
rtaa->rt = rt; /* Set the RT pointer */
|
||
|
|
rtaa->offset_to_data = data_offset; /* Set the offset */
|
||
|
|
data_offset += rt->el_size; /* Offset for next */
|
||
|
|
|
||
|
|
if (rt->el_tag == RT_ARR_START) /* Set up array looping */
|
||
|
|
{
|
||
|
|
++arr_loop_level;
|
||
|
|
arr_loops[arr_loop_level] = rt->u.arr.num_elmnts;
|
||
|
|
}
|
||
|
|
|
||
|
|
rtaa++; /* point to next runtime AA element */
|
||
|
|
rt++; /* point to next runtime element */
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Post process to calculate the 'rtaa->el_size' values (for packed */
|
||
|
|
/* local representation). */
|
||
|
|
ms_rtaa_el_size_calc (*rt_aa_out, *num_aa_out);
|
||
|
|
|
||
|
|
if (mms_debug_sel & MMS_LOG_RTAA)
|
||
|
|
_ms_log_runtime_aa (*rt_aa_out, *num_aa_out);
|
||
|
|
|
||
|
|
/* save the high water mark */
|
||
|
|
if (*num_aa_out > m_hw_rt_aa_ctrl)
|
||
|
|
m_hw_rt_aa_ctrl = *num_aa_out;
|
||
|
|
|
||
|
|
S_UNLOCK_COMMON_RESOURCES ();
|
||
|
|
return (SD_SUCCESS);
|
||
|
|
}
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/* _ms_calc_rt_aa_size */
|
||
|
|
/************************************************************************/
|
||
|
|
|
||
|
|
static ST_VOID _ms_calc_rt_aa_size (SD_CONST RUNTIME_TYPE *rt_head, ST_INT rt_num,
|
||
|
|
ST_INT *num_aa_out)
|
||
|
|
{
|
||
|
|
SD_CONST RUNTIME_TYPE *rt_end;
|
||
|
|
SD_CONST RUNTIME_TYPE *rt;
|
||
|
|
ST_INT arr_loop_buf[ASN1_MAX_LEVEL];
|
||
|
|
ST_INT num_aa;
|
||
|
|
|
||
|
|
S_LOCK_COMMON_RESOURCES ();
|
||
|
|
arr_loop_level = 0;
|
||
|
|
arr_loops = arr_loop_buf;
|
||
|
|
|
||
|
|
num_aa = 0;
|
||
|
|
rt = rt_head; /* set runtime ptr */
|
||
|
|
rt_end = rt_head + rt_num; /* end block */
|
||
|
|
|
||
|
|
/* Traverse the RT type as though we were doing a ASN.1 to LOCAL, and */
|
||
|
|
/* count the RTAA elements */
|
||
|
|
while (rt < rt_end)
|
||
|
|
{
|
||
|
|
if (rt->el_tag == RT_ARR_END) /* treat case of array ending */
|
||
|
|
{
|
||
|
|
if (--arr_loops[arr_loop_level] > 0) /* if need to do next ar elmnt */
|
||
|
|
{
|
||
|
|
rt -= rt->u.arr.num_rt_blks; /* mv rt to start of arr */
|
||
|
|
continue;
|
||
|
|
}
|
||
|
|
else
|
||
|
|
--arr_loop_level;
|
||
|
|
}
|
||
|
|
++num_aa; /* Count this one */
|
||
|
|
|
||
|
|
if (rt->el_tag == RT_ARR_START) /* Set up array looping */
|
||
|
|
{
|
||
|
|
++arr_loop_level;
|
||
|
|
arr_loops[arr_loop_level] = rt->u.arr.num_elmnts;
|
||
|
|
}
|
||
|
|
rt++; /* point to next runtime element */
|
||
|
|
}
|
||
|
|
*num_aa_out = num_aa;
|
||
|
|
S_UNLOCK_COMMON_RESOURCES ();
|
||
|
|
}
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/* Create a RTAA with elements selected by a AA for the specified RT */
|
||
|
|
/* type */
|
||
|
|
/* This table is allocated via chk_calloc, and is sized for the max */
|
||
|
|
/* possible AA size. If desired, this may be realloc'd to the correct */
|
||
|
|
/* size by the caller. */
|
||
|
|
|
||
|
|
ST_RET _ms_mk_rt_aa (SD_CONST RUNTIME_TYPE *rt, ST_INT rt_num,
|
||
|
|
ALT_ACCESS *alt_acc,
|
||
|
|
RT_AA_CTRL **rt_aa_out, ST_INT *num_aa_out)
|
||
|
|
{
|
||
|
|
ALT_ACC_EL *aa;
|
||
|
|
ST_INT num_aa;
|
||
|
|
ST_RET ret;
|
||
|
|
ST_INT num_all_rtaa;
|
||
|
|
RT_AA_CTRL *all_rtaa;
|
||
|
|
RT_AA_CTRL *rtaa;
|
||
|
|
AA_APPLY_CTRL aa_app_ctrl;
|
||
|
|
ST_UINT32 mms_log_mask_save;
|
||
|
|
ST_INT _max_rt_aa_ctrl;
|
||
|
|
|
||
|
|
S_LOCK_COMMON_RESOURCES ();
|
||
|
|
|
||
|
|
aa = alt_acc->aa;
|
||
|
|
num_aa = alt_acc->num_aa;
|
||
|
|
|
||
|
|
/* Make the 'all' rtaa - has all elements expanded, with offsets. */
|
||
|
|
/* This is used with the AA to select the elements for the new RTAA */
|
||
|
|
|
||
|
|
/* Don't allow logging of the 'all' runtime aa table */
|
||
|
|
mms_log_mask_save = mms_debug_sel;
|
||
|
|
mms_debug_sel &= ~MMS_LOG_RTAA;
|
||
|
|
ret = _ms_mk_rt_aa_all (rt, rt_num, &all_rtaa, &num_all_rtaa);
|
||
|
|
mms_debug_sel = mms_log_mask_save;
|
||
|
|
|
||
|
|
if (ret)
|
||
|
|
{
|
||
|
|
S_UNLOCK_COMMON_RESOURCES ();
|
||
|
|
return (ret);
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Allocate the output (new) RT AA table */
|
||
|
|
_max_rt_aa_ctrl = m_max_rt_aa_ctrl;
|
||
|
|
if (_max_rt_aa_ctrl == 0)
|
||
|
|
_ms_calc_rt_aa_size (rt, rt_num, &_max_rt_aa_ctrl);
|
||
|
|
|
||
|
|
rtaa = (RT_AA_CTRL *) chk_calloc (_max_rt_aa_ctrl, sizeof (RT_AA_CTRL));
|
||
|
|
*rt_aa_out = rtaa;
|
||
|
|
*num_aa_out = 0;
|
||
|
|
|
||
|
|
/* Initialize the AA process control structure components */
|
||
|
|
|
||
|
|
/* Alternate Access */
|
||
|
|
aa_app_ctrl.num_aa = num_aa;
|
||
|
|
aa_app_ctrl.aa_head = aa;
|
||
|
|
aa_app_ctrl.aa_end = aa + num_aa - 1;
|
||
|
|
aa_app_ctrl.curr_aa = aa;
|
||
|
|
|
||
|
|
/* Default RTAA */
|
||
|
|
aa_app_ctrl.num_all_rtaa = num_all_rtaa;
|
||
|
|
aa_app_ctrl.all_rtaa_head = all_rtaa;
|
||
|
|
aa_app_ctrl.all_rtaa_end = all_rtaa + (num_all_rtaa -1);
|
||
|
|
|
||
|
|
/* New RTAA */
|
||
|
|
aa_app_ctrl.num_rtaa = 0;
|
||
|
|
aa_app_ctrl.rtaa_head = rtaa;
|
||
|
|
aa_app_ctrl.curr_rtaa = rtaa;
|
||
|
|
|
||
|
|
/* Nest Level */
|
||
|
|
aa_app_ctrl.nest = 0;
|
||
|
|
|
||
|
|
/* Get the appropriate rt_aa_ctrl elements */
|
||
|
|
/* Start by getting the first nest level elements, based on the RT. */
|
||
|
|
/* Note that these functions will call recursively to get handle */
|
||
|
|
/* further nest levels */
|
||
|
|
|
||
|
|
if (rt->el_tag == RT_ARR_START)
|
||
|
|
{
|
||
|
|
ret = get_arr_elmnts (&aa_app_ctrl, all_rtaa);
|
||
|
|
}
|
||
|
|
else if (rt->el_tag == RT_STR_START)
|
||
|
|
{
|
||
|
|
ret = get_struct_comps (&aa_app_ctrl, all_rtaa);
|
||
|
|
}
|
||
|
|
else
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("Runtime Type must be a Structure or Array for AA");
|
||
|
|
ret = MVE_RT_TYPE;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* If successful, set the output AA count and log if enabled */
|
||
|
|
if (ret == SD_SUCCESS)
|
||
|
|
{
|
||
|
|
*num_aa_out = aa_app_ctrl.num_rtaa;
|
||
|
|
|
||
|
|
/* Post process to calculate the 'rtaa->el_size' values (for packed */
|
||
|
|
/* local representation). */
|
||
|
|
ms_rtaa_el_size_calc (*rt_aa_out, *num_aa_out);
|
||
|
|
|
||
|
|
if (mms_debug_sel & MMS_LOG_RTAA)
|
||
|
|
_ms_log_runtime_aa (*rt_aa_out, *num_aa_out);
|
||
|
|
|
||
|
|
/* save the high water mark */
|
||
|
|
if (*num_aa_out > m_hw_rt_aa_ctrl)
|
||
|
|
m_hw_rt_aa_ctrl = *num_aa_out;
|
||
|
|
}
|
||
|
|
else
|
||
|
|
{
|
||
|
|
chk_free (rtaa); /* If error, need to free the RTAA */
|
||
|
|
}
|
||
|
|
|
||
|
|
chk_free (all_rtaa); /* we are done with the 'all' RTAA */
|
||
|
|
S_UNLOCK_COMMON_RESOURCES ();
|
||
|
|
|
||
|
|
return (ret);
|
||
|
|
}
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/* We are working on a structure level, and need to copy the selected */
|
||
|
|
/* RTAA components for this nest level. This function can be called */
|
||
|
|
/* recursively as further nesting levels are encountered. */
|
||
|
|
/* The 'w_rtaa' parameter is the 'working' RTAA, and is used to select */
|
||
|
|
/* the scope (nest) for the operation */
|
||
|
|
|
||
|
|
static ST_RET get_struct_comps (AA_APPLY_CTRL *aa_app, RT_AA_CTRL *w_rtaa)
|
||
|
|
{
|
||
|
|
ST_RET ret;
|
||
|
|
RT_AA_CTRL *o_rtaa;
|
||
|
|
ALT_ACC_EL *aa;
|
||
|
|
ST_INT num_str_comp;
|
||
|
|
RT_AA_CTRL *start_rtaa;
|
||
|
|
RT_AA_CTRL *str_end_rtaa = NULL;
|
||
|
|
ST_BOOLEAN done;
|
||
|
|
|
||
|
|
/* get working pointers */
|
||
|
|
aa = aa_app->curr_aa; /* Current AA */
|
||
|
|
o_rtaa = aa_app->curr_rtaa; /* Output RTAA */
|
||
|
|
|
||
|
|
/* Check to see if we need to have the outer structure */
|
||
|
|
/* We need this if there are more than 1 named components selected */
|
||
|
|
|
||
|
|
if (count_num_comp (aa_app, aa, &num_str_comp))
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
|
||
|
|
if (num_str_comp != 1)
|
||
|
|
{
|
||
|
|
str_end_rtaa = find_end_rtaa (aa_app, w_rtaa);
|
||
|
|
if (!str_end_rtaa)
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
|
||
|
|
/* Write the start component of the output rtaa */
|
||
|
|
COPY_RTAA (o_rtaa,w_rtaa);
|
||
|
|
aa_app->num_rtaa++;
|
||
|
|
aa_app->curr_rtaa++;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Get all selected named components */
|
||
|
|
ret = SD_SUCCESS;
|
||
|
|
done = SD_FALSE;
|
||
|
|
while (!done && ret == SD_SUCCESS)
|
||
|
|
{
|
||
|
|
aa = aa_app->curr_aa; /* get current AA pointer */
|
||
|
|
o_rtaa = aa_app->curr_rtaa; /* get the output RTAA pointer */
|
||
|
|
|
||
|
|
/* This AA sel type can be a named component (w/wo further nesting) */
|
||
|
|
/* or a 'end nest' element. */
|
||
|
|
switch (aa->sel_type)
|
||
|
|
{
|
||
|
|
case AA_COMP :
|
||
|
|
/* This AA selects a entire named component. Just find the */
|
||
|
|
/* component name in the ALL RTAA and copy it's RTAA elements */
|
||
|
|
|
||
|
|
start_rtaa = find_named_comp (aa_app, aa->u.component, w_rtaa);
|
||
|
|
if (!start_rtaa)
|
||
|
|
{
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
}
|
||
|
|
ret = get_component_elmnts (aa_app, start_rtaa);
|
||
|
|
++aa_app->curr_aa;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case AA_COMP_NEST :
|
||
|
|
/* This AA selects a named component, with further selection. */
|
||
|
|
/* Find the component name in the ALL RTAA and call recursively */
|
||
|
|
/* to get the components. */
|
||
|
|
|
||
|
|
/* This component must be a structure or an array, so that we */
|
||
|
|
/* need to call recursively to get the selected RT AA elements */
|
||
|
|
|
||
|
|
start_rtaa = find_named_comp (aa_app, aa->u.component, w_rtaa);
|
||
|
|
if (!start_rtaa)
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
|
||
|
|
++aa_app->nest; /* Increment the nest level */
|
||
|
|
/* Point to the next AA */
|
||
|
|
if (aa_app->curr_aa < aa_app->aa_end)
|
||
|
|
++aa_app->curr_aa;
|
||
|
|
else
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("AA table too small");
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Based on the RT type, get the next level with the scope */
|
||
|
|
/* defined by the start RTAA. */
|
||
|
|
if (start_rtaa->rt->el_tag == RT_ARR_START)
|
||
|
|
{
|
||
|
|
ret = get_arr_elmnts (aa_app, start_rtaa);
|
||
|
|
}
|
||
|
|
else if (start_rtaa->rt->el_tag == RT_STR_START)
|
||
|
|
{
|
||
|
|
ret = get_struct_comps (aa_app, start_rtaa);
|
||
|
|
}
|
||
|
|
else
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("Incorrect RT Type for further nesting");
|
||
|
|
return (MVE_RT_TYPE);
|
||
|
|
}
|
||
|
|
--aa_app->nest; /* Decrement the nest level */
|
||
|
|
|
||
|
|
/* curr_aa should now point to our END_NEST, consume it */
|
||
|
|
if (aa_app->curr_aa->sel_type != AA_END_NEST)
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("Required AA_END_NEST not present");
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
}
|
||
|
|
else /* Consume the AA_END_NEST */
|
||
|
|
++aa_app->curr_aa;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case AA_END_NEST :
|
||
|
|
done = SD_TRUE; /* This level is complete */
|
||
|
|
break;
|
||
|
|
|
||
|
|
case AA_ALL :
|
||
|
|
case AA_ALL_NEST :
|
||
|
|
case AA_INDEX_NEST :
|
||
|
|
case AA_INDEX_RANGE_NEST :
|
||
|
|
case AA_INDEX :
|
||
|
|
case AA_INDEX_RANGE :
|
||
|
|
MLOG_NERR0 ("Incorrect AA sel_type for structure component selection");
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
break;
|
||
|
|
|
||
|
|
default :
|
||
|
|
MLOG_NERR0 ("Invalid AA sel_type");
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Prepare to look at next AA, if this was not the last */
|
||
|
|
if (aa_app->curr_aa > aa_app->aa_end)
|
||
|
|
done = SD_TRUE;
|
||
|
|
} /* End while getting named components at this level */
|
||
|
|
|
||
|
|
|
||
|
|
/* Don't continue if an error was detected */
|
||
|
|
if (ret)
|
||
|
|
return (ret);
|
||
|
|
|
||
|
|
|
||
|
|
/* Now copy the structure end element if required */
|
||
|
|
if (num_str_comp != 1)
|
||
|
|
{
|
||
|
|
o_rtaa = aa_app->curr_rtaa;
|
||
|
|
COPY_RTAA (o_rtaa, str_end_rtaa);
|
||
|
|
aa_app->num_rtaa++;
|
||
|
|
aa_app->curr_rtaa++;
|
||
|
|
}
|
||
|
|
|
||
|
|
return (ret);
|
||
|
|
}
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/* We are working on a array selection, and need to copy the selected */
|
||
|
|
/* RTAA components for this selection. This function can be called */
|
||
|
|
/* recusively as further nesting levels are encountered. */
|
||
|
|
/* The 'w_rtaa' parameter is the 'working' RTAA, and is used to select */
|
||
|
|
/* the scope (nest) for the operation */
|
||
|
|
|
||
|
|
|
||
|
|
static ST_RET get_arr_elmnts (AA_APPLY_CTRL *aa_app, RT_AA_CTRL *w_rtaa)
|
||
|
|
{
|
||
|
|
ST_RET ret;
|
||
|
|
ST_INT i;
|
||
|
|
RT_AA_CTRL *el_rtaa;
|
||
|
|
RT_AA_CTRL *o_rtaa;
|
||
|
|
RT_AA_CTRL *arr_end_rtaa = NULL;
|
||
|
|
ST_INT nest;
|
||
|
|
ALT_ACC_EL *aa;
|
||
|
|
ST_INT num_el;
|
||
|
|
ST_INT start_el;
|
||
|
|
ST_INT curr_el;
|
||
|
|
|
||
|
|
|
||
|
|
ret = SD_SUCCESS;
|
||
|
|
|
||
|
|
/* get working pointers */
|
||
|
|
aa = aa_app->curr_aa; /* Current AA */
|
||
|
|
o_rtaa = aa_app->curr_rtaa; /* Output RTAA */
|
||
|
|
|
||
|
|
/* This AA sel type must be one of the array selection types, */
|
||
|
|
/* (w/wo further nesting) */
|
||
|
|
|
||
|
|
/* Start by determining the number of elements and the start element */
|
||
|
|
switch (aa->sel_type)
|
||
|
|
{
|
||
|
|
case AA_INDEX :
|
||
|
|
case AA_INDEX_NEST :
|
||
|
|
num_el = 1;
|
||
|
|
start_el = (ST_INT) aa->u.index;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case AA_INDEX_RANGE :
|
||
|
|
case AA_INDEX_RANGE_NEST :
|
||
|
|
num_el = (ST_INT) aa->u.ir.num_elmnts;
|
||
|
|
start_el = (ST_INT) aa->u.ir.low_index;
|
||
|
|
if (!num_el && !start_el)
|
||
|
|
{
|
||
|
|
num_el = w_rtaa->rt->u.arr.num_elmnts;
|
||
|
|
start_el = 0;
|
||
|
|
}
|
||
|
|
break;
|
||
|
|
|
||
|
|
case AA_ALL :
|
||
|
|
case AA_ALL_NEST :
|
||
|
|
num_el = w_rtaa->rt->u.arr.num_elmnts;
|
||
|
|
start_el = 0;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case AA_COMP :
|
||
|
|
case AA_COMP_NEST :
|
||
|
|
MLOG_NERR0 ("Invalid AA Type");
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
break;
|
||
|
|
|
||
|
|
default :
|
||
|
|
MLOG_NERR0 ("Bad AA Type");
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* num_el is the number of elements to get, start_el is the base index */
|
||
|
|
/* w_rtaa points to the start of the array in the default RTAA */
|
||
|
|
|
||
|
|
/* Determine whether the array elements have further AA select ... */
|
||
|
|
if (aa->sel_type == AA_INDEX_NEST ||
|
||
|
|
aa->sel_type == AA_INDEX_RANGE_NEST ||
|
||
|
|
aa->sel_type == AA_ALL_NEST)
|
||
|
|
{
|
||
|
|
nest = SD_TRUE;
|
||
|
|
}
|
||
|
|
else
|
||
|
|
nest = SD_FALSE;
|
||
|
|
|
||
|
|
|
||
|
|
/* Check to see if we need to have the outer array */
|
||
|
|
/* We need this if there are more than 1 element selected */
|
||
|
|
|
||
|
|
if (num_el != 1)
|
||
|
|
{
|
||
|
|
arr_end_rtaa = find_end_rtaa (aa_app, w_rtaa);
|
||
|
|
if (!arr_end_rtaa)
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
|
||
|
|
/* Write the start component of the output rtaa */
|
||
|
|
COPY_RTAA (o_rtaa,w_rtaa);
|
||
|
|
aa_app->num_rtaa++;
|
||
|
|
aa_app->curr_rtaa++;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Now we work through the array elements, getting them one at a time */
|
||
|
|
curr_el = start_el;
|
||
|
|
for (i = 0; i < num_el && ret == SD_SUCCESS; ++i, ++curr_el)
|
||
|
|
{
|
||
|
|
aa_app->curr_aa = aa; /* Restore the working AA position */
|
||
|
|
o_rtaa = aa_app->curr_rtaa; /* Output RTAA */
|
||
|
|
|
||
|
|
/* Move the working RTAA pointer to the next element to be selected */
|
||
|
|
el_rtaa = find_arr_el (aa_app, w_rtaa, curr_el);
|
||
|
|
if (!el_rtaa)
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
|
||
|
|
/* If further selection is to take place, do it */
|
||
|
|
if (nest)
|
||
|
|
{
|
||
|
|
/* Set up working parameters for the nest level of nesting */
|
||
|
|
if (aa_app->curr_aa < aa_app->aa_end)
|
||
|
|
++aa_app->curr_aa;
|
||
|
|
else
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("AA table too small");
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
}
|
||
|
|
++aa_app->nest; /* Increment the nest level */
|
||
|
|
|
||
|
|
if (el_rtaa->rt->el_tag == RT_ARR_START)
|
||
|
|
{
|
||
|
|
ret = get_arr_elmnts (aa_app, el_rtaa);
|
||
|
|
}
|
||
|
|
else if (el_rtaa->rt->el_tag == RT_STR_START)
|
||
|
|
{
|
||
|
|
ret = get_struct_comps (aa_app, el_rtaa);
|
||
|
|
}
|
||
|
|
else /* Whoops, internal error */
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("Bad RT Type for further AA selection");
|
||
|
|
return (MVE_RT_TYPE);
|
||
|
|
}
|
||
|
|
--aa_app->nest; /* Decrement the nest level */
|
||
|
|
}
|
||
|
|
else /* No further selection, copy the compoment */
|
||
|
|
{
|
||
|
|
ret = get_component_elmnts (aa_app, el_rtaa);
|
||
|
|
}
|
||
|
|
} /* end for each selected element */
|
||
|
|
|
||
|
|
|
||
|
|
/* Now copy the array end element if required */
|
||
|
|
if (ret == SD_SUCCESS && num_el != 1)
|
||
|
|
{
|
||
|
|
o_rtaa = aa_app->curr_rtaa;
|
||
|
|
COPY_RTAA (o_rtaa, arr_end_rtaa);
|
||
|
|
aa_app->num_rtaa++;
|
||
|
|
aa_app->curr_rtaa++;
|
||
|
|
}
|
||
|
|
|
||
|
|
if (nest)
|
||
|
|
{
|
||
|
|
/* curr_aa should now point to our END_NEST, consume it */
|
||
|
|
if (aa_app->curr_aa->sel_type != AA_END_NEST)
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("Required AA_END_NEST not present");
|
||
|
|
ret = MVE_AA_SELECT;
|
||
|
|
}
|
||
|
|
else /* Consume the AA_END_NEST */
|
||
|
|
++aa_app->curr_aa;
|
||
|
|
}
|
||
|
|
else
|
||
|
|
++aa_app->curr_aa; /* Point to the next AA */
|
||
|
|
|
||
|
|
return (ret);
|
||
|
|
}
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/* Given the array or structure start RTAA pointer, return a pointer to */
|
||
|
|
/* the corresponding end element */
|
||
|
|
|
||
|
|
static RT_AA_CTRL *find_end_rtaa (AA_APPLY_CTRL *aa_app,
|
||
|
|
RT_AA_CTRL *start_rtaa)
|
||
|
|
{
|
||
|
|
SD_CONST RUNTIME_TYPE *start_rt;
|
||
|
|
SD_CONST RUNTIME_TYPE *end_rt;
|
||
|
|
ST_INT num_rt;
|
||
|
|
RT_AA_CTRL *rtaa;
|
||
|
|
|
||
|
|
start_rt = start_rtaa->rt;
|
||
|
|
if (start_rt->el_tag == RT_ARR_START)
|
||
|
|
{
|
||
|
|
num_rt = start_rt->u.arr.num_rt_blks;
|
||
|
|
}
|
||
|
|
else if (start_rt->el_tag == RT_STR_START)
|
||
|
|
{
|
||
|
|
num_rt = start_rt->u.str.num_rt_blks;
|
||
|
|
}
|
||
|
|
else
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("Bad RT Type");
|
||
|
|
return (NULL);
|
||
|
|
}
|
||
|
|
|
||
|
|
end_rt = start_rt + (num_rt + 1);
|
||
|
|
|
||
|
|
/* Just a trivial sanity check */
|
||
|
|
if (end_rt->el_tag != RT_ARR_END &&
|
||
|
|
end_rt->el_tag != RT_STR_END)
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("Bad RT Type");
|
||
|
|
return (NULL);
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Now find the RTAA that has a reference to the end structure */
|
||
|
|
/* within this scope (we hope!) */
|
||
|
|
|
||
|
|
for (rtaa = start_rtaa; rtaa <= aa_app->all_rtaa_end; ++rtaa)
|
||
|
|
{
|
||
|
|
if (rtaa->rt == end_rt)
|
||
|
|
return (rtaa);
|
||
|
|
}
|
||
|
|
|
||
|
|
MLOG_NERR0 ("End RT Not Found");
|
||
|
|
return (NULL);
|
||
|
|
}
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/* Copy the current RTAA element, including any sub-elements */
|
||
|
|
|
||
|
|
static ST_RET get_component_elmnts (AA_APPLY_CTRL *aa_app, RT_AA_CTRL *rtaa)
|
||
|
|
{
|
||
|
|
RT_AA_CTRL *last_rtaa;
|
||
|
|
RT_AA_CTRL *dest_rtaa;
|
||
|
|
|
||
|
|
if (rtaa->rt->el_tag == RT_ARR_START ||
|
||
|
|
rtaa->rt->el_tag == RT_STR_START)
|
||
|
|
{
|
||
|
|
last_rtaa = find_end_rtaa (aa_app, rtaa);
|
||
|
|
if (!last_rtaa)
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
}
|
||
|
|
else /* Simple element, just copy one */
|
||
|
|
last_rtaa = rtaa;
|
||
|
|
|
||
|
|
dest_rtaa = aa_app->curr_rtaa;
|
||
|
|
while (rtaa <= last_rtaa)
|
||
|
|
{
|
||
|
|
COPY_RTAA (dest_rtaa, rtaa);
|
||
|
|
aa_app->num_rtaa++;
|
||
|
|
aa_app->curr_rtaa++;
|
||
|
|
++dest_rtaa;
|
||
|
|
++rtaa;
|
||
|
|
}
|
||
|
|
return (SD_SUCCESS);
|
||
|
|
}
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/* Count the number of named components selected at this level */
|
||
|
|
/* by the alternate access select */
|
||
|
|
|
||
|
|
static ST_INT count_num_comp (AA_APPLY_CTRL *aa_app,
|
||
|
|
ALT_ACC_EL *aa,
|
||
|
|
ST_INT *count_out)
|
||
|
|
{
|
||
|
|
ST_INT count;
|
||
|
|
ST_INT nest;
|
||
|
|
ST_INT done;
|
||
|
|
|
||
|
|
done = SD_FALSE;
|
||
|
|
nest = 0;
|
||
|
|
count = 0;
|
||
|
|
while (done == SD_FALSE)
|
||
|
|
{
|
||
|
|
switch (aa->sel_type)
|
||
|
|
{
|
||
|
|
case AA_COMP :
|
||
|
|
if (nest == 0)
|
||
|
|
++count;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case AA_COMP_NEST :
|
||
|
|
if (nest == 0)
|
||
|
|
++count;
|
||
|
|
nest++;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case AA_INDEX :
|
||
|
|
case AA_INDEX_RANGE :
|
||
|
|
case AA_ALL :
|
||
|
|
break;
|
||
|
|
|
||
|
|
case AA_INDEX_NEST :
|
||
|
|
case AA_INDEX_RANGE_NEST :
|
||
|
|
case AA_ALL_NEST :
|
||
|
|
nest++;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case AA_END_NEST :
|
||
|
|
if (--nest < 0)
|
||
|
|
done = SD_TRUE;
|
||
|
|
break;
|
||
|
|
|
||
|
|
default :
|
||
|
|
MLOG_NERR0 ("Bad AA Type");
|
||
|
|
return (MVE_AA_SELECT);
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
|
||
|
|
if (aa >= aa_app->aa_end) /* If we are done (level 0 only) */
|
||
|
|
done = SD_TRUE;
|
||
|
|
|
||
|
|
aa++; /* Point to next */
|
||
|
|
}
|
||
|
|
|
||
|
|
*count_out = count;
|
||
|
|
return (SD_SUCCESS);
|
||
|
|
}
|
||
|
|
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/* Given a RTAA pointer, find a named component at the current nest */
|
||
|
|
/* The 'w_rtaa' parameter is the 'working' RTAA, and is used to select */
|
||
|
|
/* the scope (nest) for the operation */
|
||
|
|
|
||
|
|
static RT_AA_CTRL *find_named_comp (AA_APPLY_CTRL *aa_app,
|
||
|
|
ST_CHAR *name,
|
||
|
|
RT_AA_CTRL *w_rtaa)
|
||
|
|
{
|
||
|
|
ST_INT nest;
|
||
|
|
ST_INT err;
|
||
|
|
|
||
|
|
if (w_rtaa->rt->el_tag != RT_STR_START)
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("Bad RT Type - must be structure start");
|
||
|
|
return (NULL);
|
||
|
|
}
|
||
|
|
w_rtaa++;
|
||
|
|
|
||
|
|
nest = 0;
|
||
|
|
err = SD_FALSE;
|
||
|
|
while (!err)
|
||
|
|
{
|
||
|
|
if (nest == 0 &&
|
||
|
|
!strcmp (name, ms_comp_name_find (w_rtaa->rt)))
|
||
|
|
{
|
||
|
|
return (w_rtaa);
|
||
|
|
}
|
||
|
|
switch (w_rtaa->rt->el_tag)
|
||
|
|
{
|
||
|
|
case RT_ARR_START :
|
||
|
|
case RT_STR_START :
|
||
|
|
nest++;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_STR_END :
|
||
|
|
case RT_ARR_END :
|
||
|
|
if (--nest < 0)
|
||
|
|
break;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_BOOL :
|
||
|
|
case RT_BIT_STRING :
|
||
|
|
case RT_INTEGER :
|
||
|
|
case RT_UNSIGNED :
|
||
|
|
case RT_FLOATING_POINT :
|
||
|
|
case RT_OCTET_STRING :
|
||
|
|
case RT_VISIBLE_STRING :
|
||
|
|
case RT_GENERAL_TIME :
|
||
|
|
case RT_BINARY_TIME :
|
||
|
|
case RT_BCD :
|
||
|
|
case RT_UTC_TIME :
|
||
|
|
case RT_BOOLEANARRAY :
|
||
|
|
case RT_UTF8_STRING :
|
||
|
|
break;
|
||
|
|
|
||
|
|
default :
|
||
|
|
err = SD_TRUE;
|
||
|
|
MLOG_NERR0 ("Bad RT Type");
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
|
||
|
|
w_rtaa++;
|
||
|
|
if (w_rtaa >= aa_app->all_rtaa_end)
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
|
||
|
|
MLOG_NERR1 ("AA Named component (%s) not found", name);
|
||
|
|
return (NULL);
|
||
|
|
}
|
||
|
|
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/* Given a 'working' RTAA pointer to the RT_ARR_START element and the */
|
||
|
|
/* element index, return a pointer to the start RTAA for the element */
|
||
|
|
/* The 'w_rtaa' parameter is the 'working' RTAA, and is used to select */
|
||
|
|
/* the scope (nest) for the operation */
|
||
|
|
|
||
|
|
static RT_AA_CTRL *find_arr_el (AA_APPLY_CTRL *aa_app,
|
||
|
|
RT_AA_CTRL *w_rtaa,
|
||
|
|
ST_INT el_index)
|
||
|
|
{
|
||
|
|
RT_AA_CTRL *ret_rtaa;
|
||
|
|
SD_CONST RUNTIME_TYPE *arr_rt;
|
||
|
|
SD_CONST RUNTIME_TYPE *start_rt;
|
||
|
|
ST_INT el;
|
||
|
|
|
||
|
|
arr_rt = w_rtaa->rt;
|
||
|
|
if (arr_rt->el_tag != RT_ARR_START)
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("RTAA is not RT_ARR_START");
|
||
|
|
return (NULL);
|
||
|
|
}
|
||
|
|
if (el_index >= arr_rt->u.arr.num_elmnts)
|
||
|
|
{
|
||
|
|
MLOG_NERR0 ("Index out of range");
|
||
|
|
return (NULL);
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Now we need to locate the el_index'th element. To do this, we first */
|
||
|
|
/* get a pointer to the 0'th element's first RT block, then search for */
|
||
|
|
/* the el_index'th occurance of the RT within the RTAA */
|
||
|
|
|
||
|
|
w_rtaa++; /* 0'th element */
|
||
|
|
start_rt = w_rtaa->rt; /* Start RT block */
|
||
|
|
el = 0;
|
||
|
|
while (w_rtaa <= aa_app->all_rtaa_end) /* while still in RTAA */
|
||
|
|
{
|
||
|
|
if (w_rtaa->rt == start_rt) /* if start of an element */
|
||
|
|
{
|
||
|
|
if (el == el_index) /* if selected element */
|
||
|
|
return (w_rtaa); /* we found it */
|
||
|
|
else
|
||
|
|
++el; /* maybe next time */
|
||
|
|
}
|
||
|
|
w_rtaa++; /* look at next RTAA */
|
||
|
|
}
|
||
|
|
|
||
|
|
ret_rtaa = (w_rtaa+1) + (el_index * arr_rt->u.arr.num_rt_blks);
|
||
|
|
return (ret_rtaa);
|
||
|
|
}
|
||
|
|
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/* ms_rtaa_el_size_calc */
|
||
|
|
/************************************************************************/
|
||
|
|
|
||
|
|
/* Given a RTAA table, calculate the 'el_size' for each element. This */
|
||
|
|
/* is done by using the alignment control table, and is used only for */
|
||
|
|
/* encoding/decoding AA data that is 'packed' in local memory. */
|
||
|
|
|
||
|
|
static ST_VOID ms_rtaa_el_size_calc (RT_AA_CTRL *runtime_aa,
|
||
|
|
ST_INT num_rt_aa)
|
||
|
|
{
|
||
|
|
ST_INT ellen;
|
||
|
|
SD_CONST RUNTIME_TYPE *rt;
|
||
|
|
RT_AA_CTRL *rtaa_above;
|
||
|
|
ST_INT curr_offset;
|
||
|
|
ST_INT pad;
|
||
|
|
ST_INT algn;
|
||
|
|
ST_INT i;
|
||
|
|
|
||
|
|
curr_offset = 0; /* Offset from start of data */
|
||
|
|
rtaa_above = NULL;
|
||
|
|
for (i = 0; i < num_rt_aa; ++i, ++runtime_aa)
|
||
|
|
{
|
||
|
|
rt = runtime_aa->rt;
|
||
|
|
|
||
|
|
/* Get 'algnment index' and size of the element (excluding padding) */
|
||
|
|
_ms_m_get_rt_info (rt, &algn, &ellen);
|
||
|
|
|
||
|
|
/* Set the base element size, before padding */
|
||
|
|
runtime_aa->el_size = ellen;
|
||
|
|
|
||
|
|
/* Check to see if padding on the element above is required for */
|
||
|
|
/* alignment for this element, add it if so. */
|
||
|
|
/* Increment the offset until no bits are set that shouldn't be */
|
||
|
|
pad = 0;
|
||
|
|
while (curr_offset & algn)
|
||
|
|
{
|
||
|
|
curr_offset++;
|
||
|
|
pad++;
|
||
|
|
}
|
||
|
|
|
||
|
|
if (pad)
|
||
|
|
{
|
||
|
|
if (!rtaa_above) /* First element better not require alignment */
|
||
|
|
{
|
||
|
|
MLOG_ERR0 ("Alignment table error");
|
||
|
|
}
|
||
|
|
else /* add pad to element above */
|
||
|
|
rtaa_above->el_size += pad;
|
||
|
|
}
|
||
|
|
|
||
|
|
/* Save the pointer to the previous RT element (not this one's name) */
|
||
|
|
rtaa_above = runtime_aa;
|
||
|
|
|
||
|
|
/* Point past the current element */
|
||
|
|
curr_offset += ellen;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/* _ms_get_rtaa_data_size */
|
||
|
|
/************************************************************************/
|
||
|
|
|
||
|
|
ST_INT _ms_get_rtaa_data_size (RT_AA_CTRL *runtime_aa,
|
||
|
|
ST_INT num_rt_aa)
|
||
|
|
{
|
||
|
|
ST_INT i;
|
||
|
|
ST_INT size;
|
||
|
|
|
||
|
|
size = 0;
|
||
|
|
for (i = 0; i < num_rt_aa; ++i, ++runtime_aa)
|
||
|
|
size += runtime_aa->el_size;
|
||
|
|
return (size);
|
||
|
|
}
|
||
|
|
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/* LOGGING FUNCTIONS */
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/************************************************************************/
|
||
|
|
/* _ms_log_runtime_aa */
|
||
|
|
/************************************************************************/
|
||
|
|
|
||
|
|
ST_VOID _ms_log_runtime_aa (RT_AA_CTRL *rt_aa, ST_INT num_aa)
|
||
|
|
{
|
||
|
|
#ifdef DEBUG_SISCO
|
||
|
|
SD_CONST RUNTIME_TYPE *rt;
|
||
|
|
|
||
|
|
ST_INT i;
|
||
|
|
ST_INT indent;
|
||
|
|
SD_CONST ST_CHAR *comp_name;
|
||
|
|
/* Use these strings to keep logging aligned and indented as desired */
|
||
|
|
#define MAX_INDENT 5
|
||
|
|
SD_CONST ST_CHAR *sp[MAX_INDENT] =
|
||
|
|
{
|
||
|
|
" ",
|
||
|
|
" ",
|
||
|
|
" ",
|
||
|
|
" ",
|
||
|
|
" ",
|
||
|
|
};
|
||
|
|
SD_CONST ST_CHAR *sp2[MAX_INDENT] =
|
||
|
|
{
|
||
|
|
" ",
|
||
|
|
" ",
|
||
|
|
" ",
|
||
|
|
" ",
|
||
|
|
"",
|
||
|
|
};
|
||
|
|
|
||
|
|
S_LOCK_COMMON_RESOURCES ();
|
||
|
|
indent = 0;
|
||
|
|
MLOG_ALWAYS1 ("RTAA : %d elements", num_aa);
|
||
|
|
|
||
|
|
for (i = 0; i < num_aa; ++i, rt_aa++)
|
||
|
|
{
|
||
|
|
rt = rt_aa->rt;
|
||
|
|
comp_name = ms_comp_name_find (rt);
|
||
|
|
if (strlen (comp_name))
|
||
|
|
{
|
||
|
|
MLOG_CALWAYS3 ("%sNamed comp %s: %s",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
comp_name);
|
||
|
|
}
|
||
|
|
|
||
|
|
switch (rt->el_tag)
|
||
|
|
{
|
||
|
|
case RT_ARR_START :
|
||
|
|
MLOG_CALWAYS5 ("%sArray start %s: size %02d, %02d elmnts, %02d rt",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.arr.num_elmnts,
|
||
|
|
rt->u.arr.num_rt_blks);
|
||
|
|
if (++indent >= MAX_INDENT)
|
||
|
|
indent--;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_ARR_END :
|
||
|
|
if (--indent < 0)
|
||
|
|
indent++;
|
||
|
|
MLOG_CALWAYS5 ("%sArray end %s: size %02d, %02d elmnts, %02d rt",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.arr.num_elmnts,
|
||
|
|
rt->u.arr.num_rt_blks);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_STR_START :
|
||
|
|
MLOG_CALWAYS3 ("%sStruct start%s: size %02d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size);
|
||
|
|
if (++indent >= MAX_INDENT)
|
||
|
|
indent--;
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_STR_END :
|
||
|
|
if (--indent < 0)
|
||
|
|
indent++;
|
||
|
|
MLOG_CALWAYS3 ("%sStruct end %s: size %02d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_BOOL :
|
||
|
|
MLOG_CALWAYS5 ("%sBoolean %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_BIT_STRING :
|
||
|
|
MLOG_CALWAYS5 ("%sBitstring %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_INTEGER :
|
||
|
|
MLOG_CALWAYS5 ("%sInteger %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_UNSIGNED :
|
||
|
|
MLOG_CALWAYS5 ("%sUnsigned %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_FLOATING_POINT :
|
||
|
|
MLOG_CALWAYS5 ("%sFloat %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_OCTET_STRING :
|
||
|
|
MLOG_CALWAYS5 ("%sOctet Str %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_VISIBLE_STRING :
|
||
|
|
MLOG_CALWAYS5 ("%sVisible Str %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_GENERAL_TIME :
|
||
|
|
MLOG_CALWAYS5 ("%sGen Time %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_BINARY_TIME :
|
||
|
|
MLOG_CALWAYS5 ("%sBin Time %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_BCD :
|
||
|
|
MLOG_CALWAYS5 ("%sBCD %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_UTC_TIME :
|
||
|
|
MLOG_CALWAYS5 ("%sUtc Time %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
case RT_UTF8_STRING :
|
||
|
|
MLOG_CALWAYS5 ("%sUTF8 Str %s: size %02d, precision %02d, offset %d",
|
||
|
|
sp[indent],
|
||
|
|
sp2[indent],
|
||
|
|
rt_aa->el_size,
|
||
|
|
rt->u.p.el_len,
|
||
|
|
rt_aa->offset_to_data);
|
||
|
|
break;
|
||
|
|
|
||
|
|
default : /* should not be any other tag */
|
||
|
|
MLOG_CALWAYS1 (" **** UNKNOWN ELEMENT %02d ",i);
|
||
|
|
break;
|
||
|
|
}
|
||
|
|
}
|
||
|
|
S_UNLOCK_COMMON_RESOURCES ();
|
||
|
|
|
||
|
|
#endif
|
||
|
|
}
|
||
|
|
|