2005-11-11 15:52:58

by Guido Günther

[permalink] [raw]
Subject: sparc64: Oops in pci_alloc_consistent with cingergyT2

Hi,
when loading the cinergyT2 module I see the following Oops on sparc64:

usb 3-2: new high speed USB device using ehci_hcd and address 4
Unable to handle kernel NULL pointer dereference
tsk->{mm,active_mm}->context = 0000000000000318
tsk->{mm,active_mm}->pgd = fffff800015c0000
\|/ ____ \|/
"@'/ .. \`@"
/_| \__/ |_\
\__U_/
modprobe(20322): Oops [#1]
TSTATE: 0000004411009603 TPC: 0000000000423568 TNPC: 000000000042356c Y: 00000000 Not tainted
TPC: <pci_alloc_consistent+0x68/0x1a0>
g0: fffff8000225f5a0 g1: 0000000000000000 g2: 00000000b6db6db7 g3: 0000000000000000
g4: fffff80013b1d0a0 g5: 0000000000000000 g6: fffff8000225c000 g7: 0000000000000000
o0: fffff80004660000 o1: 0000000000000000 o2: 0000000000000000 o3: fffff80004660000
o4: 0000000000000000 o5: fffff80013f43810 sp: fffff8000225ee41 ret_pc: 0000000000423560
RPC: <pci_alloc_consistent+0x60/0x1a0>
l0: 0000000000000001 l1: fffff80004660000 l2: 0000000000000000 l3: 0000000000000001
l4: 0000000000000000 l5: 0000000000002000 l6: 0000000000000000 l7: 0000000070195298
i0: 0000000000000000 i1: 0000000000004000 i2: fffff80005dd0508 i3: 00000000efa01501
i4: fffff8000225c000 i5: 0000000000000002 i6: fffff8000225ef01 i7: 000000000226e3ac
I7: <cinergyt2_alloc_stream_urbs+0xc/0x120 [cinergyT2]>
Caller[000000000226e3ac]: cinergyt2_alloc_stream_urbs+0xc/0x120 [cinergyT2]
Caller[000000000226f364]: cinergyt2_probe+0x84/0x3c0 [cinergyT2]
Caller[000000000200009c]: usb_probe_interface+0x5c/0x80 [usbcore]
Caller[000000000054b7b0]: driver_probe_device+0x30/0xc0
Caller[000000000054b8e8]: __driver_attach+0x28/0x40
Caller[000000000054ae28]: bus_for_each_dev+0x48/0x80
Caller[000000000054b2ec]: bus_add_driver+0x6c/0xe0
Caller[0000000002000194]: usb_register+0x54/0xc0 [usbcore]
Caller[0000000002276008]: cinergyt2_init+0x8/0x80 [cinergyT2]
Caller[00000000004613ac]: sys_init_module+0x14c/0x220
Caller[0000000000410e54]: linux_sparc_syscall32+0x34/0x40
Caller[0000000000012758]: 0x12758
Instruction DUMP: 2b000008 4003a40f 932d5010 <c25ca030> c4584000 f058af10 a9520000 9190200f b336700d

This is due to the fact that cinergyt2_alloc_stream_urbs calls
pci_alloc_consistent with a NULL argument for the pci dev (it's a USB
device):

cinergyt2->streambuf = pci_alloc_consistent(NULL,
STREAM_URB_COUNT*STREAM_BUF_SIZE,
&cinergyt2->streambuf_dmahandle);

dma_alloc_coherent doesn't seem to be implemented on sparc64, what would
be the right way to tackle this?
Cheers,
-- Guido


2005-11-11 19:10:24

by Alan

[permalink] [raw]
Subject: Re: sparc64: Oops in pci_alloc_consistent with cingergyT2

On Gwe, 2005-11-11 at 16:33 +0100, Guido Guenther wrote:
> cinergyt2->streambuf = pci_alloc_consistent(NULL,
> STREAM_URB_COUNT*STREAM_BUF_SIZE,
> &cinergyt2->streambuf_dmahandle);
>
> dma_alloc_coherent doesn't seem to be implemented on sparc64, what would


The DMA channel in question is the PCI hub to which the device is
connected. So it should not be using NULL, it should be passing the pci
device id of the bus controller to whom it is attached

2005-11-11 20:09:51

by David Miller

[permalink] [raw]
Subject: Re: sparc64: Oops in pci_alloc_consistent with cingergyT2

From: Guido Guenther <[email protected]>
Date: Fri, 11 Nov 2005 16:33:55 +0100

> This is due to the fact that cinergyt2_alloc_stream_urbs calls
> pci_alloc_consistent with a NULL argument for the pci dev (it's a USB
> device):
>
> cinergyt2->streambuf = pci_alloc_consistent(NULL,
> STREAM_URB_COUNT*STREAM_BUF_SIZE,
> &cinergyt2->streambuf_dmahandle);
>
> dma_alloc_coherent doesn't seem to be implemented on sparc64, what would
> be the right way to tackle this?

It should be using "usb_buffer_alloc()" or similar.

No USB driver should be calling the DMA mapping interfaces
directly.

Where is this driver? I can't find it in the 2.6.x sources.

2005-11-11 20:13:27

by David Miller

[permalink] [raw]
Subject: Re: sparc64: Oops in pci_alloc_consistent with cingergyT2

From: Alan Cox <[email protected]>
Date: Fri, 11 Nov 2005 19:41:20 +0000

> The DMA channel in question is the PCI hub to which the device is
> connected. So it should not be using NULL, it should be passing the pci
> device id of the bus controller to whom it is attached

We have USB buffer allocation routines for drivers which abstract this
away and perform all the calls correctly, so none of this knowledge
needs to be in a USB driver.

2005-11-12 19:37:08

by Guido Günther

[permalink] [raw]
Subject: Re: sparc64: Oops in pci_alloc_consistent with cingergyT2

On Fri, Nov 11, 2005 at 12:09:50PM -0800, David S. Miller wrote:
> From: Guido Guenther <[email protected]>
> Date: Fri, 11 Nov 2005 16:33:55 +0100
>
> > This is due to the fact that cinergyt2_alloc_stream_urbs calls
> > pci_alloc_consistent with a NULL argument for the pci dev (it's a USB
> > device):
> >
> > cinergyt2->streambuf = pci_alloc_consistent(NULL,
> > STREAM_URB_COUNT*STREAM_BUF_SIZE,
> > &cinergyt2->streambuf_dmahandle);
> >
> > dma_alloc_coherent doesn't seem to be implemented on sparc64, what would
> > be the right way to tackle this?
>
> It should be using "usb_buffer_alloc()" or similar.
>
> No USB driver should be calling the DMA mapping interfaces
> directly.
>
> Where is this driver? I can't find it in the 2.6.x sources.
It's in media/dvb/cinergyT2. The attached patch gives me nice television
on an US5 - but the tv program is crappy as usual.
Cheers and thanks,
-- Guido

P.S.: I didn't check if all the ioctls are really compatible, but the
ones I checked seem to be.

--- linux-2.6.14.orig/drivers/media/dvb/cinergyT2/cinergyT2.c 2005-11-12 19:08:05.000000000 +0100
+++ linux-2.6.14/drivers/media/dvb/cinergyT2/cinergyT2.c 2005-11-12 19:06:51.000000000 +0100
@@ -275,7 +275,7 @@
if (cinergyt2->stream_urb[i])
usb_free_urb(cinergyt2->stream_urb[i]);

- pci_free_consistent(NULL, STREAM_URB_COUNT*STREAM_BUF_SIZE,
+ usb_buffer_free(cinergyt2->udev, STREAM_URB_COUNT*STREAM_BUF_SIZE,
cinergyt2->streambuf, cinergyt2->streambuf_dmahandle);
}

@@ -283,9 +283,8 @@
{
int i;

- cinergyt2->streambuf = pci_alloc_consistent(NULL,
- STREAM_URB_COUNT*STREAM_BUF_SIZE,
- &cinergyt2->streambuf_dmahandle);
+ cinergyt2->streambuf = usb_buffer_alloc(cinergyt2->udev, STREAM_URB_COUNT*STREAM_BUF_SIZE,
+ SLAB_ATOMIC, &cinergyt2->streambuf_dmahandle);
if (!cinergyt2->streambuf) {
dprintk(1, "failed to alloc consistent stream memory area, bailing out!\n");
return -ENOMEM;
--- linux-2.6.14.orig/include/linux/compat_ioctl.h 2005-10-28 02:02:08.000000000 +0200
+++ linux-2.6.14/include/linux/compat_ioctl.h 2005-11-12 19:44:58.000000000 +0100
@@ -786,3 +786,74 @@
COMPATIBLE_IOCTL(HIDIOCSFLAG)
COMPATIBLE_IOCTL(HIDIOCGCOLLECTIONINDEX)
COMPATIBLE_IOCTL(HIDIOCGCOLLECTIONINFO)
+/* dvb */
+COMPATIBLE_IOCTL(AUDIO_STOP)
+COMPATIBLE_IOCTL(AUDIO_PLAY)
+COMPATIBLE_IOCTL(AUDIO_PAUSE)
+COMPATIBLE_IOCTL(AUDIO_CONTINUE)
+COMPATIBLE_IOCTL(AUDIO_SELECT_SOURCE)
+COMPATIBLE_IOCTL(AUDIO_SET_MUTE)
+COMPATIBLE_IOCTL(AUDIO_SET_AV_SYNC)
+COMPATIBLE_IOCTL(AUDIO_SET_BYPASS_MODE)
+COMPATIBLE_IOCTL(AUDIO_CHANNEL_SELECT)
+COMPATIBLE_IOCTL(AUDIO_GET_STATUS)
+COMPATIBLE_IOCTL(AUDIO_GET_CAPABILITIES)
+COMPATIBLE_IOCTL(AUDIO_CLEAR_BUFFER)
+COMPATIBLE_IOCTL(AUDIO_SET_ID)
+COMPATIBLE_IOCTL(AUDIO_SET_MIXER)
+COMPATIBLE_IOCTL(AUDIO_SET_STREAMTYPE)
+COMPATIBLE_IOCTL(AUDIO_SET_EXT_ID)
+COMPATIBLE_IOCTL(AUDIO_SET_ATTRIBUTES)
+COMPATIBLE_IOCTL(AUDIO_SET_KARAOKE)
+COMPATIBLE_IOCTL(DMX_START)
+COMPATIBLE_IOCTL(DMX_STOP)
+COMPATIBLE_IOCTL(DMX_SET_FILTER)
+COMPATIBLE_IOCTL(DMX_SET_PES_FILTER)
+COMPATIBLE_IOCTL(DMX_SET_BUFFER_SIZE)
+COMPATIBLE_IOCTL(DMX_GET_EVENT)
+COMPATIBLE_IOCTL(DMX_GET_PES_PIDS)
+COMPATIBLE_IOCTL(DMX_GET_CAPS)
+COMPATIBLE_IOCTL(DMX_SET_SOURCE)
+COMPATIBLE_IOCTL(DMX_GET_STC)
+COMPATIBLE_IOCTL(FE_GET_INFO)
+COMPATIBLE_IOCTL(FE_DISEQC_RESET_OVERLOAD)
+COMPATIBLE_IOCTL(FE_DISEQC_SEND_MASTER_CMD)
+COMPATIBLE_IOCTL(FE_DISEQC_RECV_SLAVE_REPLY)
+COMPATIBLE_IOCTL(FE_DISEQC_SEND_BURST)
+COMPATIBLE_IOCTL(FE_SET_TONE)
+COMPATIBLE_IOCTL(FE_SET_VOLTAGE)
+COMPATIBLE_IOCTL(FE_ENABLE_HIGH_LNB_VOLTAGE)
+COMPATIBLE_IOCTL(FE_READ_STATUS)
+COMPATIBLE_IOCTL(FE_READ_BER)
+COMPATIBLE_IOCTL(FE_READ_SIGNAL_STRENGTH)
+COMPATIBLE_IOCTL(FE_READ_SNR)
+COMPATIBLE_IOCTL(FE_READ_UNCORRECTED_BLOCKS)
+COMPATIBLE_IOCTL(FE_SET_FRONTEND)
+COMPATIBLE_IOCTL(FE_GET_FRONTEND)
+COMPATIBLE_IOCTL(FE_GET_EVENT)
+COMPATIBLE_IOCTL(FE_DISHNETWORK_SEND_LEGACY_CMD)
+COMPATIBLE_IOCTL(VIDEO_STOP)
+COMPATIBLE_IOCTL(VIDEO_PLAY)
+COMPATIBLE_IOCTL(VIDEO_FREEZE)
+COMPATIBLE_IOCTL(VIDEO_CONTINUE)
+COMPATIBLE_IOCTL(VIDEO_SELECT_SOURCE)
+COMPATIBLE_IOCTL(VIDEO_SET_BLANK)
+COMPATIBLE_IOCTL(VIDEO_GET_STATUS)
+COMPATIBLE_IOCTL(VIDEO_GET_EVENT)
+COMPATIBLE_IOCTL(VIDEO_SET_DISPLAY_FORMAT)
+COMPATIBLE_IOCTL(VIDEO_STILLPICTURE)
+COMPATIBLE_IOCTL(VIDEO_FAST_FORWARD)
+COMPATIBLE_IOCTL(VIDEO_SLOWMOTION)
+COMPATIBLE_IOCTL(VIDEO_GET_CAPABILITIES)
+COMPATIBLE_IOCTL(VIDEO_CLEAR_BUFFER)
+COMPATIBLE_IOCTL(VIDEO_SET_ID)
+COMPATIBLE_IOCTL(VIDEO_SET_STREAMTYPE)
+COMPATIBLE_IOCTL(VIDEO_SET_FORMAT)
+COMPATIBLE_IOCTL(VIDEO_SET_SYSTEM)
+COMPATIBLE_IOCTL(VIDEO_SET_HIGHLIGHT)
+COMPATIBLE_IOCTL(VIDEO_SET_SPU)
+COMPATIBLE_IOCTL(VIDEO_SET_SPU_PALETTE)
+COMPATIBLE_IOCTL(VIDEO_GET_NAVI)
+COMPATIBLE_IOCTL(VIDEO_SET_ATTRIBUTES)
+COMPATIBLE_IOCTL(VIDEO_GET_SIZE)
+COMPATIBLE_IOCTL(VIDEO_GET_FRAME_RATE)
--- linux-2.6.14.orig/fs/compat_ioctl.c 2005-10-28 02:02:08.000000000 +0200
+++ linux-2.6.14/fs/compat_ioctl.c 2005-11-12 19:51:50.000000000 +0100
@@ -121,6 +121,11 @@

#include <linux/hiddev.h>

+#include <linux/dvb/audio.h>
+#include <linux/dvb/dmx.h>
+#include <linux/dvb/frontend.h>
+#include <linux/dvb/video.h>
+
#undef INCLUDES
#endif

2005-11-13 19:10:24

by Johannes Stezenbach

[permalink] [raw]
Subject: Re: sparc64: Oops in pci_alloc_consistent with cingergyT2

On Sat, Nov 12, 2005 at 08:17:08PM +0100, Guido Guenther wrote:
> On Fri, Nov 11, 2005 at 12:09:50PM -0800, David S. Miller wrote:
> > From: Guido Guenther <[email protected]>
> > Date: Fri, 11 Nov 2005 16:33:55 +0100
> >
> > > This is due to the fact that cinergyt2_alloc_stream_urbs calls
> > > pci_alloc_consistent with a NULL argument for the pci dev (it's a USB
> > > device):
> > >
> > > cinergyt2->streambuf = pci_alloc_consistent(NULL,
> > > STREAM_URB_COUNT*STREAM_BUF_SIZE,
> > > &cinergyt2->streambuf_dmahandle);
> > >
> > > dma_alloc_coherent doesn't seem to be implemented on sparc64, what would
> > > be the right way to tackle this?
> >
> > It should be using "usb_buffer_alloc()" or similar.
> >
> > No USB driver should be calling the DMA mapping interfaces
> > directly.
> >
> > Where is this driver? I can't find it in the 2.6.x sources.
> It's in media/dvb/cinergyT2. The attached patch gives me nice television
> on an US5 - but the tv program is crappy as usual.
> Cheers and thanks,
> -- Guido
>
> P.S.: I didn't check if all the ioctls are really compatible, but the
> ones I checked seem to be.

Thanks for fixing this up. Just make sure to Cc: the maintainers.


Johannes


> --- linux-2.6.14.orig/drivers/media/dvb/cinergyT2/cinergyT2.c 2005-11-12 19:08:05.000000000 +0100
> +++ linux-2.6.14/drivers/media/dvb/cinergyT2/cinergyT2.c 2005-11-12 19:06:51.000000000 +0100
> @@ -275,7 +275,7 @@
> if (cinergyt2->stream_urb[i])
> usb_free_urb(cinergyt2->stream_urb[i]);
>
> - pci_free_consistent(NULL, STREAM_URB_COUNT*STREAM_BUF_SIZE,
> + usb_buffer_free(cinergyt2->udev, STREAM_URB_COUNT*STREAM_BUF_SIZE,
> cinergyt2->streambuf, cinergyt2->streambuf_dmahandle);
> }
>
> @@ -283,9 +283,8 @@
> {
> int i;
>
> - cinergyt2->streambuf = pci_alloc_consistent(NULL,
> - STREAM_URB_COUNT*STREAM_BUF_SIZE,
> - &cinergyt2->streambuf_dmahandle);
> + cinergyt2->streambuf = usb_buffer_alloc(cinergyt2->udev, STREAM_URB_COUNT*STREAM_BUF_SIZE,
> + SLAB_ATOMIC, &cinergyt2->streambuf_dmahandle);
> if (!cinergyt2->streambuf) {
> dprintk(1, "failed to alloc consistent stream memory area, bailing out!\n");
> return -ENOMEM;
> --- linux-2.6.14.orig/include/linux/compat_ioctl.h 2005-10-28 02:02:08.000000000 +0200
> +++ linux-2.6.14/include/linux/compat_ioctl.h 2005-11-12 19:44:58.000000000 +0100
> @@ -786,3 +786,74 @@
> COMPATIBLE_IOCTL(HIDIOCSFLAG)
> COMPATIBLE_IOCTL(HIDIOCGCOLLECTIONINDEX)
> COMPATIBLE_IOCTL(HIDIOCGCOLLECTIONINFO)
> +/* dvb */
> +COMPATIBLE_IOCTL(AUDIO_STOP)
> +COMPATIBLE_IOCTL(AUDIO_PLAY)
> +COMPATIBLE_IOCTL(AUDIO_PAUSE)
> +COMPATIBLE_IOCTL(AUDIO_CONTINUE)
> +COMPATIBLE_IOCTL(AUDIO_SELECT_SOURCE)
> +COMPATIBLE_IOCTL(AUDIO_SET_MUTE)
> +COMPATIBLE_IOCTL(AUDIO_SET_AV_SYNC)
> +COMPATIBLE_IOCTL(AUDIO_SET_BYPASS_MODE)
> +COMPATIBLE_IOCTL(AUDIO_CHANNEL_SELECT)
> +COMPATIBLE_IOCTL(AUDIO_GET_STATUS)
> +COMPATIBLE_IOCTL(AUDIO_GET_CAPABILITIES)
> +COMPATIBLE_IOCTL(AUDIO_CLEAR_BUFFER)
> +COMPATIBLE_IOCTL(AUDIO_SET_ID)
> +COMPATIBLE_IOCTL(AUDIO_SET_MIXER)
> +COMPATIBLE_IOCTL(AUDIO_SET_STREAMTYPE)
> +COMPATIBLE_IOCTL(AUDIO_SET_EXT_ID)
> +COMPATIBLE_IOCTL(AUDIO_SET_ATTRIBUTES)
> +COMPATIBLE_IOCTL(AUDIO_SET_KARAOKE)
> +COMPATIBLE_IOCTL(DMX_START)
> +COMPATIBLE_IOCTL(DMX_STOP)
> +COMPATIBLE_IOCTL(DMX_SET_FILTER)
> +COMPATIBLE_IOCTL(DMX_SET_PES_FILTER)
> +COMPATIBLE_IOCTL(DMX_SET_BUFFER_SIZE)
> +COMPATIBLE_IOCTL(DMX_GET_EVENT)
> +COMPATIBLE_IOCTL(DMX_GET_PES_PIDS)
> +COMPATIBLE_IOCTL(DMX_GET_CAPS)
> +COMPATIBLE_IOCTL(DMX_SET_SOURCE)
> +COMPATIBLE_IOCTL(DMX_GET_STC)
> +COMPATIBLE_IOCTL(FE_GET_INFO)
> +COMPATIBLE_IOCTL(FE_DISEQC_RESET_OVERLOAD)
> +COMPATIBLE_IOCTL(FE_DISEQC_SEND_MASTER_CMD)
> +COMPATIBLE_IOCTL(FE_DISEQC_RECV_SLAVE_REPLY)
> +COMPATIBLE_IOCTL(FE_DISEQC_SEND_BURST)
> +COMPATIBLE_IOCTL(FE_SET_TONE)
> +COMPATIBLE_IOCTL(FE_SET_VOLTAGE)
> +COMPATIBLE_IOCTL(FE_ENABLE_HIGH_LNB_VOLTAGE)
> +COMPATIBLE_IOCTL(FE_READ_STATUS)
> +COMPATIBLE_IOCTL(FE_READ_BER)
> +COMPATIBLE_IOCTL(FE_READ_SIGNAL_STRENGTH)
> +COMPATIBLE_IOCTL(FE_READ_SNR)
> +COMPATIBLE_IOCTL(FE_READ_UNCORRECTED_BLOCKS)
> +COMPATIBLE_IOCTL(FE_SET_FRONTEND)
> +COMPATIBLE_IOCTL(FE_GET_FRONTEND)
> +COMPATIBLE_IOCTL(FE_GET_EVENT)
> +COMPATIBLE_IOCTL(FE_DISHNETWORK_SEND_LEGACY_CMD)
> +COMPATIBLE_IOCTL(VIDEO_STOP)
> +COMPATIBLE_IOCTL(VIDEO_PLAY)
> +COMPATIBLE_IOCTL(VIDEO_FREEZE)
> +COMPATIBLE_IOCTL(VIDEO_CONTINUE)
> +COMPATIBLE_IOCTL(VIDEO_SELECT_SOURCE)
> +COMPATIBLE_IOCTL(VIDEO_SET_BLANK)
> +COMPATIBLE_IOCTL(VIDEO_GET_STATUS)
> +COMPATIBLE_IOCTL(VIDEO_GET_EVENT)
> +COMPATIBLE_IOCTL(VIDEO_SET_DISPLAY_FORMAT)
> +COMPATIBLE_IOCTL(VIDEO_STILLPICTURE)
> +COMPATIBLE_IOCTL(VIDEO_FAST_FORWARD)
> +COMPATIBLE_IOCTL(VIDEO_SLOWMOTION)
> +COMPATIBLE_IOCTL(VIDEO_GET_CAPABILITIES)
> +COMPATIBLE_IOCTL(VIDEO_CLEAR_BUFFER)
> +COMPATIBLE_IOCTL(VIDEO_SET_ID)
> +COMPATIBLE_IOCTL(VIDEO_SET_STREAMTYPE)
> +COMPATIBLE_IOCTL(VIDEO_SET_FORMAT)
> +COMPATIBLE_IOCTL(VIDEO_SET_SYSTEM)
> +COMPATIBLE_IOCTL(VIDEO_SET_HIGHLIGHT)
> +COMPATIBLE_IOCTL(VIDEO_SET_SPU)
> +COMPATIBLE_IOCTL(VIDEO_SET_SPU_PALETTE)
> +COMPATIBLE_IOCTL(VIDEO_GET_NAVI)
> +COMPATIBLE_IOCTL(VIDEO_SET_ATTRIBUTES)
> +COMPATIBLE_IOCTL(VIDEO_GET_SIZE)
> +COMPATIBLE_IOCTL(VIDEO_GET_FRAME_RATE)
> --- linux-2.6.14.orig/fs/compat_ioctl.c 2005-10-28 02:02:08.000000000 +0200
> +++ linux-2.6.14/fs/compat_ioctl.c 2005-11-12 19:51:50.000000000 +0100
> @@ -121,6 +121,11 @@
>
> #include <linux/hiddev.h>
>
> +#include <linux/dvb/audio.h>
> +#include <linux/dvb/dmx.h>
> +#include <linux/dvb/frontend.h>
> +#include <linux/dvb/video.h>
> +
> #undef INCLUDES
> #endif
>
> -
> To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
> the body of a message to [email protected]
> More majordomo info at http://vger.kernel.org/majordomo-info.html
> Please read the FAQ at http://www.tux.org/lkml/
>