1 2 3 4 5 6 7 8 9 10 11 12 13 14 15 16 17 18 19 20 21 22 23 24 25 26 27 28 29 30 31 32 33 34 35 36 37 38 39 40 41 42 43 44 45 46 47 48 49 50 51 52 53 54 55 56 57 58 59 60 61 62 63 64 65 66 67 68 69 70 71 72 73 74 75 76 77 78 79 80 81 82 83 84 85 86 87 88 89 90 91 92 93 94 95 96 97 98 99 100 101 102 103 104 105 106 107 108 109 110 111 112 113 114 115 116 117 118 119 120 121 122 123 124 125 126 127 128 129 130 131 132 133 134 135 136 137 138 139 140 141 142 143 144 145 146 147 148 149 150 151 152 153 154 155 156 157 158 159 160 161 162 163 164 165 166 167 168 169 170 171 172 173 174 175 176 177 178 179 180 181 182 183 184 185 186 187 188 189 190 191 192 193 194 195 196 197 198 199 200 201 202 203 204 205 206 207 208 209 210 211 212 213 214 215 216 217 218 219 220 221 222 223 224 225 226 227 228 229 230 231 232 233 234 235 236 237 238 239 240 241 242 243 244 245 246 247 248 249
|
/*
* RT-Linux scheduler
*
* Written by Michael Barabanov, Victor Yodaiken
* Copyright (C) VJY Associates LLC, 1998-1999
* Released under the terms of the GPL
*
*/
#ifndef __RTL__SCHED__
#define __RTL__SCHED__
#include <asm/spinlock.h>
#include <asm/ptrace.h>
#include <linux/tasks.h>
#include <linux/rtl.h>
#include <linux/malloc.h>
#include <linux/tqueue.h>
#include <rtl_conf.h>
#include <rtl_core.h>
#include <rtl_time.h>
#include <arch/rtl_fpu.h>
/* #include "../schedulers/x86/switch.h" */
extern void rtl_tq_sync (struct tq_struct *tq_s);
enum rtl_task_states {
RTL_THREAD_READY = 1, RTL_THREAD_DELAYED = 2, RTL_THREAD_DORMANT = 4, RTL_THREAD_SUSPENDED = 8, RTL_THREAD_ACTIVE = 16, RTL_THREAD_ZOMBIE = 32, RTL_THREAD_WAIT_NEEDED = 64
};
/* for sched_param and others */
#include <linux/sched.h>
typedef struct sched_param rtl_sched_param;
#define TIMER_ABSTIME 1
#define RTL_MAX_TIMERS 32
typedef struct rtl_timer_struct *timer_t;
/* threads have no clocks. Clocks belong to schedulers. We can add scheduling
policies in which a scheduler juggles multiple clocks, but there is no advantage
that I can see in allowing a thread to specify its hardware clock
*/
struct rtl_thread_struct {
int *stack; /* hardcoded */
int uses_fp;
enum rtl_task_states state;
int *stack_bottom;
rtl_sched_param sched_param;
struct rtl_thread_struct *next;
RTL_FPU_CONTEXT fpu_regs;
int cpu;
hrtime_t resume_time;
hrtime_t period;
void *retval;
int pending_signals;
struct tq_struct free_task;
void *user[4];
int errno_val;
int pad [64];
};
#define RTL_SIGNAL_DELETE 0
#define RTL_SIGNAL_WAKEUP 1
#define RTL_SIGNAL_SUSPEND 2
extern void rtl_schedule (void);
typedef struct rtl_thread_struct RTL_THREAD_STRUCT;
typedef RTL_THREAD_STRUCT *pthread_t;
#define rtl_is_linux_task(cpu, a) (a == &sched_data(cpu)->rtl_linux_task)
struct rtl_sched_cpu_struct {
RTL_THREAD_STRUCT *rtl_current;
RTL_THREAD_STRUCT rtl_linux_task;
RTL_THREAD_STRUCT idle_task;
RTL_THREAD_STRUCT *rtl_task_fpu_owner; /* the task whose FP context is currently in the FPU unit */
RTL_THREAD_STRUCT *rtl_tasks; /* the queue of RT tasks */
task_queue rtl_tq_cpu;
clockid_t clock;
hrtime_t timerset;
int sched_user[4]; /* on x86 sched_user[0] is the Linux TS flag */
}/* __attribute__ ((aligned (64)))*/;
typedef struct rtl_sched_cpu_struct schedule_t;
#ifdef __SMP__
extern struct rtl_sched_cpu_struct rtl_sched [NR_CPUS];
#define sched_data(cpu) (&rtl_sched [cpu])
#define LOCAL_SCHED (&rtl_sched[rtl_getcpuid()])
#else
extern struct rtl_sched_cpu_struct rtl_sched [1];
#define sched_data(cpu) (&rtl_sched[0])
#define LOCAL_SCHED (&rtl_sched[0])
#endif
#define RTL_CURRENT (LOCAL_SCHED->rtl_current)
#define RTL_TQ(cpu) (sched_data(cpu)->rtl_tq_cpu)
/* RTL-specific function TODO: write POSIX equivalents for these */
extern int pthread_delete_np (pthread_t thread);
extern int pthread_setfp_np (pthread_t thread, int flag);
extern int pthread_wakeup_np (pthread_t thread);
extern int pthread_suspend_np (pthread_t thread);
/* end RTL-specific */
/* POSIX interface */
extern inline int sched_get_priority_max(int policy) { return 1000000; }
extern inline int sched_get_priority_min(int policy) { return 0; }
extern inline pthread_t pthread_self(void) {
return (LOCAL_SCHED)-> rtl_current;
}
extern inline int pthread_equal(pthread_t thread1, pthread_t thread2)
{
return thread1 == thread2;
}
typedef struct STRUCT_PTHREAD_ATTR {
int stack_size;
rtl_sched_param sched_param;
int cpu;
int use_fp;
} pthread_attr_t;
extern inline int pthread_attr_init(pthread_attr_t *attr)
{
attr->stack_size = 3000;
attr->sched_param.sched_priority = sched_get_priority_min(0);
attr->cpu = rtl_getcpuid();
attr->use_fp = 0;
return 0;
}
extern inline int pthread_attr_destroy(pthread_attr_t *attr)
{
return 0;
}
/*
extern inline int pthread_attr_setfp_np (pthread_attr_t *attr, int flag)
{
attr->use_fp = flag;
return 0;
}
*/
extern inline int pthread_attr_setstacksize(pthread_attr_t *attr, size_t stacksize)
{
attr->stack_size = stacksize;
return 0;
}
extern inline int pthread_attr_getcpu_np(pthread_attr_t *attr, int * cpu)
{
*cpu = attr->cpu;
return 0;
}
extern int pthread_attr_setcpu_np(pthread_attr_t *attr, int cpu);
extern int pthread_wait_np(void);
extern int pthread_make_periodic_np (pthread_t p, hrtime_t start_time, hrtime_t period);
/* this one is deprecated */
extern int pthread_setperiod_np(pthread_t p,const struct itimerspec *t);
extern inline clockid_t rtl_getschedclock(void)
{
return LOCAL_SCHED->clock;
}
extern int rtl_setclockmode (clockid_t clock, int mode, hrtime_t period);
extern inline void pthread_yield(void)
{
/* TODO */
}
extern inline int pthread_setschedparam(pthread_t thread, int policy,
const rtl_sched_param *param) {
thread->sched_param = *param;
return 0;
}
extern inline int pthread_getschedparam(pthread_t thread, int *policy,
rtl_sched_param *param) {
*param = thread->sched_param;
return 0;
}
extern inline int pthread_attr_setschedparam(pthread_attr_t *attr,
const rtl_sched_param *param) {
attr->sched_param = *param;
return 0;
}
extern inline int pthread_attr_getschedparam(const pthread_attr_t *attr,
rtl_sched_param *param) {
*param = attr->sched_param;
return 0;
}
extern int pthread_create (pthread_t *thread, pthread_attr_t *attr, void *(*start_routine)(void *), void *arg);
#define PTHREAD_CANCELED ((void *) -1)
extern void pthread_exit(void *retval);
/* end of POSIX interface */
#ifdef CONFIG_X86_REMOTE_DEBUG
extern void breakpoint(void);
#endif
#include <rtl_compat.h>
#ifdef CONFIG_RTL_USE_V1_API
#define pthread_make_periodic_np (PleaseUse_rt_task_make_periodic_In_V1_EmulationMode=1)
#endif
#endif
|