Performance testing

I’m running QNX 6.2.1 on an Intel PIII and I’m testing an application to see
how well it is able to maintain a 1 msec run interval while other processes
are going running. I started the test by running the test application in
photon and I had some fairly wide ranging run intervals, so I then shutdown
photon and ran it from the shell and had the same results. I even tried
changing the priority of the application from 22 to 25 and then up to 62 and
that didn’t help either. What I’ve been seeing is that the run interval is
normally just about 1 msec (1.0003 to .9996 msec) but every 6 or 7 seconds
the 1 msec run interval is missed, sometimes the run interval is measured as
2 msec and in some instances it’s over 5 msec.

Here is what I’m doing, I first set the ClockPeriod to 1 msec, and set the
scheduling to FIFO. I register a pulse to be delivered every 1 msec with
timer_create and then have my process loop on a MsgReceive call waiting for
the pulses from the timer. Right before I call the main part of the
application I call ClockCycles and check to see how many cycles have gone by
since my application ran, and for some reason I’m getting same very odd
results. I’m not sure if I’m using ClockCycles incorrectly or if the 1 msec
clock pulse is just not capable of being delivered that quick. Attached is
some of the code… I appreciate any help or ideas anyone may have. I’m
hoping this is a problem with the way I’m using ClockCycles.


Here are some snippets of what I’m doing…


setting the ClockPeriod…

program->process_id = getpid();


program->process_started = time(NULL);

program->process_exit_status = 0;




param.sched_priority = getprio(0);

if (sched_setscheduler(0,SCHED_FIFO,&param ) == -1)

{

debug(-1, module, “Can’t sched_setscheduler(): error
= (%d): %s”,


errno, strerror(errno));

return(TBC_ERROR);

}



//==============================================

// Set the system timer resolution

//==============================================

new_clock_period.nsec = 1000000; // 1 msec = 1,000,000 nsec




if (ClockPeriod(CLOCK_REALTIME, &new_clock_period,
&original_clock_period, 0) == -1)

{

debug(-1, module,“Can’t
ClockPeriod(CLOCK_REALTIME,new_clock_period, original_clock_period, 0): (%d)
%s”,

errno, strerror(errno));

return(ERROR);

}





Here is the section where I set the run timer for this process…


Progstat->chid = ChannelCreate(_NTO_CHF_FIXED_PRIORITY);
dpp = _dispatch_create(Progstat->chid, 0);
name_ptr = name_attach(dpp, Progstat->process_name, NULL);


event.sigev_coid = ConnectAttach(ND_LOCAL_NODE, 0,
Progstat->chid,
_NTO_SIDE_CHANNEL, 0);

event.sigev_notify = SIGEV_PULSE;

event.sigev_priority = getprio(0);
event.sigev_code = PULSE_RUN_MESSAGE;

if (timer_create(CLOCK_REALTIME, &event,&tid) == -1)
{
Debug(-1, module, “Can’t timer_create(): (%d) %s”, errno,
strerror(errno));
return(ERROR);
}

//========================================
// Set the timer interval
//========================================
run_timer_spec.it_value.tv_sec = msec / 1000;
run_timer_spec.it_value.tv_nsec = (msec % 1000) * 1000000;
run_timer_spec.it_interval.tv_sec = run_timer_spec.it_value.tv_sec;
run_timer_spec.it_interval.tv_nsec =
run_timer_spec.it_value.tv_nsec;

if (timer_settime(tid, 0, &run_timer_spec, NULL) == -1)
{
Debug(-1, module, “Can’t timer_settime(): (%d) %s”,
errno, strerror(errno));
return(ERROR);
}





and finally here is code for how to figure out the time between pulses…

static uint64_t cycles_per_msec = 0, cycles_per_sec = 0, new_time=0,
old_time=0, run_interval_time = 0;
float diff = 0;
static unsigned short int expired_ticks=0;

cycles_per_sec = SYSPAGE_ENTRY(qtime)->cycles_per_sec;
cycles_per_msec = (cycles_per_sec / 1000.0);




while loop on MsgReceive()





//==================================================
// capture the time when we start to run, and compare it to the last run

// time.
//==================================================
run_interval_time = new_time;
new_time = ClockCycles();

if ((new_time >= run_interval_time)
&& (run_interval_time != 0))
{
diff = (float) ((float)(new_time - run_interval_time) /
cycles_per_msec);
expired_ticks = (unsigned short int) ((new_time - run_interval_time)
/ cycles_per_msec);


// store the last number of ticks that expired for the interval
Progstat->process_last_run_interval = diff;

debug(0, module, “Run Interval = %lf, expired ticks = %d”, diff,
expired_ticks,);

}




//==================================================
// call the run function passed in…
//==================================================
if (run_func() != OK)
{
Debug(-1, module, “Can’t run_func()”);
return(ERROR);
}

















\

Scott
cscott_76@NOSPAMyahoo.com
Delete NOSPAM for email.

Check out the thread “Tick-tock Part II - Understanding the Neutrino micro
kernel’s concept of time” in qdn.public.articles. Basically, you can’t set the
clock period to exactly 1000000 ns.

Murf

“C. Scott” wrote:

I’m running QNX 6.2.1 on an Intel PIII and I’m testing an application to see
how well it is able to maintain a 1 msec run interval while other processes
are going running. I started the test by running the test application in
photon and I had some fairly wide ranging run intervals, so I then shutdown
photon and ran it from the shell and had the same results. I even tried
changing the priority of the application from 22 to 25 and then up to 62 and
that didn’t help either. What I’ve been seeing is that the run interval is
normally just about 1 msec (1.0003 to .9996 msec) but every 6 or 7 seconds
the 1 msec run interval is missed, sometimes the run interval is measured as
2 msec and in some instances it’s over 5 msec.

Here is what I’m doing, I first set the ClockPeriod to 1 msec, and set the
scheduling to FIFO. I register a pulse to be delivered every 1 msec with
timer_create and then have my process loop on a MsgReceive call waiting for
the pulses from the timer. Right before I call the main part of the
application I call ClockCycles and check to see how many cycles have gone by
since my application ran, and for some reason I’m getting same very odd
results. I’m not sure if I’m using ClockCycles incorrectly or if the 1 msec
clock pulse is just not capable of being delivered that quick. Attached is
some of the code… I appreciate any help or ideas anyone may have. I’m
hoping this is a problem with the way I’m using ClockCycles.

Here are some snippets of what I’m doing…

setting the ClockPeriod…

program->process_id = getpid();

program->process_started = time(NULL);

program->process_exit_status = 0;

param.sched_priority = getprio(0);

if (sched_setscheduler(0,SCHED_FIFO,&param ) == -1)

{

debug(-1, module, “Can’t sched_setscheduler(): error
= (%d): %s”,

errno, strerror(errno));

return(TBC_ERROR);

}

//==============================================

// Set the system timer resolution

//==============================================

new_clock_period.nsec = 1000000; // 1 msec = 1,000,000 nsec

if (ClockPeriod(CLOCK_REALTIME, &new_clock_period,
&original_clock_period, 0) == -1)

{

debug(-1, module,“Can’t
ClockPeriod(CLOCK_REALTIME,new_clock_period, original_clock_period, 0): (%d)
%s”,

errno, strerror(errno));

return(ERROR);

}

Here is the section where I set the run timer for this process…

Progstat->chid = ChannelCreate(_NTO_CHF_FIXED_PRIORITY);
dpp = _dispatch_create(Progstat->chid, 0);
name_ptr = name_attach(dpp, Progstat->process_name, NULL);

event.sigev_coid = ConnectAttach(ND_LOCAL_NODE, 0,
Progstat->chid,
_NTO_SIDE_CHANNEL, 0);

event.sigev_notify = SIGEV_PULSE;

event.sigev_priority = getprio(0);
event.sigev_code = PULSE_RUN_MESSAGE;

if (timer_create(CLOCK_REALTIME, &event,&tid) == -1)
{
Debug(-1, module, “Can’t timer_create(): (%d) %s”, errno,
strerror(errno));
return(ERROR);
}

//========================================
// Set the timer interval
//========================================
run_timer_spec.it_value.tv_sec = msec / 1000;
run_timer_spec.it_value.tv_nsec = (msec % 1000) * 1000000;
run_timer_spec.it_interval.tv_sec = run_timer_spec.it_value.tv_sec;
run_timer_spec.it_interval.tv_nsec =
run_timer_spec.it_value.tv_nsec;

if (timer_settime(tid, 0, &run_timer_spec, NULL) == -1)
{
Debug(-1, module, “Can’t timer_settime(): (%d) %s”,
errno, strerror(errno));
return(ERROR);
}

and finally here is code for how to figure out the time between pulses…

static uint64_t cycles_per_msec = 0, cycles_per_sec = 0, new_time=0,
old_time=0, run_interval_time = 0;
float diff = 0;
static unsigned short int expired_ticks=0;

cycles_per_sec = SYSPAGE_ENTRY(qtime)->cycles_per_sec;
cycles_per_msec = (cycles_per_sec / 1000.0);

while loop on MsgReceive()

//==================================================
// capture the time when we start to run, and compare it to the last run

// time.
//==================================================
run_interval_time = new_time;
new_time = ClockCycles();

if ((new_time >= run_interval_time)
&& (run_interval_time != 0))
{
diff = (float) ((float)(new_time - run_interval_time) /
cycles_per_msec);
expired_ticks = (unsigned short int) ((new_time - run_interval_time)
/ cycles_per_msec);

// store the last number of ticks that expired for the interval
Progstat->process_last_run_interval = diff;

debug(0, module, “Run Interval = %lf, expired ticks = %d”, diff,
expired_ticks,);

}

//==================================================
// call the run function passed in…
//==================================================
if (run_func() != OK)
{
Debug(-1, module, “Can’t run_func()”);
return(ERROR);
}


Scott
cscott_76@NOSPAMyahoo.com
Delete NOSPAM for email.

Thanks for the reply Murf, that fixed the entire problem.


C. Scott


“John Murphy” <murf@perftech.com> wrote in message
news:40280B68.26F53AB1@perftech.com

Check out the thread “Tick-tock Part II - Understanding the Neutrino micro
kernel’s concept of time” in qdn.public.articles. Basically, you can’t
set the
clock period to exactly 1000000 ns.

Murf

“C. Scott” wrote:

I’m running QNX 6.2.1 on an Intel PIII and I’m testing an application to
see
how well it is able to maintain a 1 msec run interval while other
processes
are going running. I started the test by running the test application in
photon and I had some fairly wide ranging run intervals, so I then
shutdown
photon and ran it from the shell and had the same results. I even tried
changing the priority of the application from 22 to 25 and then up to 62
and
that didn’t help either. What I’ve been seeing is that the run interval
is
normally just about 1 msec (1.0003 to .9996 msec) but every 6 or 7
seconds
the 1 msec run interval is missed, sometimes the run interval is
measured as
2 msec and in some instances it’s over 5 msec.

Here is what I’m doing, I first set the ClockPeriod to 1 msec, and set
the
scheduling to FIFO. I register a pulse to be delivered every 1 msec with
timer_create and then have my process loop on a MsgReceive call waiting
for
the pulses from the timer. Right before I call the main part of the
application I call ClockCycles and check to see how many cycles have
gone by
since my application ran, and for some reason I’m getting same very odd
results. I’m not sure if I’m using ClockCycles incorrectly or if the 1
msec
clock pulse is just not capable of being delivered that quick. Attached
is
some of the code… I appreciate any help or ideas anyone may have. I’m
hoping this is a problem with the way I’m using ClockCycles.

Here are some snippets of what I’m doing…

setting the ClockPeriod…

program->process_id = getpid();

program->process_started = time(NULL);

program->process_exit_status = 0;

param.sched_priority = getprio(0);

if (sched_setscheduler(0,SCHED_FIFO,&param ) == -1)

{

debug(-1, module, “Can’t sched_setscheduler():
error
= (%d): %s”,

errno, strerror(errno));

return(TBC_ERROR);

}

//==============================================

// Set the system timer resolution

//==============================================

new_clock_period.nsec = 1000000; // 1 msec = 1,000,000
nsec

if (ClockPeriod(CLOCK_REALTIME, &new_clock_period,
&original_clock_period, 0) == -1)

{

debug(-1, module,“Can’t
ClockPeriod(CLOCK_REALTIME,new_clock_period, original_clock_period, 0):
(%d)
%s”,

errno, strerror(errno));

return(ERROR);

}

Here is the section where I set the run timer for this process…

Progstat->chid = ChannelCreate(_NTO_CHF_FIXED_PRIORITY);
dpp = _dispatch_create(Progstat->chid, 0);
name_ptr = name_attach(dpp, Progstat->process_name, NULL);

event.sigev_coid = ConnectAttach(ND_LOCAL_NODE, 0,
Progstat->chid,
_NTO_SIDE_CHANNEL, 0);

event.sigev_notify = SIGEV_PULSE;

event.sigev_priority = getprio(0);
event.sigev_code = PULSE_RUN_MESSAGE;

if (timer_create(CLOCK_REALTIME, &event,&tid) == -1)
{
Debug(-1, module, “Can’t timer_create(): (%d) %s”, errno,
strerror(errno));
return(ERROR);
}

//========================================
// Set the timer interval
//========================================
run_timer_spec.it_value.tv_sec = msec / 1000;
run_timer_spec.it_value.tv_nsec = (msec % 1000) * 1000000;
run_timer_spec.it_interval.tv_sec =
run_timer_spec.it_value.tv_sec;
run_timer_spec.it_interval.tv_nsec =
run_timer_spec.it_value.tv_nsec;

if (timer_settime(tid, 0, &run_timer_spec, NULL) == -1)
{
Debug(-1, module, “Can’t timer_settime(): (%d) %s”,
errno, strerror(errno));
return(ERROR);
}

and finally here is code for how to figure out the time between
pulses…

static uint64_t cycles_per_msec = 0, cycles_per_sec = 0,
new_time=0,
old_time=0, run_interval_time = 0;
float diff = 0;
static unsigned short int expired_ticks=0;

cycles_per_sec = SYSPAGE_ENTRY(qtime)->cycles_per_sec;
cycles_per_msec = (cycles_per_sec / 1000.0);

while loop on MsgReceive()

//==================================================
// capture the time when we start to run, and compare it to the last
run

// time.
//==================================================
run_interval_time = new_time;
new_time = ClockCycles();

if ((new_time >= run_interval_time)
&& (run_interval_time != 0))
{
diff = (float) ((float)(new_time - run_interval_time) /
cycles_per_msec);
expired_ticks = (unsigned short int) ((new_time -
run_interval_time)
/ cycles_per_msec);

// store the last number of ticks that expired for the interval
Progstat->process_last_run_interval = diff;

debug(0, module, “Run Interval = %lf, expired ticks = %d”, diff,
expired_ticks,);

}

//==================================================
// call the run function passed in…
//==================================================
if (run_func() != OK)
{
Debug(-1, module, “Can’t run_func()”);
return(ERROR);
}


Scott
cscott_76@NOSPAMyahoo.com
Delete NOSPAM for email.