Your Browser is not longer supported

Please use Google Chrome, Mozilla Firefox or Microsoft Edge to view the page correctly
Loading...

{{viewport.spaceProperty.prod}}

Example

The following example, which is also in the SYSLIB.SM2.<ver> library.
It clarifies the use of the SM2GMS and SM2GDAT macros. To begin with, the sample program outputs the host name and obtains the SM2 online monitoring cycle. The data of the SM2 data buffers BASIC, SDEVICE, TIME_IO and DAB are then output in the cycle of the SM2 online monitoring cycle. Each of these data buffers serves as an example for one of four data buffer types:

  • BASIC data buffer (type 1)
    The time stamp of the monitoring cycle is output and the number of samples in the cycle obtained.

  • SDEVICE data buffer (type 2)
    The utilization of each device whose utilization with regard to DMS I/Os exceeds a threshold value is output.

  • TIME-IO data buffer (type 3)
    The number of active logical machines is output, together with the CPU utilization for each active logical machine whose CPU utilization exceeds a threshold value.

  • DAB data buffer (type 4)
    The number of reads and the number of read hits are output for each DAB buffer.

Note in the SM2GDAT example that a value of 0 is specified for the “length_buffer” parameter in the first call in order to determine the actually required size of “length_buffer”.

#include <stdio.h>
#include <stdlib.h>
#include <signal.h>

#include "FHDR.H"
#include "SM2GMS.H"
#include "SM2GDAT.H"
#include "SM2RC.H"

#define  SHORT_TIME  1
#define  LONG_TIME   60

#define  WAIT_SHORT_AND_TRY_AGAIN   0
#define  WAIT_LONG_AND_TRY_AGAIN    1
#define  BUFFER_TOO_SHORT           2
#define  TERMINATE_PROGRAM          3

#define  NOT_DEFINED   0
#define  NOT_SET   0
#define  SET       1

#define  SIZE_4K_PAGE   4096

#define  DMS_IOS_THRESHOLD_VALUE           60.0
#define  CPU_UTILIZATION_THRESHOLD_VALUE   50.0

typedef   struct SM2GDAT_buffer_header_mdl      StrBufferHeader;
typedef   struct SM2GDAT_basic_single_mdl       StrBASICsingle;
typedef   struct SM2GDAT_sdevice_multiple_mdl   StrSDEVICEmultiple;
typedef   struct SM2GDAT_time_io_single_mdl     StrTIME_IOsingle;
typedef   struct SM2GDAT_time_io_multiple_mdl   StrTIME_IOmultiple;
typedef   struct SM2GDAT_dab_single_mdl         StrDABsingle;
typedef   struct SM2GDAT_dab_buffer_area_mdl    StrDAB_BUFFER_AREAmultiple;
typedef   struct SM2GDAT_dab_partial_area_mdl   StrDAB_PARTIAL_AREAmultiple;
typedef   unsigned char                         Uchar;

struct SM2GMS_get_measurement_stat_mdl SM2_STATUS;
struct SM2GDAT_get_data_mdl SM2_DATA;
struct SM2GDAT_global_header_mdl *GlobalHeader_ptr;
struct StrBufferHeader *BufferHeader_ptr;

void *buffer_ptr;
long length_buffer = 0L;  /* initialized with 0L for the first call of SM2GDAT */
int Cycle;
int NumberSamples;
char DABData;
char LocalHostName[] = "        ";

void TerminateProgram( char * );

void main( void )
{
 void GetSM2StatusInformations( void );
 void CallSM2GDAT( double );
 void ShowBASICData( void );
 void ShowSDEVICEData( void );
 void ShowTIME_IOData( void );
 void ShowDABData( void );

 GetSM2StatusInformations( );

 for( ; ; )
 {
     CallSM2GDAT(   SM2GDAT_BUFFER_BASIC         /* data buffer of type 1 */
                  + SM2GDAT_BUFFER_SDEVICE       /* data buffer of type 2 */
                  + SM2GDAT_BUFFER_TIME_IO       /* data buffer of type 3 */
                  + SM2GDAT_BUFFER_DAB );        /* data buffer of type 4 */

     ShowBASICData( );
     ShowSDEVICEData( );
     ShowTIME_IOData( );
     ShowDABData( );

     sleep( Cycle );
 }

 exit( 0 );
}

void TerminateProgram( char *Message )
{
 printf( "\n\n%s\n\n", Message );
 printf( "Program abnormally terminated.\n" );
 exit( -1 );
}

void GetSM2StatusInformations( void )
{
 char TRY_AGAIN;
 char Message[100];
 int Errorhandling( int, int, char * );

 TRY_AGAIN = 'y';
 while( TRY_AGAIN == 'y' )
 {
    SM2GMS( SM2_STATUS, LocalHostName );   /* calling macro SM2GMS */
    if( SM2_STATUS.hdr.FHDR_RC_MAINCODE == FHDRsuccessful_processing )
       TRY_AGAIN = 'n';
    else
    {
       switch( Errorhandling( ( int )SM2_STATUS.hdr.FHDR_RC_MAINCODE,
                              ( int )SM2_STATUS.hdr.FHDR_RC_SUBCODE1,
                              Message ) )
       {
          case WAIT_SHORT_AND_TRY_AGAIN:
                 sleep( SHORT_TIME );
                 TRY_AGAIN = 'y';
                 break;

          case WAIT_LONG_AND_TRY_AGAIN:
                 sleep( LONG_TIME );
                 TRY_AGAIN = 'y';
                 break;

          case TERMINATE_PROGRAM:
                 TerminateProgram( Message );
                 break;

          default:
                 TerminateProgram( "Unexpected return code from SM2GMS.\n" );
                 break;
       }
    }
 }

 printf( "Host:  %8.8s\n", SM2_STATUS.status.endsystem_name );

 if( SM2_STATUS.status.online_cycle == NOT_DEFINED )
    Cycle = SM2_STATUS.status.offline_cycle;
 else
    Cycle = SM2_STATUS.status.online_cycle;

 if( SM2_STATUS.status.active_programs.flag.dab == SET )
    DABData = 'y';      /* measurement program DAB is active */
 else
    DABData = 'n';      /* measurement program DAB is not active */
}

void CallSM2GDAT( double BufferSelection )
{
 char Message[100];
 int Errorhandling( int, int, char * );
 void GetMemory( void );
 char TRY_AGAIN;

 TRY_AGAIN = 'y';
 while( TRY_AGAIN == 'y' )
 {
    /* calling macro SM2GDAT to get the data buffers */
    SM2GDAT( SM2_DATA, length_buffer, buffer_ptr, BufferSelection, LocalHostName );

    if( SM2_DATA.hdr.FHDR_RC_MAINCODE == FHDRsuccessful_processing )
       TRY_AGAIN = 'n';
    else
    {
       switch( Errorhandling( ( int )SM2_DATA.hdr.FHDR_RC_MAINCODE,
                              ( int )SM2_DATA.hdr.FHDR_RC_SUBCODE1,
                              Message ) )
       {
          case WAIT_SHORT_AND_TRY_AGAIN:
                 sleep( SHORT_TIME );
                 TRY_AGAIN = 'y';
                 break;

          case WAIT_LONG_AND_TRY_AGAIN:
                 sleep( LONG_TIME );
                 TRY_AGAIN = 'y';
                 break;

          case BUFFER_TOO_SHORT:
                 /* needed buffer_length has increased since the last call of SM2GDAT */
                 /* this return code is especially expected for the first call of */
                 /* SM2GDAT, because length_buffer is initialized with 0 */
                 length_buffer = SM2_DATA.length_buffer; /* copy the needed size */
                 GetMemory( );      /* allocate memory for the output area */
                 TRY_AGAIN = 'y';
                 break;

          case TERMINATE_PROGRAM:
                 TerminateProgram( Message );
                 break;

          default:
                 TerminateProgram( "Unexpected return code from SM2GDAT.\n" );
                 break;
       }
    }
 }
 
 /* initialize pointer to evaluate the global header */
 GlobalHeader_ptr = ( struct SM2GDAT_global_header_mdl * )buffer_ptr;
}

int Errorhandling( int MAINCODE, int SUBCODE1, char *Message )
{
 switch( MAINCODE )
 {
    case FHDRlinkage_error:
            switch( SUBCODE1 )
            {
               case FHDRfct_not_supported:
               case FHDRfct_not_available:
               case FHDRver_not_supported:
               case FHDRalignment_error:
               case FHDRss_not_created:
                       break;

               case FHDRwait_short_term:
                       return( WAIT_SHORT_AND_TRY_AGAIN );

               case FHDRwait_long_term:
                       return( WAIT_LONG_AND_TRY_AGAIN );

               default:
                       break;
            }

            break;

    case SM2RCbuffer_too_short:
            return( BUFFER_TOO_SHORT );

    case SM2RCno_data:
            return( WAIT_SHORT_AND_TRY_AGAIN );

    case SM2RCbuffer_not_valid:
    case SM2RCsystem_error:
    case SM2RCgatherer_down:
            break;

    default:
            break;
 }

 sprintf( Message, "MAINCODE: %d, SUBCODE1: %d",
                    MAINCODE, SUBCODE1 );

 return( TERMINATE_PROGRAM );
}

void GetMemory( void )
{
 static char FirstCall = 'y';

 if( FirstCall == 'y' )
    FirstCall = 'n';
 else
    free( buffer_ptr );

 buffer_ptr = ( Uchar *)malloc((unsigned int)( SIZE_4K_PAGE * length_buffer ));
 
 if( buffer_ptr == NULL )
    TerminateProgram( "malloc( ): Not enough memory." );
}

/*
 *    evaluates the BASIC data buffer - this is an example to evaluate
 *                                      a data buffer of type 1
 */
void ShowBASICData( void )
{
 StrBufferHeader *BufferHeader_ptr;
 StrBASICsingle *BASICsingle_ptr;

 /* initialize pointer to evaluate the buffer header of the BASIC data buffer */
 BufferHeader_ptr = ( StrBufferHeader * )GlobalHeader_ptr->basic_ptr;

 if( BufferHeader_ptr->state.valid == NOT_SET ) /* no valid data in data buffer */
 {
    printf( "Data in BASIC-Buffer not valid.\n" );
    return;
 }

 /* initialize pointer to evaluate the fixed data area of the BASIC data buffer */
 BASICsingle_ptr = 
 ( StrBASICsingle * ) ( ( Uchar * ) BufferHeader_ptr + BufferHeader_ptr->fixed_part_dsp );

 printf( "\n\nTime stamp of cycle:   %10.10s %8.8s\n",
         BASICsingle_ptr->date, BASICsingle_ptr->time );

 NumberSamples = BASICsingle_ptr->samples;
}

/*
 *    evaluates the SDEVICE data buffer - this is an example to evaluate
 *                                        a data buffer of type 2
 */
void ShowSDEVICEData( void )
{
 StrBufferHeader *BufferHeader_ptr;
 StrSDEVICEmultiple *SDEVICEmultiple_ptr;
 Uchar *Multiple_ptr;
 int LengthMultipleGroup;
 int NumberMultipleGroups;
 float DmsBusy;
 int i;

 /* initialize pointer to evaluate the buffer header of the SDEVICE data buffer */
 BufferHeader_ptr = ( StrBufferHeader * )GlobalHeader_ptr->sdevice_ptr;

 if( BufferHeader_ptr->state.valid == NOT_SET ) /* no valid data in data buffer */
 {
    printf( "\nData in SDEVICE-Buffer not valid.\n" );
    return;
 }

 LengthMultipleGroup = BufferHeader_ptr->length_group;
 NumberMultipleGroups = BufferHeader_ptr->number_groups;

 /* initialize pointer with the address of the first repeat group */
 Multiple_ptr = ( Uchar * ) BufferHeader_ptr + BufferHeader_ptr->first_group_dsp;

 printf( "\n" );
 for( i = 0; i != NumberMultipleGroups; i++, Multiple_ptr += LengthMultipleGroup )
 {
     /* initialize pointer to evaluate the repeat group of the SDEVICE data buffer */
     SDEVICEmultiple_ptr = ( StrSDEVICEmultiple * ) Multiple_ptr;
     DmsBusy = ( SDEVICEmultiple_ptr->busy_dms * 100.0 ) / NumberSamples;

     if( DmsBusy >= DMS_IOS_THRESHOLD_VALUE )
        printf( "Utilization of VSN %6.6s, MN %4.4s, Type %02x: %f\n",
                 SDEVICEmultiple_ptr->vsn,
                 SDEVICEmultiple_ptr->mnemonic,
                 SDEVICEmultiple_ptr->type[1],
                 DmsBusy );
 }
}

/*
 *    evaluates the TIME_IO data buffer - this is an example to evaluate
 *                                        a data buffer of type 3
 */
void ShowTIME_IOData( void )
{
 StrBufferHeader *BufferHeader_ptr;
 StrTIME_IOsingle *TIME_IOsingle_ptr;
 StrTIME_IOmultiple *TIME_IOmultiple_ptr;
 Uchar *Multiple_ptr;
 int LengthMultipleGroup;
 int NumberMultipleGroups;
 float SUM, CPU_Utilization;
 int i;

 /* initialize pointer to evaluate the buffer header of the TIME_IO data buffer */
BufferHeader_ptr = ( StrBufferHeader * )GlobalHeader_ptr->time_io_ptr;

if( BufferHeader_ptr->state.valid == NOT_SET ) /* no valid data in data buffer */
{
   printf( "\nData in TIME_IO-Buffer not valid.\n" );
   return;
}

/* initialize pointer to evaluate the fixed data area of the TIME_IO data buffer */
TIME_IOsingle_ptr = ( StrTIME_IOsingle * ) ( ( Uchar * ) BufferHeader_ptr
                                     + BufferHeader_ptr->fixed_part_dsp );

printf( "\nNumber active logical machines:  %d\n",
        TIME_IOsingle_ptr->active_lm );

LengthMultipleGroup = BufferHeader_ptr->length_group;
NumberMultipleGroups = BufferHeader_ptr->number_groups;

/* initialize pointer with the address of the first repeat group */
Multiple_ptr = ( Uchar * ) BufferHeader_ptr + BufferHeader_ptr->first_group_dsp;

for( i = 0; i != NumberMultipleGroups; i++, Multiple_ptr += LengthMultipleGroup )
{
    /* initialize pointer to evaluate the repeat group of the TIME_IO data buffer */
    TIME_IOmultiple_ptr = ( StrTIME_IOmultiple * ) Multiple_ptr;
    SUM = (  TIME_IOmultiple_ptr->tu_time
           + TIME_IOmultiple_ptr->tpr_time
           + TIME_IOmultiple_ptr->sih_time );

    if( ( SUM + TIME_IOmultiple_ptr->idle_time ) > 0 )
       CPU_Utilization = ( SUM * 100.0 ) / ( SUM + TIME_IOmultiple_ptr->idle_time );
    else
       CPU_Utilization = 0.0;

    if( i == 0 )
    {
       /* the first repeat group contains the average values of all logical machines */
       printf( "Average CPU utilization of all logical machines:  %f %%\n",
               CPU_Utilization );
    }
    else
    {
        if( CPU_Utilization >= CPU_UTILIZATION_THRESHOLD_VALUE )
           printf( "CPU utilization logical machine %d:  %f %%\n",
                   i, CPU_Utilization );
    }
 }
}

/*
 *    evaluates the DAB data buffer - this is an example to evaluate
 *                                    a data buffer of type 4
 */
void ShowDABData( void )
{
 StrBufferHeader *BufferHeader_ptr;
 StrDABsingle *DABsingle_ptr;
 StrDAB_BUFFER_AREAmultiple *DAB_BUFFER_AREAmultiple_ptr;
 Uchar *Multiple_ptr;
 int LengthMultipleGroup;
 int NumberMultipleGroups;
 long reads, read_hits;
 int i;

 void EvaluatePartialAreas( int, StrDABsingle *, long *, long *);

 if( DABData == 'n' )
 {
    printf( "\nMeasurement program DAB is not active.\n" );
    return;
 }

 /* initialize pointer to evaluate the buffer header of the DAB data buffer */
 BufferHeader_ptr = ( StrBufferHeader * )GlobalHeader_ptr->dab_ptr;

 if( BufferHeader_ptr->state.valid == NOT_SET ) /* no valid data in data buffer */
 {
    printf( "\nData in DAB-Buffer not valid.\n" );
    return;
 }

 /* initialize pointer to evaluate the fixed data area of the DAB data buffer */
 DABsingle_ptr = 
 ( StrDABsingle * ) ( ( Uchar * ) BufferHeader_ptr + BufferHeader_ptr->fixed_part_dsp );

 if( DABsingle_ptr->reconfigurations != 0 ) /* DAB reconfiguration */
 {
    printf( "\nDAB reconfiguration in last cycle.\n" );
    return;
 }

 LengthMultipleGroup = DABsingle_ptr->length_buffer_area_group;
 NumberMultipleGroups = DABsingle_ptr->number_buffer_area_groups;

 /* initialize pointer with the address of the first buffer area repeat group */
 Multiple_ptr = ( Uchar * ) DABsingle_ptr + DABsingle_ptr->first_buffer_area_group_dsp;

 printf( "\n" );
 for( i = 0; i != NumberMultipleGroups; i++, Multiple_ptr += LengthMultipleGroup )
 {
     reads = read_hits = 0L;

     /* initialize pointer to evaluate the buffer area repeat group of the DAB data buffer */
     DAB_BUFFER_AREAmultiple_ptr = ( StrDAB_BUFFER_AREAmultiple * ) Multiple_ptr;

     EvaluatePartialAreas( i + 1, DABsingle_ptr, &reads, &read_hits );

     printf( "DAB buffer  %-32.32s:   reads:  %ld, read_hits:  %ld\n",
             DAB_BUFFER_AREAmultiple_ptr->id, reads, read_hits );
 }
}

void EvaluatePartialAreas( int BufferIndex, StrDABsingle *DABsingle_ptr,
                           long *reads, long *read_hits )
{
 StrDAB_PARTIAL_AREAmultiple *DAB_PARTIAL_AREAmultiple_ptr;
 Uchar *Multiple_ptr;
 int LengthMultipleGroup;
 int NumberMultipleGroups;
 int i;

 LengthMultipleGroup = DABsingle_ptr->length_partial_area_group;
 NumberMultipleGroups = DABsingle_ptr->number_partial_area_groups;

 /* initialize pointer with the address of the first partial area repeat group */
 Multiple_ptr = ( Uchar * ) DABsingle_ptr + DABsingle_ptr->first_partial_area_group_dsp;

 for( i = 0; i != NumberMultipleGroups; i++, Multiple_ptr += LengthMultipleGroup )
 {
     /* initialize pointer to evaluate the buffer area repeat group of the DAB data buffer */
     DAB_PARTIAL_AREAmultiple_ptr = ( StrDAB_PARTIAL_AREAmultiple * ) Multiple_ptr;

     /* the partial area belongs to the buffer and was served in the monitoring cycle */
     if(    DAB_PARTIAL_AREAmultiple_ptr->buffer_index == BufferIndex
         && DAB_PARTIAL_AREAmultiple_ptr->state == SM2GDATserved )
     {
        *reads += DAB_PARTIAL_AREAmultiple_ptr->transfers.read;
        *read_hits += DAB_PARTIAL_AREAmultiple_ptr->transfers.read_hit;
     }
 }
}