00001
00002
00003
00004
00005
00006
00007
00008
00009
00010
00011
00012
00013
00014
00015
00016
00017
00018
00019
00020
00021
00022
00023
00024
00025
00026
00027
00028
00029
00030
00031
00032
00033
00034
00035
00036
00037
00038 #ifndef _RTAI_ASM_M68KNOMMU_HAL_H
00039 #define _RTAI_ASM_M68KNOMMU_HAL_H
00040
00041 #include <linux/version.h>
00042
00043
00044
00045
00046 #define RTAI_SYSCALL_MODE
00047
00048
00049 #define RTAI_DUOSS
00050 #define LOCKED_LINUX_IN_IRQ_HANDLER
00051 #define DOMAIN_TO_STALL (fusion_domain)
00052
00053 #include <rtai_hal_names.h>
00054 #include <asm/rtai_vectors.h>
00055 #include <rtai_types.h>
00056
00057 #define RTAI_NR_CPUS 1
00058
00059 #define FIRST_EXTERNAL_VECTOR 0x40
00060
00061 #ifndef _RTAI_FUSION_H
00062 static __inline__ unsigned long ffnz (unsigned long word) {
00063
00064 int r = 1;
00065 if (!(word & 0xff)) {
00066 word >>= 8;
00067 r += 8;
00068 }
00069 if (!(word & 0xf)) {
00070 word >>= 4;
00071 r += 4;
00072 }
00073 if (!(word & 3)) {
00074 word >>= 2;
00075 r += 2;
00076 }
00077 if (!(word & 1)) {
00078 word >>= 1;
00079 r += 1;
00080 }
00081 return r - 1;
00082 }
00083 #endif
00084
00085 static inline unsigned long long rtai_ulldiv (unsigned long long ull,
00086 unsigned long uld,
00087 unsigned long *r) {
00088
00089 unsigned long long qf, rf, q, p;
00090 unsigned long tq, rh;
00091 p = ull;
00092 q = 0;
00093 rf = 0x100000000ULL - (qf = 0xFFFFFFFFUL / uld) * uld;
00094 while (p >= uld) {
00095 q += (((unsigned long long)(tq = ((unsigned long)(p >> 32)) / uld)) << 32);
00096 rh = ((unsigned long)(p >> 32)) - tq * uld;
00097 q += rh * qf + (tq = (unsigned long)p / uld);
00098 p = rh * rf + ((unsigned long)p - tq * uld);
00099 }
00100 if (r)
00101 *r = p;
00102 return q;
00103 }
00104
00105 static inline int rtai_imuldiv (int i, int mult, int div) {
00106
00107
00108 long long temp = i * (long long)mult;
00109 return rtai_ulldiv(temp, div, NULL);
00110 }
00111
00112 static inline unsigned long long rtai_llimd(unsigned long long ll, unsigned int mult, unsigned int div) {
00113 unsigned long long res, tmp;
00114 unsigned long r;
00115 res = rtai_ulldiv(ll,div,&r) * mult;
00116 tmp = r * (unsigned long long)mult;
00117 res += rtai_ulldiv(tmp, div, NULL);
00118 return res;
00119 }
00120
00121
00122
00123 #if defined(__KERNEL__) && !defined(__cplusplus)
00124 #include <linux/sched.h>
00125 #include <linux/interrupt.h>
00126 #include <asm/system.h>
00127 #include <asm/io.h>
00128 #include <asm/rtai_atomic.h>
00129 #include <asm/rtai_fpu.h>
00130 #include <rtai_trace.h>
00131
00132 extern asmlinkage int fprintk(const char *fmt, ...);
00133
00134 struct rtai_realtime_irq_s {
00135 int (*handler)(unsigned irq, void *cookie);
00136 void *cookie;
00137 int retmode;
00138 int cpumask;
00139 int (*irq_ack)(unsigned int);
00140 };
00141
00142
00143
00144
00145
00146
00147
00148 static inline int ext_irq_vector(int irq)
00149 {
00150 if (irq != 2) {
00151 return (FIRST_EXTERNAL_VECTOR + irq);
00152 }
00153 return -EINVAL;
00154 }
00155
00156 #define RTAI_DOMAIN_ID 0x9ac15d93 // nam2num("rtai_d")
00157 #define RTAI_NR_TRAPS HAL_NR_FAULTS
00158 #define RTAI_NR_SRQS 32
00159
00160 #define RTAI_APIC_TIMER_VECTOR RTAI_APIC_HIGH_VECTOR
00161 #define RTAI_APIC_TIMER_IPI RTAI_APIC_HIGH_IPI
00162 #define RTAI_SMP_NOTIFY_VECTOR RTAI_APIC_LOW_VECTOR
00163 #define RTAI_SMP_NOTIFY_IPI RTAI_APIC_LOW_IPI
00164
00165 #define RTAI_TIMER_LINUX_IRQ 96
00166 #define RT_TIMER_IRQ 96
00167 #define RTAI_FREQ_8254 MCF_BUSCLK
00168 #define RTAI_COUNTER_2_LATCH 0xfffe
00169 #define RTAI_LATENCY_8254 CONFIG_RTAI_SCHED_8254_LATENCY
00170 #define RTAI_SETUP_TIME_8254 8011
00171
00172 #define RTAI_CALIBRATED_APIC_FREQ 0
00173 #define RTAI_FREQ_APIC (rtai_tunables.apic_freq)
00174 #define RTAI_LATENCY_APIC CONFIG_RTAI_SCHED_APIC_LATENCY
00175 #define RTAI_SETUP_TIME_APIC 1000
00176
00177 #define RTAI_TIME_LIMIT 0x7000000000000000LL
00178
00179 #define rtai_cpuid() hal_processor_id()
00180 #define rtai_tskext(idx) hal_tskext[idx]
00181
00182
00183 #define rtai_hw_cli() hal_hw_cli()
00184 #define rtai_hw_sti() hal_hw_sti()
00185 #define rtai_hw_save_flags_and_cli(x) hal_hw_local_irq_save(x)
00186 #define rtai_hw_restore_flags(x) hal_hw_local_irq_restore(x)
00187 #define rtai_hw_save_flags(x) hal_hw_local_irq_flags(x)
00188
00189
00190 #define rtai_cli() hal_hw_cli()
00191 #define rtai_sti() hal_hw_sti()
00192 #define rtai_save_flags_and_cli(x) hal_hw_local_irq_save(x)
00193 #define rtai_restore_flags(x) hal_hw_local_irq_restore(x)
00194 #define rtai_save_flags(x) hal_hw_local_irq_flags(x)
00195
00196 static inline struct hal_domain_struct *get_domain_pointer(int n)
00197 {
00198 struct list_head *p = hal_pipeline.next;
00199 struct hal_domain_struct *d;
00200 unsigned long i = 0;
00201 while (p != &hal_pipeline) {
00202 d = list_entry(p, struct hal_domain_struct, p_link);
00203 if (++i == n) {
00204 return d;
00205 }
00206 p = d->p_link.next;
00207 }
00208 return (struct hal_domain_struct *)i;
00209 }
00210
00211 #define RTAI_LT_KERNEL_VERSION_FOR_NONPERCPU KERNEL_VERSION(2,6,20)
00212
00213 #define RTAI_LT_KERNEL_VERSION_FOR_IRQDESC KERNEL_VERSION(2,6,23)
00214
00215 #if LINUX_VERSION_CODE < RTAI_LT_KERNEL_VERSION_FOR_NONPERCPU
00216
00217 #define ROOT_STATUS_ADR(cpuid) (ipipe_root_status[cpuid])
00218 #define ROOT_STATUS_VAL(cpuid) (*ipipe_root_status[cpuid])
00219
00220 #define hal_pend_domain_uncond(irq, domain, cpuid) \
00221 do { \
00222 hal_irq_hits_pp(irq, domain, cpuid); \
00223 if (likely(!test_bit(IPIPE_LOCK_FLAG, &(domain)->irqs[irq].control))) { \
00224 __set_bit((irq) & IPIPE_IRQ_IMASK, &(domain)->cpudata[cpuid].irq_pending_lo[(irq) >> IPIPE_IRQ_ISHIFT]); \
00225 __set_bit((irq) >> IPIPE_IRQ_ISHIFT, &(domain)->cpudata[cpuid].irq_pending_hi); \
00226 } \
00227 } while (0)
00228
00229 #define hal_fast_flush_pipeline(cpuid) \
00230 do { \
00231 if (hal_root_domain->cpudata[cpuid].irq_pending_hi != 0) { \
00232 rtai_cli(); \
00233 hal_sync_stage(IPIPE_IRQMASK_ANY); \
00234 } \
00235 } while (0)
00236
00237 #else
00238
00239 #define ROOT_STATUS_ADR(cpuid) (&ipipe_cpudom_var(hal_root_domain, status))
00240 #define ROOT_STATUS_VAL(cpuid) (ipipe_cpudom_var(hal_root_domain, status))
00241
00242 #define hal_pend_domain_uncond(irq, domain, cpuid) \
00243 do { \
00244 if (likely(!test_bit(IPIPE_LOCK_FLAG, &(domain)->irqs[irq].control))) { \
00245 __set_bit((irq) & IPIPE_IRQ_IMASK, &ipipe_cpudom_var(domain, irqpend_lomask)[(irq) >> IPIPE_IRQ_ISHIFT]); \
00246 __set_bit((irq) >> IPIPE_IRQ_ISHIFT, &ipipe_cpudom_var(domain, irqpend_himask)); \
00247 } else { \
00248 __set_bit((irq) & IPIPE_IRQ_IMASK, &ipipe_cpudom_var(domain, irqheld_mask)[(irq) >> IPIPE_IRQ_ISHIFT]); \
00249 } \
00250 ipipe_cpudom_var(domain, irqall)[irq]++; \
00251 } while (0)
00252
00253 #define hal_fast_flush_pipeline(cpuid) \
00254 do { \
00255 if (ipipe_cpudom_var(hal_root_domain, irqpend_himask) != 0) { \
00256 rtai_cli(); \
00257 hal_sync_stage(IPIPE_IRQMASK_ANY); \
00258 } \
00259 } while (0)
00260
00261 #endif
00262
00263 #define hal_pend_uncond(irq, cpuid) hal_pend_domain_uncond(irq, hal_root_domain, cpuid)
00264
00265 extern volatile unsigned long *ipipe_root_status[];
00266
00267 #define hal_test_and_fast_flush_pipeline(cpuid) \
00268 do { \
00269 if (!test_bit(IPIPE_STALL_FLAG, ROOT_STATUS_ADR(cpuid))) { \
00270 hal_fast_flush_pipeline(cpuid); \
00271 rtai_sti(); \
00272 } \
00273 } while (0)
00274
00275 #ifdef CONFIG_PREEMPT
00276 #define rtai_save_and_lock_preempt_count() \
00277 do { int *prcntp, prcnt; prcnt = xchg(prcntp = &preempt_count(), 1);
00278 #define rtai_restore_preempt_count() \
00279 *prcntp = prcnt; } while (0)
00280 #else
00281 #define rtai_save_and_lock_preempt_count();
00282 #define rtai_restore_preempt_count();
00283 #endif
00284
00285 typedef int (*rt_irq_handler_t)(unsigned irq, void *cookie);
00286
00287 #define RTAI_CALIBRATED_CPU_FREQ 0
00288 #define RTAI_CPU_FREQ (rtai_tunables.cpu_freq)
00289
00290 extern long long rdtsc(void);
00291
00292 #define rtai_rdtsc() rdtsc()
00293
00294 struct calibration_data {
00295
00296 unsigned long cpu_freq;
00297 unsigned long apic_freq;
00298 int latency;
00299 int setup_time_TIMER_CPUNIT;
00300 int setup_time_TIMER_UNIT;
00301 int timers_tol[RTAI_NR_CPUS];
00302 };
00303
00304 struct apic_timer_setup_data {
00305
00306 int mode;
00307 int count;
00308 };
00309
00310 extern struct rt_times rt_times;
00311
00312 extern struct rt_times rt_smp_times[RTAI_NR_CPUS];
00313
00314 extern struct calibration_data rtai_tunables;
00315
00316 extern volatile unsigned long rtai_cpu_lock[];
00317
00318
00319 #define SET_TASKPRI(cpuid)
00320 #define CLR_TASKPRI(cpuid)
00321
00322 extern struct rtai_switch_data {
00323 volatile unsigned long sflags;
00324 volatile unsigned long lflags;
00325 } rtai_linux_context[RTAI_NR_CPUS];
00326
00327 irqreturn_t rtai_broadcast_to_local_timers(int irq,
00328 void *dev_id,
00329 struct pt_regs *regs);
00330
00331 static inline unsigned long rtai_save_flags_irqbit(void)
00332 {
00333 unsigned long flags;
00334 rtai_save_flags(flags);
00335 return !(flags & ~ALLOWINT);
00336 }
00337
00338 static inline unsigned long rtai_save_flags_irqbit_and_cli(void)
00339 {
00340 unsigned long flags;
00341 rtai_save_flags_and_cli(flags);
00342 return !(flags & ~ALLOWINT);
00343 }
00344
00345 #define _send_sched_ipi(dest)
00346
00347 #define rt_spin_lock(lock)
00348 #define rt_spin_unlock(lock)
00349
00350 #define rt_spin_lock_irq(lock) do { rtai_cli(); } while (0)
00351 #define rt_spin_unlock_irq(lock) do { rtai_sti(); } while (0)
00352
00353 static inline unsigned long rt_spin_lock_irqsave(spinlock_t *lock)
00354 {
00355 unsigned long flags;
00356 rtai_save_flags_and_cli(flags);
00357 return flags;
00358 }
00359 #define rt_spin_unlock_irqrestore(flags, lock) do { rtai_restore_flags(flags); } while (0)
00360
00361 #define rt_get_global_lock() do { rtai_cli(); } while (0)
00362 #define rt_release_global_lock()
00363
00364 #define rt_global_cli() do { rtai_cli(); } while (0)
00365 #define rt_global_sti() do { rtai_sti(); } while (0)
00366
00367 static inline unsigned long rt_global_save_flags_and_cli(void)
00368 {
00369 unsigned long flags;
00370 rtai_save_flags_and_cli(flags);
00371 return flags;
00372 }
00373 #define rt_global_restore_flags(flags) do { rtai_restore_flags(flags); } while (0)
00374
00375 #define rt_global_save_flags(flags) do { rtai_save_flags(*flags); } while (0)
00376
00377 asmlinkage int rt_printk(const char *format, ...);
00378 asmlinkage int rt_sync_printk(const char *format, ...);
00379
00380 extern struct hal_domain_struct rtai_domain;
00381 extern struct hal_domain_struct *fusion_domain;
00382
00383 #define _rt_switch_to_real_time(cpuid) \
00384 do { \
00385 rtai_linux_context[cpuid].lflags = xchg(ROOT_STATUS_ADR(cpuid), (1 << IPIPE_STALL_FLAG)); \
00386 rtai_linux_context[cpuid].sflags = 1; \
00387 hal_current_domain(cpuid) = &rtai_domain; \
00388 } while (0)
00389
00390 #define rt_switch_to_linux(cpuid) \
00391 do { \
00392 if (rtai_linux_context[cpuid].sflags) { \
00393 hal_current_domain(cpuid) = hal_root_domain; \
00394 ROOT_STATUS_VAL(cpuid) = rtai_linux_context[cpuid].lflags; \
00395 rtai_linux_context[cpuid].sflags = 0; \
00396 CLR_TASKPRI(cpuid); \
00397 } \
00398 } while (0)
00399
00400 #define rt_switch_to_real_time(cpuid) \
00401 do { \
00402 if (!rtai_linux_context[cpuid].sflags) { \
00403 _rt_switch_to_real_time(cpuid); \
00404 } \
00405 } while (0)
00406
00407 #define ack_bad_irq hal_ack_system_irq // linux does not export ack_bad_irq
00408
00409 #define rtai_init_taskpri_irqs() do { } while (0)
00410
00411 static inline int rt_save_switch_to_real_time(int cpuid)
00412 {
00413 SET_TASKPRI(cpuid);
00414 if (!rtai_linux_context[cpuid].sflags) {
00415 _rt_switch_to_real_time(cpuid);
00416 return 0;
00417 }
00418 return 1;
00419 }
00420
00421 #define rt_restore_switch_to_linux(sflags, cpuid) \
00422 do { \
00423 if (!sflags) { \
00424 rt_switch_to_linux(cpuid); \
00425 } else if (!rtai_linux_context[cpuid].sflags) { \
00426 SET_TASKPRI(cpuid); \
00427 _rt_switch_to_real_time(cpuid); \
00428 } \
00429 } while (0)
00430
00431 #define in_hrt_mode(cpuid) (rtai_linux_context[cpuid].sflags)
00432
00433 #include <asm/coldfire.h>
00434 #include <asm/mcftimer.h>
00435 #include <asm/mcfsim.h>
00436 #include <asm/io.h>
00437
00438 #define TA(a) (MCF_MBAR + MCFTIMER_BASE1 + (a))
00439
00440 #if defined(CONFIG_M532x)
00441 #define __raw_readtrr __raw_readl
00442 #define __raw_writetrr __raw_writel
00443 #else
00444 #define __raw_readtrr __raw_readw
00445 #define __raw_writetrr __raw_writew
00446 #endif
00447
00448 static inline void rt_set_timer_delay (int delay) {
00449
00450 if (delay) {
00451
00452
00453
00454
00455 asm volatile(" \
00456 bra 1f\n\t \
00457 2: \
00458 movel %1, %%d1\n\t \
00459 addl %0, %%d1\t\n \
00460 movel %%d1, %2\n\t \
00461 bra 3f\n\t \
00462 1: \
00463 bra 2b\n\t \
00464 3: \
00465 ": :"d" (delay), "m"(*(long*)(void*)TA(MCFTIMER_TCN)), "m"(*(long*)(void*)TA(MCFTIMER_TRR)) : "memory", "d1");
00466 read_timer_cnt();
00467 }
00468 else
00469 {
00470 __raw_writetrr(rt_smp_times[0].intr_time, TA(MCFTIMER_TRR));
00471 }
00472 }
00473
00474
00475
00476 unsigned long rtai_critical_enter(void (*synch)(void));
00477
00478 void rtai_critical_exit(unsigned long flags);
00479
00480 int rtai_calibrate_8254(void);
00481
00482 void rtai_set_linux_task_priority(struct task_struct *task,
00483 int policy,
00484 int prio);
00485
00486 long rtai_catch_event (struct hal_domain_struct *domain, unsigned long event, int (*handler)(unsigned long, void *));
00487
00488 #endif
00489
00490
00491
00492 #ifdef __KERNEL__
00493
00494 #include <linux/kernel.h>
00495
00496 #define rtai_print_to_screen rt_printk
00497
00498 void *ll2a(long long ll, char *s);
00499
00500 #ifdef __cplusplus
00501 extern "C" {
00502 #endif
00503
00504 int rt_request_irq(unsigned irq,
00505 int (*handler)(unsigned irq, void *cookie),
00506 void *cookie,
00507 int retmode);
00508
00509 int rt_release_irq(unsigned irq);
00510
00511 int rt_set_irq_ack(unsigned int irq, int (*irq_ack)(unsigned int));
00512
00513 static inline int rt_request_irq_wack(unsigned irq, int (*handler)(unsigned irq, void *cookie), void *cookie, int retmode, int (*irq_ack)(unsigned int))
00514 {
00515 int retval;
00516 if ((retval = rt_request_irq(irq, handler, cookie, retmode)) < 0) {
00517 return retval;
00518 }
00519 return rt_set_irq_ack(irq, irq_ack);
00520 }
00521
00522 void rt_set_irq_cookie(unsigned irq, void *cookie);
00523
00524 void rt_set_irq_retmode(unsigned irq, int fastret);
00525
00526
00527
00528
00529
00530 unsigned rt_startup_irq(unsigned irq);
00531
00532 void rt_shutdown_irq(unsigned irq);
00533
00534 void rt_enable_irq(unsigned irq);
00535
00536 void rt_disable_irq(unsigned irq);
00537
00538 void rt_mask_and_ack_irq(unsigned irq);
00539
00540 void rt_unmask_irq(unsigned irq);
00541
00542 void rt_ack_irq(unsigned irq);
00543
00544
00545
00546 struct desc_struct {
00547 void *a;
00548 };
00549
00550 struct desc_struct rtai_set_gate_vector (unsigned vector, int type, int dpl, void *handler);
00551
00552 void rtai_reset_gate_vector(unsigned vector, struct desc_struct e);
00553
00554 void rt_do_irq(unsigned irq);
00555
00556 int rt_request_linux_irq(unsigned irq,
00557 void *handler,
00558 char *name,
00559 void *dev_id);
00560
00561 int rt_free_linux_irq(unsigned irq,
00562 void *dev_id);
00563
00564 void rt_pend_linux_irq(unsigned irq);
00565
00566 RTAI_SYSCALL_MODE void usr_rt_pend_linux_irq(unsigned irq);
00567
00568 void rt_pend_linux_srq(unsigned srq);
00569
00570 int rt_request_srq(unsigned label,
00571 void (*k_handler)(void),
00572 long long (*u_handler)(unsigned long));
00573
00574 int rt_free_srq(unsigned srq);
00575
00576 int rt_assign_irq_to_cpu(int irq,
00577 unsigned long cpus_mask);
00578
00579 int rt_reset_irq_to_sym_mode(int irq);
00580
00581 void rt_request_timer_cpuid(void (*handler)(void),
00582 unsigned tick,
00583 int cpuid);
00584
00585 int rt_request_timer(void (*handler)(void), unsigned tick, int);
00586
00587 void rt_free_timer(void);
00588
00589 RT_TRAP_HANDLER rt_set_trap_handler(RT_TRAP_HANDLER handler);
00590
00591 void rt_release_rtc(void);
00592
00593 void rt_request_rtc(long rtc_freq, void *handler);
00594
00595 #define rt_mount()
00596
00597 #define rt_umount()
00598
00599 void (*rt_set_ihook(void (*hookfn)(int)))(int);
00600
00601
00602
00603 static inline int rt_request_global_irq(unsigned irq, void (*handler)(void))
00604 {
00605 return rt_request_irq(irq, (int (*)(unsigned,void *))handler, 0, 0);
00606 }
00607
00608 static inline int rt_request_global_irq_ext(unsigned irq, void (*handler)(void), unsigned long cookie)
00609 {
00610 return rt_request_irq(irq, (int (*)(unsigned,void *))handler, (void *)cookie, 1);
00611 }
00612
00613 static inline void rt_set_global_irq_ext(unsigned irq, int ext, unsigned long cookie)
00614 {
00615 rt_set_irq_cookie(irq, (void *)cookie);
00616 }
00617
00618 static inline int rt_free_global_irq(unsigned irq)
00619 {
00620 return rt_release_irq(irq);
00621 }
00622
00623 #ifdef __cplusplus
00624 }
00625 #endif
00626
00627 #endif
00628
00629 #include <asm/rtai_oldnames.h>
00630
00631 #define RTAI_DEFAULT_TICK 100000
00632 #ifdef CONFIG_RTAI_TRACE
00633 #define RTAI_DEFAULT_STACKSZ 8192
00634 #else
00635 #define RTAI_DEFAULT_STACKSZ 1024
00636 #endif
00637
00638
00639
00640 #endif
00641
00642
00643 #ifndef _RTAI_HAL_XN_H
00644 #define _RTAI_HAL_XN_H
00645
00646
00647
00648 #define SET_FUSION_TIMER_RUNNING()
00649
00650 #define CLEAR_FUSION_TIMER_RUNNING()
00651
00652 #define IS_FUSION_TIMER_RUNNING() (0)
00653
00654 #define NON_RTAI_SCHEDULE(cpuid) do { schedule(); } while (0)
00655
00656 #endif