PCI hardware-Interrupts on Pentium 4

Hi,

I am using QNX 6.2 running on a Pentium IV 1800MHz. Hardware interrupts from
my dataacquisition PCI card don’t occur in QNX. It works really fine with an
Pentium II 400MHz.
Can anybody help?

thanks
daniel

Hi Daniel…

Where is the faulty code?

Regards…

Miguel.


Daniel wrote:

Hi,

I am using QNX 6.2 running on a Pentium IV 1800MHz. Hardware interrupts from
my dataacquisition PCI card don’t occur in QNX. It works really fine with an
Pentium II 400MHz.
Can anybody help?

thanks
daniel

Here is the code. It stops after InterruptWait() is called.


int main(int argc, char **argv){
int i = 1;
struct sigevent event;
int intId;
me8100_info_type info;
int file_handle;

file_handle = open("/dev/me8100_0", O_RDWR, 0); /* open the data
acquisition card /
err = ioctl(file_handle, ME8100_GET_BOARD_INFO, &info); /
Get the
PCI-info from PCI card*/
event.sigev_notify = SIGEV_INTR; /* Set the event /
printf(“Attach to IRQ %d\n”, info.int_line); /
Attach to the
interrupt /
intId = InterruptAttachEvent(info.int_line, &event, NULL);
/
Do the job forever */
while(1)
{
printf(“Waiting for interrupts\n”);
InterruptWait(0, NULL);
i++;
printf(“Interrupt occured %d times\n”, i)
InterruptUnmask(info.int_line, intId);
}
}




“Miguel Simon” <simon@ou.edu> schrieb im Newsbeitrag
news:3F4609FD.6000906@ou.edu

Hi Daniel…

Where is the faulty code?

Regards…

Miguel.


Daniel wrote:
Hi,

I am using QNX 6.2 running on a Pentium IV 1800MHz. Hardware interrupts
from
my dataacquisition PCI card don’t occur in QNX. It works really fine
with an
Pentium II 400MHz.
Can anybody help?

thanks
daniel

Hi Daniel…

How do you set and enable the board to generate interrupts? I do not
see the code that does that. Do you do this anywhere? If so, you should
show this code so that we can help…

Regards…

Miguel



Daniel wrote:

Here is the code. It stops after InterruptWait() is called.


int main(int argc, char **argv){
int i = 1;
struct sigevent event;
int intId;
me8100_info_type info;
int file_handle;

file_handle = open("/dev/me8100_0", O_RDWR, 0); /* open the data
acquisition card /
err = ioctl(file_handle, ME8100_GET_BOARD_INFO, &info); /
Get the
PCI-info from PCI card*/
event.sigev_notify = SIGEV_INTR; /* Set the event /
printf(“Attach to IRQ %d\n”, info.int_line); /
Attach to the
interrupt /
intId = InterruptAttachEvent(info.int_line, &event, NULL);
/
Do the job forever */
while(1)
{
printf(“Waiting for interrupts\n”);
InterruptWait(0, NULL);
i++;
printf(“Interrupt occured %d times\n”, i)
InterruptUnmask(info.int_line, intId);
}
}




“Miguel Simon” <> simon@ou.edu> > schrieb im Newsbeitrag
news:> 3F4609FD.6000906@ou.edu> …

Hi Daniel…

Where is the faulty code?

Regards…

Miguel.


Daniel wrote:

Hi,

I am using QNX 6.2 running on a Pentium IV 1800MHz. Hardware interrupts

from

my dataacquisition PCI card don’t occur in QNX. It works really fine

with an

Pentium II 400MHz.
Can anybody help?

thanks
daniel

\

Hi Miguel,

thanks for your reply. Here is the missing code part. The resource manager
is compiled from the manufacturer.

me8100_info_type info;
_uint16 pattern_a;
_uint16 mask_b;
_uint16 ctrl_a;
_uint16 ctrl_b;

err = ioctl(file_handle, ME8100_GET_BOARD_INFO, &info); /* Get the
board info in order to get the interrupt line /
ThreadCtl(_NTO_TCTL_IO, 0); /
Access for I/O functions in order to do
InterruptAttachEvent() /
pattern_a = 0x0001; /
Set a bit pattern for port a /
ioctl(file_handle, ME8100_WRITE_PATTERN_A, &pattern_a);
ctrl_a = 0x40;
err = ioctl(file_handle, ME8100_WRITE_CTRL_A, &ctrl_a); /
Enable
interrupt by bit pattern for port a */

I tested some different computers and this is the result: The Program works
fine on a pentium2 but doesn’t work on a pentium4. I think this could be the
reason, but I don’t know how to enable a pentium4 to do the correct
interrupt handling.


“Miguel Simon” <simon@ou.edu> schrieb im Newsbeitrag
news:3F46B08F.2070004@ou.edu

Hi Daniel…

How do you set and enable the board to generate interrupts? I do not
see the code that does that. Do you do this anywhere? If so, you should
show this code so that we can help…

Regards…

Miguel



Daniel wrote:
Here is the code. It stops after InterruptWait() is called.


int main(int argc, char **argv){
int i = 1;
struct sigevent event;
int intId;
me8100_info_type info;
int file_handle;

file_handle = open("/dev/me8100_0", O_RDWR, 0); /* open the data
acquisition card /
err = ioctl(file_handle, ME8100_GET_BOARD_INFO, &info); /
Get the
PCI-info from PCI card*/
event.sigev_notify = SIGEV_INTR; /* Set the event /
printf(“Attach to IRQ %d\n”, info.int_line); /
Attach to the
interrupt /
intId = InterruptAttachEvent(info.int_line, &event, NULL);
/
Do the job forever */
while(1)
{
printf(“Waiting for interrupts\n”);
InterruptWait(0, NULL);
i++;
printf(“Interrupt occured %d times\n”, i)
InterruptUnmask(info.int_line, intId);
}
}




“Miguel Simon” <> simon@ou.edu> > schrieb im Newsbeitrag
news:> 3F4609FD.6000906@ou.edu> …

Hi Daniel…

Where is the faulty code?

Regards…

Miguel.


Daniel wrote:

Hi,

I am using QNX 6.2 running on a Pentium IV 1800MHz. Hardware interrupts

from

my dataacquisition PCI card don’t occur in QNX. It works really fine

with an

Pentium II 400MHz.
Can anybody help?

thanks
daniel


\

Hi Daniel…

Humm…, if the program that you have works well in P2 but not in a P4,
then…? I suppose that QNX folks would have to dive in for this. In
any case, I wonder if you:

  1. have compared the output of pci -vv for the same board on both the P2
    and P4 computers? Does it look the same?
  2. Have you tried different manufacturers of P4 computers?
  3. Have you verified that the interrupt assigned by the bios does not
    conflict with other resources? What is different?
  4. Can you drive this board with a P4 windows or linux machine? If so,
    look at the resources that windows assigns, and see what happens in QNX.
  5. Who wrote the low level driver for this board?
  6. Do they have source code? Have you contacted them?
  7. How old is this code?
  8. What version of QNX OS are you running?
  9. Have you tried assigning a higher priority to the driver code? Can
    you even do this?
  10. Etc…

It looks like you may have a hardware setup issue…, perhaps. Experts
will say.

Incidentally, I guess that you know that you have to disable the
plug&play bios option, correct?

Regards…

Miguel.



Daniel wrote:

Hi Miguel,

thanks for your reply. Here is the missing code part. The resource manager
is compiled from the manufacturer.

me8100_info_type info;
_uint16 pattern_a;
_uint16 mask_b;
_uint16 ctrl_a;
_uint16 ctrl_b;

err = ioctl(file_handle, ME8100_GET_BOARD_INFO, &info); /* Get the
board info in order to get the interrupt line /
ThreadCtl(_NTO_TCTL_IO, 0); /
Access for I/O functions in order to do
InterruptAttachEvent() /
pattern_a = 0x0001; /
Set a bit pattern for port a /
ioctl(file_handle, ME8100_WRITE_PATTERN_A, &pattern_a);
ctrl_a = 0x40;
err = ioctl(file_handle, ME8100_WRITE_CTRL_A, &ctrl_a); /
Enable
interrupt by bit pattern for port a */

I tested some different computers and this is the result: The Program works
fine on a pentium2 but doesn’t work on a pentium4. I think this could be the
reason, but I don’t know how to enable a pentium4 to do the correct
interrupt handling.


“Miguel Simon” <> simon@ou.edu> > schrieb im Newsbeitrag
news:> 3F46B08F.2070004@ou.edu> …

Hi Daniel…

How do you set and enable the board to generate interrupts? I do not
see the code that does that. Do you do this anywhere? If so, you should
show this code so that we can help…

Regards…

Miguel



Daniel wrote:

Here is the code. It stops after InterruptWait() is called.


int main(int argc, char **argv){
int i = 1;
struct sigevent event;
int intId;
me8100_info_type info;
int file_handle;

file_handle = open("/dev/me8100_0", O_RDWR, 0); /* open the data
acquisition card /
err = ioctl(file_handle, ME8100_GET_BOARD_INFO, &info); /
Get the
PCI-info from PCI card*/
event.sigev_notify = SIGEV_INTR; /* Set the event /
printf(“Attach to IRQ %d\n”, info.int_line); /
Attach to the
interrupt /
intId = InterruptAttachEvent(info.int_line, &event, NULL);
/
Do the job forever */
while(1)
{
printf(“Waiting for interrupts\n”);
InterruptWait(0, NULL);
i++;
printf(“Interrupt occured %d times\n”, i)
InterruptUnmask(info.int_line, intId);
}
}




“Miguel Simon” <> simon@ou.edu> > schrieb im Newsbeitrag
news:> 3F4609FD.6000906@ou.edu> …


Hi Daniel…

Where is the faulty code?

Regards…

Miguel.


Daniel wrote:


Hi,

I am using QNX 6.2 running on a Pentium IV 1800MHz. Hardware interrupts

from


my dataacquisition PCI card don’t occur in QNX. It works really fine

with an


Pentium II 400MHz.
Can anybody help?

thanks
daniel


\

Thanks Miguel,
I tested a lot. I hope I could achieve something commenting your mail. I am
really thankfull about every hint.

Hi Daniel…

Humm…, if the program that you have works well in P2 but not in a P4,
then…? I suppose that QNX folks would have to dive in for this. In
any case, I wonder if you:

  1. have compared the output of pci -vv for the same board on both the P2
    and P4 computers? Does it look the same?
    so far, I can’t find any difference
  2. Have you tried different manufacturers of P4 computers?
    Yes. SCENIC P4 2400MHz with AMI-BIOS and a P4 1800 with ASUS motherboard and

AWARD Bios.

  1. Have you verified that the interrupt assigned by the bios does not
    conflict with other resources? What is different?
    I deactivated all other PCI-slots in BIOS I removed all PCI cards, i

disabled all onboard components … I think there is no hardware conflict

  1. Can you drive this board with a P4 windows or linux machine? If so,
    look at the resources that windows assigns, and see what happens in QNX.
    The board rund on both P4 machines in Windows 2000 and Windows XP. The

ressources are the same, I think.

  1. Who wrote the low level driver for this board?
    It has been written by the manufacturer.
  2. Do they have source code? Have you contacted them?
    Yes, Ihave parts of the source code, but aren’t allowed to post. are there

any significant parts I could search for?

  1. How old is this code?
    Its a QNX 6.1 source code from 2002
  2. What version of QNX OS are you running?
    QNX 6.2
  3. Have you tried assigning a higher priority to the driver code? Can
    you even do this?
    I didn’t, but I will do!
  4. Etc…

It looks like you may have a hardware setup issue…, perhaps. Experts
will say.

Incidentally, I guess that you know that you have to disable the
plug&play bios option, correct?
Of course plug&play is disabled. The Interrupt mode is set to PIC not APIC.

thanks again,
Daniel

Daniel wrote:
Hi Miguel,

thanks for your reply. Here is the missing code part. The resource
manager
is compiled from the manufacturer.

me8100_info_type info;
_uint16 pattern_a;
_uint16 mask_b;
_uint16 ctrl_a;
_uint16 ctrl_b;

err = ioctl(file_handle, ME8100_GET_BOARD_INFO, &info); /* Get the
board info in order to get the interrupt line /
ThreadCtl(_NTO_TCTL_IO, 0); /
Access for I/O functions in order to
do
InterruptAttachEvent() /
pattern_a = 0x0001; /
Set a bit pattern for port a /
ioctl(file_handle, ME8100_WRITE_PATTERN_A, &pattern_a);
ctrl_a = 0x40;
err = ioctl(file_handle, ME8100_WRITE_CTRL_A, &ctrl_a); /
Enable
interrupt by bit pattern for port a */

I tested some different computers and this is the result: The Program
works
fine on a pentium2 but doesn’t work on a pentium4. I think this could be
the
reason, but I don’t know how to enable a pentium4 to do the correct
interrupt handling.


“Miguel Simon” <> simon@ou.edu> > schrieb im Newsbeitrag
news:> 3F46B08F.2070004@ou.edu> …

Hi Daniel…

How do you set and enable the board to generate interrupts? I do not
see the code that does that. Do you do this anywhere? If so, you should
show this code so that we can help…

Regards…

Miguel



Daniel wrote:

Here is the code. It stops after InterruptWait() is called.


int main(int argc, char **argv){
int i = 1;
struct sigevent event;
int intId;
me8100_info_type info;
int file_handle;

file_handle = open("/dev/me8100_0", O_RDWR, 0); /* open the data
acquisition card /
err = ioctl(file_handle, ME8100_GET_BOARD_INFO, &info); /
Get the
PCI-info from PCI card*/
event.sigev_notify = SIGEV_INTR; /* Set the event /
printf(“Attach to IRQ %d\n”, info.int_line); /
Attach to the
interrupt /
intId = InterruptAttachEvent(info.int_line, &event, NULL);
/
Do the job forever */
while(1)
{
printf(“Waiting for interrupts\n”);
InterruptWait(0, NULL);
i++;
printf(“Interrupt occured %d times\n”, i)
InterruptUnmask(info.int_line, intId);
}
}




“Miguel Simon” <> simon@ou.edu> > schrieb im Newsbeitrag
news:> 3F4609FD.6000906@ou.edu> …


Hi Daniel…

Where is the faulty code?

Regards…

Miguel.


Daniel wrote:


Hi,

I am using QNX 6.2 running on a Pentium IV 1800MHz. Hardware
interrupts

from


my dataacquisition PCI card don’t occur in QNX. It works really fine

with an


Pentium II 400MHz.
Can anybody help?

thanks
daniel



\

Hi Daniel…

Daniel wrote:

  1. Can you drive this board with a P4 windows or linux machine? If so,
    look at the resources that windows assigns, and see what happens in QNX.

The board rund on both P4 machines in Windows 2000 and Windows XP. The
ressources are the same, I think.

  1. I suppose that you run QNX and Windows in the same machine. Given
    this then, the fact that the same machine runs the code on window$, this
    tells you that the machine itself is not the problem.

  2. does this point to a source code problem? Perhaps. I suppose that if
    you have QNX source code, then you compile the code in your QNX machine.
    In other words, you compile that code and generate the driver from
    scratch. This opposite to having a compiled driver that you ‘just use as
    is’. The reason for this would be that there may be differences in
    compiler, kernel, etc… depending on the version of the OS that you run
    and the version that the driver provider has…

  3. If the above checks, then… would this be a problem with the OS?
    This option is highly unlikely. QNX folks would have to help from here on.

Bests…

Miguel.

What does ‘pci -v’ say about your board? Can you post that fragment? And
what is PCI BIOS version on the motherboard (2.1 or 2.2)? Is your data
acquisition board PCI2.1 or PCI2.2 compliant? Or maybe it is PCI2.0 ???

“Daniel” <daniel-grimm@gmx.de> wrote in message
news:bi729a$gcg$1@inn.qnx.com

Hi Miguel,

thanks for your reply. Here is the missing code part. The resource manager
is compiled from the manufacturer.

me8100_info_type info;
_uint16 pattern_a;
_uint16 mask_b;
_uint16 ctrl_a;
_uint16 ctrl_b;

err = ioctl(file_handle, ME8100_GET_BOARD_INFO, &info); /* Get the
board info in order to get the interrupt line /
ThreadCtl(_NTO_TCTL_IO, 0); /
Access for I/O functions in order to
do
InterruptAttachEvent() /
pattern_a = 0x0001; /
Set a bit pattern for port a /
ioctl(file_handle, ME8100_WRITE_PATTERN_A, &pattern_a);
ctrl_a = 0x40;
err = ioctl(file_handle, ME8100_WRITE_CTRL_A, &ctrl_a); /
Enable
interrupt by bit pattern for port a */

I tested some different computers and this is the result: The Program
works
fine on a pentium2 but doesn’t work on a pentium4. I think this could be
the
reason, but I don’t know how to enable a pentium4 to do the correct
interrupt handling.


“Miguel Simon” <> simon@ou.edu> > schrieb im Newsbeitrag
news:> 3F46B08F.2070004@ou.edu> …
Hi Daniel…

How do you set and enable the board to generate interrupts? I do not
see the code that does that. Do you do this anywhere? If so, you should
show this code so that we can help…

Regards…

Miguel



Daniel wrote:
Here is the code. It stops after InterruptWait() is called.


int main(int argc, char **argv){
int i = 1;
struct sigevent event;
int intId;
me8100_info_type info;
int file_handle;

file_handle = open("/dev/me8100_0", O_RDWR, 0); /* open the data
acquisition card /
err = ioctl(file_handle, ME8100_GET_BOARD_INFO, &info); /
Get
the
PCI-info from PCI card*/
event.sigev_notify = SIGEV_INTR; /* Set the event /
printf(“Attach to IRQ %d\n”, info.int_line); /
Attach to the
interrupt /
intId = InterruptAttachEvent(info.int_line, &event, NULL);
/
Do the job forever */
while(1)
{
printf(“Waiting for interrupts\n”);
InterruptWait(0, NULL);
i++;
printf(“Interrupt occured %d times\n”, i)
InterruptUnmask(info.int_line, intId);
}
}




“Miguel Simon” <> simon@ou.edu> > schrieb im Newsbeitrag
news:> 3F4609FD.6000906@ou.edu> …

Hi Daniel…

Where is the faulty code?

Regards…

Miguel.


Daniel wrote:

Hi,

I am using QNX 6.2 running on a Pentium IV 1800MHz. Hardware
interrupts

from

my dataacquisition PCI card don’t occur in QNX. It works really fine

with an

Pentium II 400MHz.
Can anybody help?

thanks
daniel




\

“Daniel” <daniel-grimm@gmx.de> wrote in message
news:bib142$dsn$1@inn.qnx.com

Thanks Miguel,
I tested a lot. I hope I could achieve something commenting your mail. I
am
really thankfull about every hint.

Try something, if your bios allows it disable P4 cache. This is going to
slow the PC down a lot though :wink:

It could be speed related or it could be that the software that control the
card (assuming it’s memory mapped) didn’t map it with cache disable. P4 has
fancier cache then P2. Do you have access to the code that talks to the
card?

  • Mario

Thanks to all who tried to help me!

It’s a problem I still can’t explain, but I was able to solve. I tested all
different PCI-slots on the PCs and it only works on one slot. Of course,
this was the slot, I didn’t test at the beginning, when I was changing two
cards.

thanks
daniel

Daniel <daniel-grimm@gmx.de> wrote:
D > Thanks to all who tried to help me!

D > It’s a problem I still can’t explain, but I was able to solve. I tested all
D > different PCI-slots on the PCs and it only works on one slot. Of course,
D > this was the slot, I didn’t test at the beginning, when I was changing two
D > cards.

Most PCI BIOSs assign interrupts based on the PCI slot number. So this
is not surprising. If you did a ‘pci -v’ as you moved the card from
slot to slot, I’m guessing that you’d see a different interrupt being
used in each.

Many PCI BIOSs will also allow you to determine which interrupt gets
assigned to what PCI slot. I found that this was necessary because I
had a full length PCI card that only fit into one slot. SO I had to
change the interrupt that that slot was using.