////////////////////////////////////////////////////////////
//
// Implementation of classes
// AProcessAttributes, AScheduleRules
//
// Copyright 2001
//
////////////////////////////////////////////////////////////
#include <pthread.h>
#include <errno.h>
#include <stdlib.h>
#include <unistd.h>
#include <string.h>
#include "ASchedule.h"
#include "AProcess.h"
// AProcessAttributes
int AProcessAttributes::set(pid_t process_id)
{
id=process_id;
policy=0;
priority=0;
child_policy=0;
child_priority=0;
AScheduleAttributes att(id);
if(att.status) return 1;
att.get_priority(priority);
policy=sched_getscheduler(id);
child_policy=policy;
child_priority=priority;
return 0;
}
int AProcessAttributes::set_child(int new_policy,int new_priority)
{
if( status ) return 1;
sched_param z;
AScheduleAttributes att(id);
att.set_priority(new_priority);
att.get(z);
child_policy=new_policy;
child_priority=new_priority;
return sched_setscheduler(id,new_policy,&z);
}
int AProcessAttributes::set_child_priority(int new_priority)
{
if( status ) return 1;
sched_param z;
AScheduleAttributes att(id);
att.set_priority(new_priority);
att.get(z);
child_priority=new_priority;
return sched_setparam(id,&z);
}
// AScheduleRules
AScheduleRules::AScheduleRules():status(0),policy(0)
{
policy=sched_getscheduler(0);
}
int AScheduleRules::set_policy(int z)
{
// to do check value !
policy=z;
return 0;
}
int AScheduleRules::priority_range(int& min_value, int& max_value, int& direction)
{
if(status) return 1;
int g=0;
g=sched_get_priority_min(policy);
if(g<0) return 1;
min_value=g;
g=sched_get_priority_max(policy);
if(g<0) return 2;
max_value=g;
direction=1;
switch(policy)
{
//case SCHED_HPUX:
//case SCHED_TIMESHARE:
case SCHED_OTHER:
case SCHED_RTPRIO: direction=-1; break;
}
return 0;
}
int AScheduleRules::priority_above(int& new_priority, int base_priority)
{
if(status) return 1;
int g=0, min_value=0, max_value=0, direction=0;
g=priority_range( min_value, max_value, direction);
if(g) return 1;
if(base_priority < min_value || base_priority > max_value) return 2;
new_priority=base_priority;
if(direction > 0 && base_priority+1 <= max_value)
++new_priority;
else if(direction < 0 && base_priority-1 >= min_value)
--new_priority;
return 0;
}
int AScheduleRules::priority_below(int& new_priority, int base_priority)
{
if(status) return 1;
int g=0, min_value=0, max_value=0, direction=0;
g=priority_range( min_value, max_value, direction);
if(g) return 1;
if(base_priority < min_value || base_priority > max_value) return 2;
new_priority=base_priority;
if(direction < 0 && base_priority+1 <= max_value)
++new_priority;
else if(direction > 0 && base_priority-1 >= min_value)
--new_priority;
return 0;
}
// functions
int AMainThreadPriority(int& priority)
{
// alternative - rtprio (2)
AScheduleAttributes att;
att.get_priority(priority);
return 0;
}
int clone_process(bool& original, AProcessAttributes& attributes)
{
pid_t id=fork();
if(errno) return 1;
attributes.set(id);
if(0==id) original=false;
else original=true;
return 0;
}