base/include/rtai_sched.h

Go to the documentation of this file.
00001 /*
00002  * Copyright (C) 1999-2008 Paolo Mantegazza <mantegazza@aero.polimi.it>
00003  *
00004  * This program is free software; you can redistribute it and/or
00005  * modify it under the terms of the GNU General Public License as
00006  * published by the Free Software Foundation; either version 2 of the
00007  * License, or (at your option) any later version.
00008  *
00009  * This program is distributed in the hope that it will be useful,
00010  * but WITHOUT ANY WARRANTY; without even the implied warranty of
00011  * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
00012  * GNU General Public License for more details.
00013  *
00014  * You should have received a copy of the GNU General Public License
00015  * along with this program; if not, write to the Free Software
00016  * Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
00017  */
00018 
00019 #ifndef _RTAI_SCHED_H
00020 #define _RTAI_SCHED_H
00021 
00022 #include <rtai.h>
00023 #ifndef __KERNEL__
00024 #include <sys/time.h>
00025 #include <time.h>
00026 #include <errno.h>
00027 #include <rtai_types.h>
00028 #endif /* __KERNEL__ */
00029 
00030 #define RT_SCHED_UP   1
00031 #define RT_SCHED_SMP  2
00032 #define RT_SCHED_MUP  3
00033 
00034 #define RT_SCHED_HIGHEST_PRIORITY  0
00035 #define RT_SCHED_LOWEST_PRIORITY   0x3fffFfff
00036 #define RT_SCHED_LINUX_PRIORITY    0x7fffFfff
00037 
00038 #define RT_RESEM_SUSPDEL  (-0x7fffFfff)
00039 
00040 #define RT_SCHED_READY        1
00041 #define RT_SCHED_SUSPENDED    2
00042 #define RT_SCHED_DELAYED      4
00043 #define RT_SCHED_SEMAPHORE    8
00044 #define RT_SCHED_SEND        16
00045 #define RT_SCHED_RECEIVE     32
00046 #define RT_SCHED_RPC         64
00047 #define RT_SCHED_RETURN     128
00048 #define RT_SCHED_MBXSUSP    256
00049 #define RT_SCHED_SFTRDY     512
00050 #define RT_SCHED_POLL      1024
00051 #define RT_SCHED_SIGSUSP    (1 << 15)
00052 
00053 #define RT_RWLINV     (11)  // keep this the highest
00054 #define RT_CHGPORTERR (10)
00055 #define RT_CHGPORTOK  (9)
00056 #define RT_NETIMOUT   (8)
00057 #define RT_DEADLOK    (7)
00058 #define RT_PERM       (6)
00059 #define RT_OBJINV     (5)
00060 #define RT_OBJREM     (4)
00061 #define RT_TIMOUT     (3)
00062 #define RT_UNBLKD     (2)
00063 #define RT_TMROVRN    (1)  // keep this the lowest, must be 1
00064 #define RTP_RWLINV     ((void *)RT_RWLINV)
00065 #define RTP_CHGPORTERR ((void *)RT_CHGPORTERR)
00066 #define RTP_CHGPORTOK  ((void *)RT_CHGPORTOK)
00067 #define RTP_NETIMOUT   ((void *)RT_NETIMOUT)
00068 #define RTP_DEADLOK    ((void *)RT_DEADLOK)
00069 #define RTP_PERM       ((void *)RT_PERM)
00070 #define RTP_OBJINV     ((void *)RT_OBJINV)
00071 #define RTP_OBJREM     ((void *)RT_OBJREM)
00072 #define RTP_TIMOUT     ((void *)RT_TIMOUT)
00073 #define RTP_UNBLKD     ((void *)RT_UNBLKD)
00074 #define RTP_TMROVRN    ((void *)RT_TMROVRN)
00075 #define RTP_HIGERR     (RTP_RWLINV)
00076 #define RTP_LOWERR     (RTP_TMROVRN)
00077 #if CONFIG_RTAI_USE_NEWERR
00078 #define RTE_BASE       (0x3FFFFF00)
00079 #define RTE_RWLINV     (RTE_BASE + RT_RWLINV)
00080 #define RTE_CHGPORTERR (RTE_BASE + RT_CHGPORTERR)
00081 #define RTE_CHGPORTOK  (RTE_BASE + RT_CHGPORTOK)
00082 #define RTE_NETIMOUT   (RTE_BASE + RT_NETIMOUT)
00083 #define RTE_DEADLOK    (RTE_BASE + RT_DEADLOK)
00084 #define RTE_PERM       (RTE_BASE + RT_PERM)
00085 #define RTE_OBJINV     (RTE_BASE + RT_OBJINV)
00086 #define RTE_OBJREM     (RTE_BASE + RT_OBJREM)
00087 #define RTE_TIMOUT     (RTE_BASE + RT_TIMOUT)
00088 #define RTE_UNBLKD     (RTE_BASE + RT_UNBLKD)
00089 #define RTE_TMROVRN    (RTE_BASE + RT_TMROVRN)
00090 #define RTE_HIGERR     (RTE_RWLINV)
00091 #define RTE_LOWERR     (RTE_TMROVRN)
00092 #else
00093 #define RTE_BASE       (0xFFFB)
00094 #define RTE_RWLINV     (RTE_BASE + RT_RWLINV)
00095 #define RTE_CHGPORTERR (RTE_BASE + RT_CHGPORTERR)
00096 #define RTE_CHGPORTOK  (RTE_BASE + RT_CHGPORTOK)
00097 #define RTE_NETIMOUT   (RTE_BASE + RT_NETIMOUT)
00098 #define RTE_DEADLOK    (RTE_BASE + RT_DEADLOK)
00099 #define RTE_PERM       (RTE_BASE + RT_PERM)
00100 #define RTE_OBJINV     (RTE_BASE + RT_OBJREM)
00101 #define RTE_OBJREM     (RTE_BASE + RT_OBJREM)
00102 #define RTE_TIMOUT     (RTE_BASE + RT_TIMOUT)
00103 #define RTE_UNBLKD     (RTE_BASE + RT_UNBLKD)
00104 #define RTE_TMROVRN    (RTE_BASE + RT_TMROVRN)
00105 #define RTE_HIGERR     (RTE_RWLINV)
00106 #define RTE_LOWERR     (RTE_TMROVRN)
00107 #endif
00108 
00109 #define RT_EINTR      (RTE_UNBLKD)
00110 
00111 #define rt_is_reterr(i)  (i >= RTE_LOWERR)
00112 
00113 #define RT_IRQ_TASK         0
00114 #define RT_IRQ_TASKLET      1
00115 #define RT_IRQ_TASK_ERR     0x7FFFFFFF
00116 
00117 struct rt_task_struct;
00118 
00119 typedef struct rt_task_info { 
00120     RTIME period; long base_priority, priority; 
00121 } RT_TASK_INFO;
00122 
00123 #ifdef __KERNEL__
00124 
00125 #include <linux/time.h>
00126 #include <linux/errno.h>
00127 
00128 #if defined(CONFIG_RTAI_LONG_TIMED_LIST) && LINUX_VERSION_CODE >= KERNEL_VERSION(2,6,0)
00129 #include <linux/rbtree.h>
00130 typedef struct rb_node rb_node_t;
00131 typedef struct rb_root rb_root_t;
00132 #endif
00133 
00134 #define RT_TASK_MAGIC 0x9ad25f6f  // nam2num("rttask")
00135 
00136 #ifndef __cplusplus
00137 
00138 #include <linux/sched.h>
00139 
00140 typedef struct rt_queue {
00141     struct rt_queue *prev;
00142     struct rt_queue *next;
00143     struct rt_task_struct *task;
00144 } QUEUE;
00145 
00146 struct mcb_t {
00147     void *sbuf;
00148     int sbytes;
00149     void *rbuf;
00150     int rbytes;
00151 };
00152 
00153 /*Exit handler functions are called like C++ destructors in rt_task_delete().*/
00154 typedef struct rt_ExitHandler {
00155     struct rt_ExitHandler *nxt;
00156     void (*fun) (void *arg1, int arg2);
00157     void *arg1;
00158     int   arg2;
00159 } XHDL;
00160 
00161 struct rt_heap_t { void *heap, *kadr, *uadr; };
00162 
00163 #define RTAI_MAX_NAME_LENGTH  32
00164 
00165 typedef struct rt_task_struct {
00166     long *stack __attribute__ ((__aligned__ (L1_CACHE_BYTES)));
00167     int uses_fpu;
00168     int magic;
00169     volatile int state, running;
00170     unsigned long runnable_on_cpus;
00171     long *stack_bottom;
00172     volatile int priority;
00173     int base_priority;
00174     int policy;
00175     int sched_lock_priority;
00176     struct rt_task_struct *prio_passed_to;
00177     RTIME period;
00178     RTIME resume_time;
00179     RTIME periodic_resume_time;
00180     RTIME yield_time;
00181     int rr_quantum, rr_remaining;
00182     int suspdepth;
00183     struct rt_queue queue;
00184     int owndres;
00185     struct rt_queue *blocked_on;
00186     struct rt_queue msg_queue;
00187     int tid;  /* trace ID */
00188     unsigned long msg;
00189     struct rt_queue ret_queue;
00190     void (*signal)(void);
00191     FPU_ENV fpu_reg __attribute__ ((__aligned__ (L1_CACHE_BYTES)));
00192     struct rt_task_struct *prev, *next;
00193     struct rt_task_struct *tprev, *tnext;
00194     struct rt_task_struct *rprev, *rnext;
00195 
00196     /* For calls from LINUX. */
00197     long *fun_args;
00198     long *bstack;
00199     struct task_struct *lnxtsk;
00200     long long retval;
00201     char *msg_buf[2];
00202     long max_msg_size[2];
00203     char task_name[RTAI_MAX_NAME_LENGTH];
00204     void *system_data_ptr;
00205     struct rt_task_struct *nextp, *prevp;
00206 
00207     RT_TRAP_HANDLER task_trap_handler[HAL_NR_FAULTS];
00208 
00209     long unblocked;
00210     void *rt_signals;
00211     volatile unsigned long pstate;
00212     unsigned long usp_flags;
00213     unsigned long usp_flags_mask;
00214     unsigned long force_soft;
00215     volatile int is_hard;
00216 
00217     long busy_time_align;
00218     struct linux_syscalls_list *linux_syscall_server; 
00219 
00220     /* For use by watchdog. */
00221     int resync_frame;
00222 
00223     /* For use by exit handler functions. */
00224     XHDL *ExitHook;
00225 
00226     RTIME exectime[2];
00227     struct mcb_t mcb;
00228 
00229     /* Real time heaps. */
00230     struct rt_heap_t heap[2];
00231 
00232     volatile int scheduler;
00233 
00234 #ifdef CONFIG_RTAI_LONG_TIMED_LIST
00235     rb_root_t rbr;
00236     rb_node_t rbn;
00237 #endif
00238     struct rt_queue resq;
00239     unsigned long resumsg;
00240 } RT_TASK __attribute__ ((__aligned__ (L1_CACHE_BYTES)));
00241 
00242 #else /* __cplusplus */
00243 extern "C" {
00244 #endif /* !__cplusplus */
00245 
00246 int rt_task_init(struct rt_task_struct *task,
00247          void (*rt_thread)(long),
00248          long data,
00249          int stack_size,
00250          int priority,
00251          int uses_fpu,
00252          void(*signal)(void));
00253 
00254 int rt_task_init_cpuid(struct rt_task_struct *task,
00255                void (*rt_thread)(long),
00256                long data,
00257                int stack_size,
00258                int priority,
00259                int uses_fpu,
00260                void(*signal)(void),
00261                unsigned run_on_cpu);
00262 
00263 int rt_kthread_init(struct rt_task_struct *task,
00264             void (*rt_thread)(long),
00265             long data,
00266             int stack_size,
00267             int priority,
00268             int uses_fpu,
00269             void(*signal)(void));
00270 
00271 int rt_kthread_init_cpuid(struct rt_task_struct *task,
00272                   void (*rt_thread)(long),
00273                   long data,
00274                   int stack_size,
00275                   int priority,
00276                   int uses_fpu,
00277                   void(*signal)(void),
00278                   unsigned run_on_cpu);
00279 
00280 RTAI_SYSCALL_MODE void rt_set_runnable_on_cpus(struct rt_task_struct *task,
00281                  unsigned long cpu_mask);
00282 
00283 RTAI_SYSCALL_MODE void rt_set_runnable_on_cpuid(struct rt_task_struct *task,
00284                   unsigned cpuid);
00285 
00286 RTAI_SYSCALL_MODE void rt_set_sched_policy(struct rt_task_struct *task,
00287              int policy,
00288              int rr_quantum_ns);
00289 
00290 int rt_task_delete(struct rt_task_struct *task);
00291 
00292 int rt_get_task_state(struct rt_task_struct *task);
00293 
00294 void rt_gettimeorig(RTIME time_orig[]);
00295 
00296 int rt_get_timer_cpu(void);
00297 
00298 int rt_is_hard_timer_running(void);
00299 
00300 void rt_set_periodic_mode(void);
00301 
00302 void rt_set_oneshot_mode(void);
00303 
00304 RTAI_SYSCALL_MODE RTIME start_rt_timer(int period);
00305 
00306 #define start_rt_timer_ns(period) start_rt_timer(nano2count((period)))
00307 
00308 RTAI_SYSCALL_MODE void start_rt_apic_timers(struct apic_timer_setup_data *setup_mode,
00309               unsigned rcvr_jiffies_cpuid);
00310 
00311 void stop_rt_timer(void);
00312 
00313 struct rt_task_struct *rt_whoami(void);
00314 
00315 int rt_sched_type(void);
00316 
00317 RTAI_SYSCALL_MODE int rt_task_signal_handler(struct rt_task_struct *task,
00318                void (*handler)(void));
00319 
00320 RTAI_SYSCALL_MODE int rt_task_use_fpu(struct rt_task_struct *task,
00321             int use_fpu_flag);
00322   
00323 void rt_linux_use_fpu(int use_fpu_flag);
00324 
00325 RTAI_SYSCALL_MODE int rt_hard_timer_tick_count(void);
00326 
00327 RTAI_SYSCALL_MODE int rt_hard_timer_tick_count_cpuid(int cpuid);
00328 
00329 RTAI_SYSCALL_MODE RTIME count2nano(RTIME timercounts);
00330 
00331 RTAI_SYSCALL_MODE RTIME nano2count(RTIME nanosecs);
00332   
00333 RTAI_SYSCALL_MODE RTIME count2nano_cpuid(RTIME timercounts, unsigned cpuid);
00334 
00335 RTAI_SYSCALL_MODE RTIME nano2count_cpuid(RTIME nanosecs, unsigned cpuid);
00336   
00337 RTIME rt_get_time(void);
00338 
00339 RTAI_SYSCALL_MODE RTIME rt_get_time_cpuid(unsigned cpuid);
00340 
00341 RTIME rt_get_time_ns(void);
00342 
00343 RTAI_SYSCALL_MODE RTIME rt_get_time_ns_cpuid(unsigned cpuid);
00344 
00345 RTIME rt_get_cpu_time_ns(void);
00346 
00347 RTIME rt_get_real_time(void);
00348 
00349 RTIME rt_get_real_time_ns(void);
00350 
00351 int rt_get_prio(struct rt_task_struct *task);
00352 
00353 int rt_get_inher_prio(struct rt_task_struct *task);
00354 
00355 RTAI_SYSCALL_MODE int rt_task_get_info(RT_TASK *task, RT_TASK_INFO *task_info);
00356 
00357 RTAI_SYSCALL_MODE int rt_get_priorities(struct rt_task_struct *task, int *priority, int *base_priority);
00358 
00359 RTAI_SYSCALL_MODE void rt_spv_RMS(int cpuid);
00360 
00361 RTAI_SYSCALL_MODE int rt_change_prio(struct rt_task_struct *task,
00362            int priority);
00363 
00364 void rt_sched_lock(void);
00365 
00366 void rt_sched_unlock(void);
00367 
00368 void rt_task_yield(void);
00369 
00370 RTAI_SYSCALL_MODE int rt_task_suspend(struct rt_task_struct *task);
00371 
00372 RTAI_SYSCALL_MODE int rt_task_suspend_if(struct rt_task_struct *task);
00373 
00374 RTAI_SYSCALL_MODE int rt_task_suspend_until(struct rt_task_struct *task, RTIME until);
00375 
00376 RTAI_SYSCALL_MODE int rt_task_suspend_timed(struct rt_task_struct *task, RTIME delay);
00377 
00378 RTAI_SYSCALL_MODE int rt_task_resume(struct rt_task_struct *task);
00379 
00380 RTAI_SYSCALL_MODE void rt_set_linux_syscall_mode(long sync_async, void (*callback_fun)(long, long));
00381 
00382 void rt_exec_linux_syscall(RT_TASK *rt_current, struct linux_syscalls_list *syscalls, struct pt_regs *regs);
00383 
00384 RTAI_SYSCALL_MODE void rt_return_linux_syscall(RT_TASK *task, unsigned long retval);
00385 
00386 RTAI_SYSCALL_MODE int rt_irq_wait(unsigned irq);
00387 
00388 RTAI_SYSCALL_MODE int rt_irq_wait_if(unsigned irq);
00389 
00390 RTAI_SYSCALL_MODE int rt_irq_wait_until(unsigned irq, RTIME until);
00391 
00392 RTAI_SYSCALL_MODE int rt_irq_wait_timed(unsigned irq, RTIME delay);
00393 
00394 RTAI_SYSCALL_MODE void rt_irq_signal(unsigned irq);
00395 
00396 RTAI_SYSCALL_MODE int rt_request_irq_task (unsigned irq, void *handler, int type, int affine2task);
00397 
00398 RTAI_SYSCALL_MODE int rt_release_irq_task (unsigned irq);
00399 
00400 RTAI_SYSCALL_MODE int rt_task_make_periodic_relative_ns(struct rt_task_struct *task,
00401                       RTIME start_delay,
00402                       RTIME period);
00403 
00404 RTAI_SYSCALL_MODE int rt_task_make_periodic(struct rt_task_struct *task,
00405               RTIME start_time,
00406               RTIME period);
00407 
00408 RTAI_SYSCALL_MODE void rt_task_set_resume_end_times(RTIME resume,
00409                   RTIME end);
00410 
00411 RTAI_SYSCALL_MODE int rt_set_resume_time(struct rt_task_struct *task,
00412                RTIME new_resume_time);
00413 
00414 RTAI_SYSCALL_MODE int rt_set_period(struct rt_task_struct *task,
00415           RTIME new_period);
00416 
00417 int rt_task_wait_period(void);
00418 
00419 void rt_schedule(void);
00420 
00421 RTIME next_period(void);
00422 
00423 RTAI_SYSCALL_MODE void rt_busy_sleep(int nanosecs);
00424 
00425 RTAI_SYSCALL_MODE int rt_sleep(RTIME delay);
00426 
00427 RTAI_SYSCALL_MODE int rt_sleep_until(RTIME time);
00428 
00429 RTAI_SYSCALL_MODE int rt_task_masked_unblock(struct rt_task_struct *task, unsigned long mask);
00430 
00431 #define rt_task_wakeup_sleeping(t)  rt_task_masked_unblock(t, RT_SCHED_DELAYED)
00432 
00433 RTAI_SYSCALL_MODE struct rt_task_struct *rt_named_task_init(const char *task_name,
00434                       void (*thread)(long),
00435                       long data,
00436                       int stack_size,
00437                       int prio,
00438                       int uses_fpu,
00439                       void(*signal)(void));
00440 
00441 RTAI_SYSCALL_MODE struct rt_task_struct *rt_named_task_init_cpuid(const char *task_name,
00442                         void (*thread)(long),
00443                         long data,
00444                         int stack_size,
00445                         int prio,
00446                         int uses_fpu,
00447                         void(*signal)(void),
00448                         unsigned run_on_cpu);
00449 
00450 RTAI_SYSCALL_MODE int rt_named_task_delete(struct rt_task_struct *task);
00451 
00452 RT_TRAP_HANDLER rt_set_task_trap_handler(struct rt_task_struct *task,
00453                      unsigned vec,
00454                      RT_TRAP_HANDLER handler);
00455 
00456 static inline RTIME timeval2count(struct timeval *t)
00457 {
00458         return nano2count(t->tv_sec*1000000000LL + t->tv_usec*1000);
00459 }
00460 
00461 static inline void count2timeval(RTIME rt, struct timeval *t)
00462 {
00463         t->tv_sec = rtai_ulldiv(count2nano(rt), 1000000000, (unsigned long *)&t->tv_usec);
00464         t->tv_usec /= 1000;
00465 }
00466 
00467 static inline RTIME timespec2count(const struct timespec *t)
00468 {
00469         return nano2count(t->tv_sec*1000000000LL + t->tv_nsec);
00470 }
00471 
00472 static inline void count2timespec(RTIME rt, struct timespec *t)
00473 {
00474         t->tv_sec = rtai_ulldiv(count2nano(rt), 1000000000, (unsigned long *)&t->tv_nsec);
00475 }
00476 
00477 static inline RTIME timespec2nanos(const struct timespec *t)
00478 {
00479         return t->tv_sec*1000000000LL + t->tv_nsec;
00480 }
00481 
00482 static inline void nanos2timespec(RTIME rt, struct timespec *t)
00483 {
00484         t->tv_sec = rtai_ulldiv(rt, 1000000000, (unsigned long *)&t->tv_nsec);
00485 }
00486 
00487 void rt_make_hard_real_time(RT_TASK *task);
00488 
00489 void rt_make_soft_real_time(RT_TASK *task);
00490 
00491 #ifdef __cplusplus
00492 }
00493 #else /* !__cplusplus */
00494 
00495 /* FIXME: These calls should move to rtai_schedcore.h */
00496 
00497 RT_TASK *rt_get_base_linux_task(RT_TASK **base_linux_task);
00498 
00499 RT_TASK *rt_alloc_dynamic_task(void);
00500 
00501 void rt_enq_ready_edf_task(RT_TASK *ready_task);
00502 
00503 void rt_enq_ready_task(RT_TASK *ready_task);
00504 
00505 int rt_renq_ready_task(RT_TASK *ready_task,
00506                int priority);
00507 
00508 void rt_rem_ready_task(RT_TASK *task);
00509 
00510 void rt_rem_ready_current(RT_TASK *rt_current);
00511 
00512 void rt_enq_timed_task(RT_TASK *timed_task);
00513 
00514 void rt_rem_timed_task(RT_TASK *task);
00515 
00516 void rt_dequeue_blocked(RT_TASK *task);
00517 
00518 RT_TASK **rt_register_watchdog(RT_TASK *wdog,
00519                    int cpuid);
00520 
00521 void rt_deregister_watchdog(RT_TASK *wdog,
00522                 int cpuid);
00523 
00524 #endif /* __cplusplus */
00525 
00526 #endif /* __KERNEL__ */
00527 
00528 #if !defined(__KERNEL__) || defined(__cplusplus)
00529 
00530 typedef struct rt_task_struct {
00531     int opaque;
00532 } RT_TASK;
00533 
00534 typedef struct QueueBlock {
00535     int opaque;
00536 } QBLK;
00537 
00538 typedef struct QueueHook {
00539     int opaque;
00540 } QHOOK;
00541 
00542 #endif /* !__KERNEL__ || __cplusplus */
00543 
00544 #endif /* !_RTAI_SCHED_H */

Generated on Tue Feb 2 17:46:04 2010 for RTAI API by  doxygen 1.4.7