📄 load_meas.cxgate
字号:
#include "per_XDx512_L15Y.h"
#include "load_meas.h"
#pragma CODE_SEG XGATE_CODE
#pragma DATA_SEG __RPAGE_SEG XGATE_DATA
/* These routines are used to measure loading of XGATE by any software routines */
/* The algorithm uses ECT, but can be changed to use the PIT */
/* with ECT and the current implementation the max. period allowed for 1 measurement is 65535 bus cycles, i.e. 1.638ms @ 40MHz */
/* ECT overflow interrupt must be pointing to the lm_timekeeping routine */
/* lm_init must be linked to XGATE SW interrupt number LM_INIT_SWX */
/* example of use:
1. Initialise measurement on the CPU side:
SetIntPrio(0x6F, RQST|3); // ECT overflow
SetIntPrio(0x39-LM_INIT_SWX, RQST|1); // init
LM_INIT(); // initialise
2. Use lm_start and lm_stop ad the beginning and end of the XGATE routine to be evaluated:
lm_start(0);
...
...
lm_stop(0);
Argument of the lm_start/lm_stop call is 0..(LM_NO_OF_CHANNELS-1)
3. Read loading in lm_load array. 0 corresponds to 0% load, 65535 corresponds to 100% load
Remarks:
A) Longest measurement which can be done is 65535 bus cycles
B) The measurement has certain amount of natural inaccuracy, typically under 0.1% (depending on the number of calls to lm_start/lm_stop per measurement period)
Version:
1.0 Original coding
1.1 Added lm_peak_runtime to record maximum execution time on a given channel
*/
#if defined(LM_USE_ECT)
#define LM_INIT_TIMER() Timer.tscr1.byte=TEN|TSFRZ; Timer.tscr2.byte=TOI
#define LM_TIMER_VAL() Timer.tcnt.word
#define LM_TIMER_ICLR() Timer.tflg2.byte=TOF
#elif defined(LM_USE_PIT)
#error PIT NOT IMPLEMENTED YET
#endif
unsigned int lm_load[LM_NO_OF_CHANNELS]; /* 0=0%, 65535=100% */
unsigned int lm_peak_runtime[LM_NO_OF_CHANNELS]; /* peak execution time in bus cycles */
static unsigned long int lm_load_accumulator[LM_NO_OF_CHANNELS];
static unsigned int lm_start_time[LM_NO_OF_CHANNELS];
static unsigned int lm_timebase;
static unsigned int lm_overhead;
/* initialise the measurement */
void interrupt lm_init(void) {
char i;
XGATE.xgswt.word = (1<<LM_INIT_SWX)<<8; /* clear SW interrupt flag */
lm_timebase=(1<<LM_MEAS_PERIOD);
LM_INIT_TIMER();
lm_overhead=0;
lm_start(0);
lm_stop(0);
lm_overhead=lm_load_accumulator[0];
for (i=0;i<LM_NO_OF_CHANNELS;i++) {
lm_load[i]=0;
lm_load_accumulator[i]=0;
lm_peak_runtime[i]=0;
}
}
/* start measurement */
void lm_start(unsigned char channel) {
lm_start_time[channel]=LM_TIMER_VAL();
}
/* stop measurement */
void lm_stop(unsigned char channel) {
register unsigned int exec_time;
exec_time=(LM_TIMER_VAL()-lm_start_time[channel]-lm_overhead);
lm_load_accumulator[channel]+=exec_time;
if (lm_peak_runtime[channel]<exec_time) lm_peak_runtime[channel]=exec_time;
}
/* timebase for the calculation */
void interrupt lm_timekeeping(void) {
LM_TIMER_ICLR(); /* clear the interrupt flag */
lm_timebase--;
if (lm_timebase==0) {
/* time is up, calculate loads */
unsigned char i;
for (i=0;i<LM_NO_OF_CHANNELS;i++) {
lm_load[i]=lm_load_accumulator[i]>>LM_MEAS_PERIOD; /* calculate the load */
lm_load_accumulator[i]=0; /* clear the accumulator */
}
/* reinitialise timebase */
lm_timebase=(1<<LM_MEAS_PERIOD);
}
}
⌨️ 快捷键说明
复制代码
Ctrl + C
搜索代码
Ctrl + F
全屏模式
F11
切换主题
Ctrl + Shift + D
显示快捷键
?
增大字号
Ctrl + =
减小字号
Ctrl + -