/****************************************************************************** *File name : MM_MISC.c *Version.Revision: 1.2 *Purpose: * This file contains the code to implement the the Division And Module * by IFSI and a boolean function thah is true if argument is even. * read_BSW_counters reads the counters set within the BootSW *Public Functions: * unsigned int is_even (unsigned int) * unsigned int IFSI_DIV (unsigned int, unsigned int) * unsigned int IFSI_MOD (unsigned int, unsigned int) * void read_BSW_counters(unsigned int *); *Description: * The code is straightforward *Creation Date & Author: 10-02-2006, Daniele Schito *Version, Update date & Author: 1.1, 08-03-2006 Daniele Schito * 1.2, 26-05-2006, SP * new function to read BootSW event counters ******************************************************************************/ #include #include #include"MM_MISC.h" /****************************************************************************** *Function name : is_even *Purpose: * This function return 1 if a is even otherwise 0 * *Syntax: * unsigned int = is_even (unsigned int a); *Input: * a : numerator; *Output: * *Return: * 1 if a is even otherwise 0 ******************************************************************************/ unsigned int is_even(unsigned int a) { return ~a & 1; } /****************************************************************************** *Function name : IFSI_DIV *Purpose: * This function compute quotient of an integer division * *Syntax: * unsigned int quotient = IFSI_DIV (unsigned int Dividend, * unsigned int Divisor); *Input: * Dividend : numerator; * Divisor : denominator; *Output: * *Return: * quotient: Dividend / Divisor ******************************************************************************/ unsigned int IFSI_DIV(unsigned int Dividend, unsigned int Divisor) { register unsigned int b; register unsigned int q = 0; b = Divisor; if (b == 0) return 0xFFFFFFFF; if (Dividend < b) return 0; if (b == 1) return Dividend; if (b == Dividend) return 1; //allign dividend and divisor b while ((b < Dividend) & (b < 0X80000000)) { b = b << 1; } do { q = q << 1; if (b <= Dividend) { Dividend -= b; q++; } b = b >> 1; } while (b >= Divisor); return q; // return quotient } /****************************************************************************** *Function name : IFSI_MOD *Purpose: * This function compute remnant of an integer division * *Syntax: * unsigned int remnant = IFSI_MOD (unsigned int Dividend, unsigned int Divisor); *Input: * Dividend : numerator; * Divisor : denominator; *Output: * *Return: * remnant: Dividend MOD Divisor ******************************************************************************/ unsigned int IFSI_MOD(unsigned int Dividend, unsigned int Divisor) { return Dividend - ( IFSI_DIV( Dividend, Divisor)* Divisor); // return the remnant } /****************************************************************************** *Function name : read_BSW_counters *Purpose: * This function is called when OBSW is started and reads the last values of * APID and event counters. If the most significant 16 bits of BOOT_SEQ_COUNTER * are set to MASK_FOR_APID_SSC then OBSW is being started from OBSW itself (eg * after patching), otherwise from bootSW. In the first case all the APIDs and * events counter are read, in the second case only first APID and counters of * events (5,1) and (5,4). Based on HERS-GEN-TN-CGS-001, Issue 1, 23/01/2006 * *Syntax: * read_BSW_counters(unsigned int * p_counters); *Input: * none *Output: * p_counters : pointer to an array of 9 elements. For the meaning see MM_MISC.h *Return: * none ******************************************************************************/ void read_BSW_counters(unsigned int *p_counters) { unsigned int pm * p_counter_BSW; unsigned int value, test, new_counter; unsigned int index; p_counter_BSW = (unsigned int pm * )BOOT_SEQ_COUNTER; value = *p_counter_BSW; test = value & 0xFFFF0000; new_counter = (value & 0xFFFF) + 1; p_counters[0] = (new_counter == 0x4000) ? 0 : new_counter; p_counter_BSW = (unsigned int pm * )BOOT_EVENT_51; p_counters[1] = (*p_counter_BSW + 1) & 0xFFFF; /* For events (5,4) I assume that counter 0 means no packet sent */ p_counter_BSW = (unsigned int pm * )BOOT_EVENT_54; value = *p_counter_BSW & 0xFFFF; p_counters[2] = (value == 0) ? 0 : value + 1; if (test != MASK_FOR_APID_SSC) /* OBSW starts after boot SW */ { memset(&p_counters[3],0,6); p_counter_BSW = (unsigned int pm * )BOOT_EVENT_52; memset(p_counter_BSW,MASK_FOR_APID_SSC,6); } else /* OBSW starts after patch or reset */ { p_counter_BSW = (unsigned int pm * )BOOT_EVENT_52; value = *p_counter_BSW & 0xFFFF; p_counters[3] = (value == MASK_FOR_APID_SSC) ? 0 : value + 1; for (index=OBSW_APID_2;index<=OBSW_APID_6;index++) { p_counter_BSW = (unsigned int pm * )index; value = *p_counter_BSW; new_counter = (value == MASK_FOR_APID_SSC) ? 0 : value + 1; p_counters[4+index-OBSW_APID_2] = (new_counter == 0x4000) ? 0 : new_counter; } } return; }