Hi Luis,

>I 'm a user of LynxOs and I would like to repeat
>the tests that you made. (between RTL and Lynx)
>Can describe the conditions and code you
>used for your different test?
>I will report my findings to the RTL list.
>Thanks,
>Luis.

To make my experiment, I have just been sending a signal to PIN10 of the
parallel port in order to trigger an interrupt. The signal I've been sending
had a 50 usecs period [yes, that's right one LPT IT every 50 usecs] and used
a scope to measure the time between PIN2(Int handler) and PIN3(Task).

I used a DELL PC 450 MHz.

While doing the experiment I was compiling (both under LynxOs and Linux) and
was ping flooding the machine too.

The figures I obtained were: 10-15 usecs scheduler latency for LynxOs
                             20-25 usecs scheduler latency for RTL

The ping flood toward LynxOs was losing most packets though.

/* ------- Here is my RTL test program (largely inspired from examples!) --- */

#include <linux/module.h>
#include <linux/kernel.h>
#include <rtl_fifo.h>
#include <asm/rt_irq.h>
#include <asm/rt_time.h>
#include <rtl_sched.h>
#include <asm/io.h>
#include <linux/cons.h>
#include "common.h"
#include <rtl_sync.h>

#define DATA_PINIRQ   0x01
#define DATA_PINTSK   0x02

RT_TASK rt_task;

static int pinirq = DATA_PINTSK;
static int pintsk = 0;
void shutdown(void);
static int shutdown_flag = 0;

void lpt_irq_handler(void) {
    switch(shutdown_flag){
        case 0:
            if (pinirq == 0)
                pinirq = DATA_PIN2;
            else 
                pinirq = 0;
            outb(pinirq|pintsk, LPT_PORT);
            rt_task_wakeup(&rt_task);
            break;
        case 1: 
            shutdown_flag = 2;
        default: /* do nothing */
    }
}

void fun(int t)
{
    while (1) {

        if (pintsk == 0)
            pintsk = DATA_PIN8;
        else 
            pintsk = 0;
        outb(pinirq|pintsk, LPT_PORT);
        rt_task_suspend(&rt_task);
    }
}

int init_module(void)
{
    int rc;
    int old_irq_state;

    printk("Starting parallel port module\n");
    rtl_no_interrupts(old_irq_state);

    outb(LPT_IRQE, LPT_PORT+2);    /* IRQE */

    if ((rc = request_RTirq(LPT_IRQ, lpt_irq_handler)))
        printk("IRQ %d busy : %d\n", LPT_IRQ, rc);
    
    rtl_restore_interrupts(old_irq_state);

    rt_task_init(&rt_task, fun, 1, 3000, 4);
    rt_task_wakeup(&rt_task);

    return 0;
}

void shutdown()
{
    int old_irq_state;

    rtl_no_interrupts(old_irq_state);
    free_RTirq(LPT_IRQ);
    rtl_restore_interrupts(old_irq_state);
    rt_task_delete(&rt_task);
}


void cleanup_module(void)
{
    int timeout = 100000;

    shutdown_flag = 1;

    /* so it's kinda sloppy, wait for timeout or for 
       interrupt routine to ack shutdown, whatever comes
       first */
    while((shutdown_flag==1) && timeout--)
        ;

    shutdown();

}

/* ------------------------------------------------------------------------- */

/* ------- Here is my LynxOs test program ---------------------------------- */

#include <conf.h>
#include <kernel.h>
#include <io.h>
#include <port_ops_x86.h>
#include <dldd.h>

extern int ionull();
extern int swait();
extern int ssignal();
extern char *sysbrk();
extern int iointset();
extern int ststart();
extern int iointclr();
extern char *sysfree();

#define outb_p(p, v)    __outb((p), (unsigned char)(v))
#define outb(p, v)      __outb((p), (unsigned char)(v))
#define inb_p(p)        __inb((p))
#define inb(p)          __inb(p)

static int rtltsk = 0x2;
static int rtlirq = 0;
static int rtlsem = 0;

struct rtlstatics {
    int st_id;
};

rtlkthread(s)
struct rtlstatics *s;
{
    int rc;

    while(1) {
        rc = swait(&rtlsem, 0);
        if (rc != OK)
            return(SYSERR);

        if (rtltsk == 0)
            rtltsk = 0x2;
        else
            rtltsk = 0;
        outb(0x378, rtltsk|rtlirq);
    }

}

int
rtlintr(s)
struct rtlstatics *s;
{
    if (rtlirq == 0)
        rtlirq = 0x1;
    else
        rtlirq = 0;
    outb(0x378, rtltsk|rtlirq);
    ssignal(&rtlsem);
}

char *
rtlinstall(info)
struct devinfo *info;
{
    struct rtlstatics *s;
    unsigned char ctemp;

    s = (struct rtlstatics *)sysbrk((long)sizeof(*s));
    bzero(s, sizeof(*s));

    iointset(32 + 7, rtlintr, s);

    outb(0x378, 0x00);
    outb(0x378 + 2, 0x10); /* IRQE */

    s->st_id = ststart(rtlkthread, 4096, 127, "foo", s, 0, 0);

    return((char *)s);
}

int
rtluninstall(s)
struct rtlstatics *s;
{
    iointclr(32 + 7);
    stremove(s->st_id);
    sysfree(s, (long)sizeof(*s));
    return(OK);
}

int
rtlopen(s, devno, f)
struct rtlstatics *s;
int devno;
struct file *f;
{
    return(OK);
}

int
rtlclose(s, f)
struct rtlstatics *s;
struct file *f;
{
    return(OK);
}

int
rtlread(s, f, buf, count)
struct rtlstatics *s;
struct file *f;
char *buf;
int count;
{
        return(OK);
}


static struct dldd entry_points = {
    rtlopen, rtlclose, rtlread, ionull,
    ionull, ionull, rtlinstall, rtluninstall,
    (char *)0
};

/* ------------------------------------------------------------------------- */

-- 
Frédéric.R.R.Roussel
[EMAIL PROTECTED]

--- [rtl] ---
To unsubscribe:
echo "unsubscribe rtl" | mail [EMAIL PROTECTED] OR
echo "unsubscribe rtl <Your_email>" | mail [EMAIL PROTECTED]
----
For more information on Real-Time Linux see:
http://www.rtlinux.org/~rtlinux/

Reply via email to