Message ID | 4EC374F0.8000400@metasoft.pl |
---|---|
State | New |
Headers | show |
Hello. > I wasn't able to reproduce this but can you try if following patch helps? I'm > not sure if it is correct but at least we get more information about the > problem. > > diff --git a/drivers/dma/ep93xx_dma.c b/drivers/dma/ep93xx_dma.c > index 6181811..5b717da 100644 > --- a/drivers/dma/ep93xx_dma.c > +++ b/drivers/dma/ep93xx_dma.c > @@ -1106,6 +1106,7 @@ static int ep93xx_dma_terminate_all(struct ep93xx_dma_chan *edmac) > spin_lock_irqsave(&edmac->lock, flags); > /* First we disable and flush the DMA channel */ > edmac->edma->hw_shutdown(edmac); > + tasklet_kill(&edmac->tasklet); > clear_bit(EP93XX_DMA_IS_CYCLIC, &edmac->flags); > list_splice_init(&edmac->active, &list); > list_splice_init(&edmac->queue, &list); > It doesn't help: Linux version 3.2.0-rc2EP-1+ (prylowski@server) (gcc version 4.4.2 (GCC) ) #1015 Mon Nov 21 08:30:57 CET 2011 CPU: ARM920T [41129200] revision 0 (ARMv4T), cr=c0007177 CPU: VIVT data cache, VIVT instruction cache Machine: Metasoft FonTel EP Board Memory policy: ECC disabled, Data cache writeback Built 1 zonelists in Zone order, mobility grouping on. Total pages: 8128 Kernel command line: mtdparts=physmap-flash.0:128K(uboot),1152K(kernel),15104K(r ootfs) root=/dev/mtdblock2 rootfstype=jffs2 console=ttyAM0 init=/sbin/init early printk lpj=496128 panic=2 PID hash table entries: 128 (order: -3, 512 bytes) Dentry cache hash table entries: 4096 (order: 2, 16384 bytes) Inode-cache hash table entries: 2048 (order: 1, 8192 bytes) Memory: 32MB = 32MB total Memory: 27452k/27452k available, 5316k reserved, 0K highmem Virtual kernel memory layout: vector : 0xffff0000 - 0xffff1000 ( 4 kB) fixmap : 0xfff00000 - 0xfffe0000 ( 896 kB) vmalloc : 0xc2800000 - 0xfe800000 ( 960 MB) lowmem : 0xc0000000 - 0xc2000000 ( 32 MB) modules : 0xbf000000 - 0xc0000000 ( 16 MB) .text : 0xc0008000 - 0xc029d000 (2644 kB) .init : 0xc029d000 - 0xc02b6000 ( 100 kB) .data : 0xc02b6000 - 0xc02d1440 ( 110 kB) .bss : 0xc02d1464 - 0xc02df51c ( 57 kB) SLUB: Genslabs=13, HWalign=32, Order=0-3, MinObjects=0, CPUs=1, Nodes=1 NR_IRQS:120 VIC @fefb0000: id 0x00041190, vendor 0x41 VIC @fefc0000: id 0x00041190, vendor 0x41 Console: colour dummy device 80x30 Calibrating delay loop (skipped) preset value.. 99.22 BogoMIPS (lpj=496128) pid_max: default: 32768 minimum: 301 Mount-cache hash table entries: 512 CPU: Testing write buffer coherency: ok NET: Registered protocol family 16 ep93xx clock: PLL1 running at 400 MHz, PLL2 at 192 MHz ep93xx clock: FCLK 200 MHz, HCLK 100 MHz, PCLK 50 MHz bio: create slab <bio-0> at 0 ep93xx-dma ep93xx-dma-m2p: EP93xx M2P DMA ready ep93xx-dma ep93xx-dma-m2m: EP93xx M2M DMA ready SCSI subsystem initialized usbcore: registered new interface driver usbfs usbcore: registered new interface driver hub usbcore: registered new device driver usb i2c-gpio i2c-gpio.0: using pins 49 (SDA) and 48 (SCL) NET: Registered protocol family 2 IP route cache hash table entries: 1024 (order: 0, 4096 bytes) TCP established hash table entries: 1024 (order: 1, 8192 bytes) TCP bind hash table entries: 1024 (order: 0, 4096 bytes) TCP: Hash tables configured (established 1024 bind 1024) TCP reno registered UDP hash table entries: 256 (order: 0, 4096 bytes) UDP-Lite hash table entries: 256 (order: 0, 4096 bytes) NET: Registered protocol family 1 JFFS2 version 2.2. (NAND) © 2001-2006 Red Hat, Inc. msgmni has been set to 53 io scheduler noop registered io scheduler deadline registered (default) Serial: AMBA driver apb:uart1: ttyAM0 at MMIO 0x808c0000 (irq = 52) is a AMBA console [ttyAM0] enabled apb:uart2: ttyAM1 at MMIO 0x808d0000 (irq = 54) is a AMBA apb:uart3: ttyAM2 at MMIO 0x808e0000 (irq = 55) is a AMBA fontel-pri fontel-pri: FonTel PRI initialized correctly. ep93xx-ide ep93xx-ide: version 0.5 scsi0 : ep93xx-ide ata1: PATA max UDMA/66 irq 40 physmap platform flash device: 01000000 at 60000000 physmap-flash.0: Found 1 x16 devices at 0x0 in 16-bit bank. Manufacturer ID 0x00 0001 Chip ID 0x002101 Amd/Fujitsu Extended Query Table at 0x0040 Amd/Fujitsu Extended Query version 1.3. number of CFI chips: 1 3 cmdlinepart partitions found on MTD device physmap-flash.0 Creating 3 MTD partitions on "physmap-flash.0": 0x000000000000-0x000000020000 : "uboot" 0x000000020000-0x000000140000 : "kernel" 0x000000140000-0x000001000000 : "rootfs" ep93xx-spi ep93xx-spi.0: EP93xx SPI Controller at 0x808a0000 irq 53 ep93xx-eth version 0.1 loading eth0: ep93xx on-chip ethernet, IRQ 39, aa:42:14:07:63:9d ohci_hcd: USB 1.1 'Open' Host Controller (OHCI) Driver ep93xx-ohci ep93xx-ohci: EP93xx OHCI ep93xx-ohci ep93xx-ohci: new USB bus registered, assigned bus number 1 ep93xx-ohci ep93xx-ohci: irq 56, io mem 0x80020000 ata1.00: HPA detected: current 234439535, native 234441648 ata1.00: ATA-7: ST9120822AS, 3.ALC, max UDMA/133 ata1.00: 234439535 sectors, multi 0: LBA48 hub 1-0:1.0: USB hub found hub 1-0:1.0: 3 ports detected Initializing USB Mass Storage driver... usbcore: registered new interface driver usb-storage USB Mass Storage support registered. ata1.00: configured for UDMA/66 scsi 0:0:0:0: Direct-Access ATA ST9120822AS 3.AL PQ: 0 ANSI: 5 usbcore: registered new interface driver fontel sd 0:0:0:0: [sda] 234439535 512-byte logical blocks: (120 GB/111 GiB) rtc-ds1307 0-0068: rtc core: registered ds1307 as rtc0 rtc-ds1307 0-0068: 56 bytes nvram sd 0:0:0:0: [sda] Write Protect is off sd 0:0:0:0: [sda] Write cache: enabled, read cache: enabled, doesn't support DPO or FUA ep93xx-rtc ep93xx-rtc: rtc core: registered ep93xx-rtc as rtc1 Software Watchdog Timer: 0.07 initialized. soft_noboot=0 soft_margin=60 sec soft _panic=0 (nowayout= 0) TCP cubic registered NET: Registered protocol family 17 NET: Registered protocol family 15 ep93xx-rtc ep93xx-rtc: setting system clock to 1970-01-01 00:00:07 UTC (7) Attempt to kill tasklet from interrupt Unable to handle kernel NULL pointer dereference at virtual address 00000000 pgd = c0004000 [00000000] *pgd=00000000 Internal error: Oops: 80000005 [#1] CPU: 0 Not tainted (3.2.0-rc2EP-1+ #1015) PC is at 0x0 LR is at sys_sched_yield+0x38/0x48 pc : [<00000000>] lr : [<c0015030>] psr: 20000093 sp : c02b7ce8 ip : c02b7cf8 fp : c02b7cf4 r10: c1918000 r9 : c19180a4 r8 : 00002118 r7 : 00000004 r6 : c02b7d20 r5 : c184d6bc r4 : c184d6b8 r3 : c023e458 r2 : c02b7ce8 r1 : 00000001 r0 : c02bcff0 Flags: nzCv IRQs off FIQs on Mode SVC_32 ISA ARM Segment kernel Control: c000717f Table: c0004000 DAC: 00000017 Process swapper (pid: 0, stack limit = 0xc02b6270) Stack: (0xc02b7ce8 to 0xc02b8000) 7ce0: c02b7d04 c02b7cf8 c023bdcc c0015008 c02b7d1c c02b7d08 7d00: c001ca04 c023bdb4 60000093 c184d680 c02b7d44 c02b7d20 c012ac8c c001c9d8 7d20: c02b7d20 c02b7d20 c02b7d44 c1914070 c19180a4 c2860000 c02b7d64 c02b7d48 7d40: c0177c50 c012ac54 c19180a4 c1918000 00000004 00000004 c02b7d8c c02b7d68 7d60: c0176a64 c0177c20 00000000 c1914190 00000000 00000001 0000000b c19180a4 7d80: c02b7dd4 c02b7d90 c0176cc0 c01769c4 00000001 40000093 00000000 00000000 7da0: c1914190 00000000 c1822000 c1912a80 00000028 00000000 00000000 00000028 7dc0: c02d8148 c02c0084 c02b7e0c c02b7dd8 c00426d0 c0176ae0 c02b7dfc c02b7de8 7de0: c0035628 c02c0084 00000028 c02b7f48 c02b7eb4 c02bd44c c02d60e0 c02b0c90 7e00: c02b7e24 c02b7e10 c004285c c004268c c02c0084 00000028 c02b7e3c c02b7e28 7e20: c0045178 c004283c c02c4578 00000028 c02b7e4c c02b7e40 c0042254 c00450fc 7e40: c02b7e6c c02b7e50 c0009838 c0042228 c001cb80 20000013 fefc0001 c02b7eb4 7e60: c02b7e7c c02b7e70 c0008190 c0009810 c02b7f04 c02b7e80 c0008b64 c0008190 7e80: 00000000 00000000 00000000 20000013 00000040 00000040 c02d60e0 c02b6000 7ea0: c02bd44c c02d60e0 c02b0c90 c02b7f04 c02b7f08 c02b7ec8 c001cdd0 c001cb80 7ec0: 20000013 ffffffff c02b7eec c02b7ed8 c004496c 0000000a c02bf674 c02c4578 7ee0: 00000011 00000000 c02b7f7c c0004000 41129200 c02b0c90 c02b7f14 c02b7f08 7f00: c001cdd0 c001cb38 c02b7f34 c02b7f18 c000983c c001cd98 c0009a60 60000013 7f20: fefb0001 c02b7f7c c02b7f44 c02b7f38 c0008190 c0009810 c02b7f9c c02b7f48 7f40: c0008b64 c0008190 c02c2bf8 00000002 c02b7f90 60000013 c02b6000 c02d1504 7f60: c02baa88 c02baa80 c0004000 41129200 c02b0c90 c02b7f9c c02b7fa0 c02b7f90 7f80: c0009a54 c0009a60 60000013 ffffffff c02b7fbc c02b7fa0 c000a03c c0009a40 7fa0: c02b80b0 c02b19ec c02b19e8 c02baa80 c02b7fcc c02b7fc0 c02384b4 c0009fd4 7fc0: c02b7ff4 c02b7fd0 c029d924 c0238464 c029d49c 00000000 00000000 c02b19ec 7fe0: c0007175 c02b803c 00000000 c02b7ff8 c000803c c029d700 00000000 00000000 Backtrace: [<c0014ff8>] (sys_sched_yield+0x0/0x48) from [<c023bdcc>] (yield+0x28/0x2c) [<c023bda4>] (yield+0x0/0x2c) from [<c001ca04>] (tasklet_kill+0x3c/0x9c) [<c001c9c8>] (tasklet_kill+0x0/0x9c) from [<c012ac8c>] (ep93xx_dma_control+0x48/ 0x1c0) r5:c184d680 r4:60000093 [<c012ac44>] (ep93xx_dma_control+0x0/0x1c0) from [<c0177c50>] (ep93xx_pata_dma_s top+0x40/0xb8) r6:c2860000 r5:c19180a4 r4:c1914070 [<c0177c10>] (ep93xx_pata_dma_stop+0x0/0xb8) from [<c0176a64>] (ata_bmdma_port_i ntr+0xb0/0x11c) r7:00000004 r6:00000004 r5:c1918000 r4:c19180a4 [<c01769b4>] (ata_bmdma_port_intr+0x0/0x11c) from [<c0176cc0>] (ata_bmdma_interr upt+0x1f0/0x274) r9:c19180a4 r8:0000000b r7:00000001 r6:00000000 r5:c1914190 r4:00000000 [<c0176ad0>] (ata_bmdma_interrupt+0x0/0x274) from [<c00426d0>] (handle_irq_event _percpu+0x54/0x1b0) [<c004267c>] (handle_irq_event_percpu+0x0/0x1b0) from [<c004285c>] (handle_irq_e vent+0x30/0x40) [<c004282c>] (handle_irq_event+0x0/0x40) from [<c0045178>] (handle_level_irq+0x8 c/0xe8) r5:00000028 r4:c02c0084 [<c00450ec>] (handle_level_irq+0x0/0xe8) from [<c0042254>] (generic_handle_irq+0 x3c/0x48) r5:00000028 r4:c02c4578 [<c0042218>] (generic_handle_irq+0x0/0x48) from [<c0009838>] (handle_IRQ+0x38/0x 8c) [<c0009800>] (handle_IRQ+0x0/0x8c) from [<c0008190>] (asm_do_IRQ+0x10/0x14) r7:c02b7eb4 r6:fefc0001 r5:20000013 r4:c001cb80 [<c0008180>] (asm_do_IRQ+0x0/0x14) from [<c0008b64>] (__irq_svc+0x24/0xc0) Exception stack(0xc02b7e80 to 0xc02b7ec8) 7e80: 00000000 00000000 00000000 20000013 00000040 00000040 c02d60e0 c02b6000 7ea0: c02bd44c c02d60e0 c02b0c90 c02b7f04 c02b7f08 c02b7ec8 c001cdd0 c001cb80 7ec0: 20000013 ffffffff [<c001cb28>] (__do_softirq+0x0/0x154) from [<c001cdd0>] (irq_exit+0x48/0x50) [<c001cd88>] (irq_exit+0x0/0x50) from [<c000983c>] (handle_IRQ+0x3c/0x8c) [<c0009800>] (handle_IRQ+0x0/0x8c) from [<c0008190>] (asm_do_IRQ+0x10/0x14) r7:c02b7f7c r6:fefb0001 r5:60000013 r4:c0009a60 [<c0008180>] (asm_do_IRQ+0x0/0x14) from [<c0008b64>] (__irq_svc+0x24/0xc0) Exception stack(0xc02b7f48 to 0xc02b7f90) 7f40: c02c2bf8 00000002 c02b7f90 60000013 c02b6000 c02d1504 7f60: c02baa88 c02baa80 c0004000 41129200 c02b0c90 c02b7f9c c02b7fa0 c02b7f90 7f80: c0009a54 c0009a60 60000013 ffffffff [<c0009a30>] (default_idle+0x0/0x34) from [<c000a03c>] (cpu_idle+0x78/0xb0) [<c0009fc4>] (cpu_idle+0x0/0xb0) from [<c02384b4>] (rest_init+0x60/0x78) r7:c02baa80 r6:c02b19e8 r5:c02b19ec r4:c02b80b0 [<c0238454>] (rest_init+0x0/0x78) from [<c029d924>] (start_kernel+0x234/0x278) [<c029d6f0>] (start_kernel+0x0/0x278) from [<c000803c>] (0xc000803c) r5:c02b803c r4:c0007175 Code: bad PC value ---[ end trace 3d4b7b18cc0879b4 ]--- Kernel panic - not syncing: Fatal exception in interrupt Rebooting in 2 seconds.. I'm calling dma_terminate_all from interrupt. It seems that tasklet_kill is not allowed to be called from this context. Thanks, Rafał Pryłowski.
On Mon, 2011-11-21 at 10:01 +0200, Mika Westerberg wrote: > On Mon, Nov 21, 2011 at 08:44:07AM +0100, Rafal Prylowski wrote: > > > > I'm calling dma_terminate_all from interrupt. It seems that tasklet_kill is not > > allowed to be called from this context. > > Ah, right. > > One more try - this time we set a flag which prevents the tasktlet from > referencing an empty list. Rather than this why not actually check for list_empty and process only when it is not empty? Also you should check the return of the ep93xx_dma_get_active() which should return NULL if it didn't find anything in active list > > diff --git a/drivers/dma/ep93xx_dma.c b/drivers/dma/ep93xx_dma.c > index 6181811..f7244b3 100644 > --- a/drivers/dma/ep93xx_dma.c > +++ b/drivers/dma/ep93xx_dma.c > @@ -155,6 +155,8 @@ struct ep93xx_dma_chan { > unsigned long flags; > /* Channel is configured for cyclic transfers */ > #define EP93XX_DMA_IS_CYCLIC 0 > +/* Channel is enabled */ > +#define EP93xx_DMA_IS_RUNNING 1 > > int buffer; > dma_cookie_t last_completed; > @@ -673,6 +675,9 @@ static void ep93xx_dma_tasklet(unsigned long data) > void *callback_param; > LIST_HEAD(list); > > + if (!test_bit(EP93XX_DMA_IS_RUNNING, &edmac->flags)) > + return; > + > spin_lock_irq(&edmac->lock); > desc = ep93xx_dma_get_active(edmac); > if (desc->complete) { > @@ -758,6 +763,8 @@ static dma_cookie_t ep93xx_dma_tx_submit(struct dma_async_tx_descriptor *tx) > edmac->chan.cookie = cookie; > desc->txd.cookie = cookie; > > + set_bit(EP93XX_DMA_IS_RUNNING, &edmac->flags); > + > /* > * If nothing is currently prosessed, we push this descriptor > * directly to the hardware. Otherwise we put the descriptor > @@ -1106,6 +1113,7 @@ static int ep93xx_dma_terminate_all(struct ep93xx_dma_chan *edmac) > spin_lock_irqsave(&edmac->lock, flags); > /* First we disable and flush the DMA channel */ > edmac->edma->hw_shutdown(edmac); > + clear_bit(EP93XX_DMA_IS_RUNNING, &edmac->flags); > clear_bit(EP93XX_DMA_IS_CYCLIC, &edmac->flags); > list_splice_init(&edmac->active, &list); > list_splice_init(&edmac->queue, &list); > > _______________________________________________ > linux-arm-kernel mailing list > linux-arm-kernel@lists.infradead.org > http://lists.infradead.org/mailman/listinfo/linux-arm-kernel
>> I'm calling dma_terminate_all from interrupt. It seems that tasklet_kill is not >> allowed to be called from this context. > > Ah, right. > > One more try - this time we set a flag which prevents the tasktlet from > referencing an empty list. > > diff --git a/drivers/dma/ep93xx_dma.c b/drivers/dma/ep93xx_dma.c > index 6181811..f7244b3 100644 > --- a/drivers/dma/ep93xx_dma.c > +++ b/drivers/dma/ep93xx_dma.c > @@ -155,6 +155,8 @@ struct ep93xx_dma_chan { > unsigned long flags; > /* Channel is configured for cyclic transfers */ > #define EP93XX_DMA_IS_CYCLIC 0 > +/* Channel is enabled */ > +#define EP93xx_DMA_IS_RUNNING 1 > > int buffer; > dma_cookie_t last_completed; > @@ -673,6 +675,9 @@ static void ep93xx_dma_tasklet(unsigned long data) > void *callback_param; > LIST_HEAD(list); > > + if (!test_bit(EP93XX_DMA_IS_RUNNING, &edmac->flags)) > + return; > + > spin_lock_irq(&edmac->lock); > desc = ep93xx_dma_get_active(edmac); > if (desc->complete) { > @@ -758,6 +763,8 @@ static dma_cookie_t ep93xx_dma_tx_submit(struct dma_async_tx_descriptor *tx) > edmac->chan.cookie = cookie; > desc->txd.cookie = cookie; > > + set_bit(EP93XX_DMA_IS_RUNNING, &edmac->flags); > + > /* > * If nothing is currently prosessed, we push this descriptor > * directly to the hardware. Otherwise we put the descriptor > @@ -1106,6 +1113,7 @@ static int ep93xx_dma_terminate_all(struct ep93xx_dma_chan *edmac) > spin_lock_irqsave(&edmac->lock, flags); > /* First we disable and flush the DMA channel */ > edmac->edma->hw_shutdown(edmac); > + clear_bit(EP93XX_DMA_IS_RUNNING, &edmac->flags); > clear_bit(EP93XX_DMA_IS_CYCLIC, &edmac->flags); > list_splice_init(&edmac->active, &list); > list_splice_init(&edmac->queue, &list); > This patch works partially for me. Drive is detected correctly, I can do simple test with hdparm, mount partitions, create file with 'touch' command, but when trying to fill partition with data I get: # dd if=/dev/zero of=/mnt/b/zero4 bs=4M Internal error: Oops - undefined instruction: 0 [#1] CPU: 0 Not tainted (3.2.0-rc2EP-1+ #1017) PC is at 0xc1862868 LR is at ep93xx_dma_tasklet+0xc4/0x174 pc : [<c1862868>] lr : [<c012b498>] psr: 00000013 sp : c10c3b60 ip : ffffffff fp : c10c3b94 r10: 00000100 r9 : 80000013 r8 : c10c3b40 r7 : c10c3b60 r6 : c10c3b94 r5 : 00000094 r4 : c10c3b60 r3 : c10c320d r2 : a0e96520 r1 : c1862758 r0 : c10c3b94 Flags: nzcv IRQs on FIQs on Mode SVC_32 ISA ARM Segment user Control: c000717f Table: c1240000 DAC: 00000015 Process dd (pid: 619, stack limit = 0xc10c2270) Stack: (0xc10c3b60 to 0xc10c4000) 3b60: c10c3b94 c10c3b60 00000001 c02bd5c4 c02d60e0 00000000 00000000 c02bd44c 3b80: c02d60e0 00000100 c10c3bb4 c10c3b98 c001c49c c012b3e4 00000018 00000001 3ba0: c02d60e0 c10c2000 c10c3bf4 c10c3bb8 c001cbc0 c001c3e4 c10c3bdc c10c3bc8 3bc0: 00000006 0000000a c02bf6e4 c02c4578 00000012 00000000 c10c3c6c 00000000 3be0: 00000000 00000000 c10c3c04 c10c3bf8 c001cdd0 c001cb38 c10c3c24 c10c3c08 3c00: c000983c c001cd98 c00e1160 80000013 fefb0001 c10c3c6c c10c3c34 c10c3c28 3c20: c0008190 c0009810 c10c3ccc c10c3c38 c0008b64 c0008190 c1a44058 00000003 3c40: ffffb58e ffffffc7 c156a000 c1a70060 c10c2000 c1a44000 00000000 00000000 3c60: 00000000 c10c3ccc c1a4404c c10c3c80 c0011a28 c00e1160 80000013 ffffffff 3c80: 00000000 00001000 c10c3cb4 c10c3c98 c00d9eac c00e0f88 c156a000 c1791250 3ca0: c156a000 00000000 c0242f4c c1a44600 03605000 00000000 00000000 00001000 3cc0: c10c3cec c10c3cd0 c00d9eac c00e0f88 c1791250 c02f9860 c156a000 03605000 3ce0: c10c3d2c c10c3cf0 c00d3d7c c00d9e94 00001000 00001000 c02f9860 c008df3c 3d00: c10c3d58 c0242d18 c10c2000 c1791308 00000000 c10c3d58 00001000 00204000 3d20: c10c3d9c c10c3d30 c0046f00 c00d3cbc 00001000 00001000 c02f9860 c008df3c 3d40: 00000000 00001000 c0242d18 c19e4000 03604000 00000000 c10c3f10 00000001 3d60: 00204000 001fc000 c008df3c c02f9860 00000073 c10c3ec8 c10c2000 c19e4000 3d80: 000001fe 00000000 c10c3f10 c1791308 c10c3e2c c10c3da0 c0049028 c0046e10 3da0: 03400000 00000000 c10c3ec8 00400000 00000000 c10c3dd0 c10c3dc4 00400000 3dc0: 03800000 00000000 00000001 c10c3ec8 c10c3e90 c02d8148 03400000 00000000 3de0: c10c3dec 00000001 c00443e8 00000001 c02d60e0 00000008 c02bf6e4 00400000 3e00: 00000000 c10c3e40 c17912ac c19e4000 03400000 c10c3e90 c10c3f10 00000001 3e20: c10c3e84 c10c3e30 c00492a4 c0048cf0 c10c3e3c c0045198 c0044954 00000000 3e40: 91827364 c10c3e44 c10c3e44 c10c3e4c c10c3e4c 00000000 c10c3e64 c10c3e90 3e60: c19e4000 c10c3f10 fffffdee c10c3f78 03400000 00000000 c10c3f44 c10c3e88 3e80: c0079114 c0049234 03400000 00000000 c0008190 40b90a78 00000000 00000001 3ea0: ffffffff c19e4000 00000000 00000000 00000000 00000000 c1aea000 c10c2000 3ec0: 00000000 00000000 03400000 00000000 c10c3f0c c10c3ee0 00400000 c0034478 3ee0: 00400000 c1a03658 00001000 40b95008 00001000 003ff000 c10c2000 c1818780 3f00: c19e4288 00000001 c01197e8 00000000 40796008 00400000 c01474b0 c19e4000 3f20: 00400000 40796008 c10c3f78 c0009124 c10c2000 00000000 c10c3f74 c10c3f48 3f40: c0079c7c c0079064 00000000 00000000 c0009124 c19e4000 03400000 00000000 3f60: 00000004 c0009124 c10c3fa4 c10c3f78 c0079df4 c0079bd0 03400000 00000000 3f80: 00000004 00000000 c10c2000 00400000 40796008 4004f7e0 00000000 c10c3fa8 3fa0: c0008fa0 c0079db8 00400000 40796008 00000001 40796008 00400000 000abfc4 3fc0: 00400000 40796008 4004f7e0 00000004 40796008 40796008 bedb5f34 00000000 3fe0: 00000001 bedb5ba0 0000ef78 40180dcc 60000010 00000001 00000000 00000000 Backtrace: [<c012b3d4>] (ep93xx_dma_tasklet+0x0/0x174) from [<c001c49c>] (tasklet_action+0x c8/0xdc) [<c001c3d4>] (tasklet_action+0x0/0xdc) from [<c001cbc0>] (__do_softirq+0x98/0x15 4) r7:c10c2000 r6:c02d60e0 r5:00000001 r4:00000018 [<c001cb28>] (__do_softirq+0x0/0x154) from [<c001cdd0>] (irq_exit+0x48/0x50) [<c001cd88>] (irq_exit+0x0/0x50) from [<c000983c>] (handle_IRQ+0x3c/0x8c) [<c0009800>] (handle_IRQ+0x0/0x8c) from [<c0008190>] (asm_do_IRQ+0x10/0x14) r7:c10c3c6c r6:fefb0001 r5:80000013 r4:c00e1160 [<c0008180>] (asm_do_IRQ+0x0/0x14) from [<c0008b64>] (__irq_svc+0x24/0xc0) Exception stack(0xc10c3c38 to 0xc10c3c80) 3c20: c1a44058 00000003 3c40: ffffb58e ffffffc7 c156a000 c1a70060 c10c2000 c1a44000 00000000 00000000 3c60: 00000000 c10c3ccc c1a4404c c10c3c80 c0011a28 c00e1160 80000013 ffffffff [<c00e0f78>] (journal_stop+0x0/0x2bc) from [<c00d9eac>] (__ext3_journal_stop+0x2 8/0x58) [<c00d9e84>] (__ext3_journal_stop+0x0/0x58) from [<c00d3d7c>] (ext3_writeback_wr ite_end+0xd0/0x174) r7:03605000 r6:c156a000 r5:c02f9860 r4:c1791250 [<c00d3cac>] (ext3_writeback_write_end+0x0/0x174) from [<c0046f00>] (generic_fil e_buffered_write+0x100/0x25c) [<c0046e00>] (generic_file_buffered_write+0x0/0x25c) from [<c0049028>] (__generi c_file_aio_write+0x348/0x544) [<c0048ce0>] (__generic_file_aio_write+0x0/0x544) from [<c00492a4>] (generic_fil e_aio_write+0x80/0xe8) [<c0049224>] (generic_file_aio_write+0x0/0xe8) from [<c0079114>] (do_sync_write+ 0xc0/0xf8) [<c0079054>] (do_sync_write+0x0/0xf8) from [<c0079c7c>] (vfs_write+0xbc/0x150) [<c0079bc0>] (vfs_write+0x0/0x150) from [<c0079df4>] (sys_write+0x4c/0x84) r8:c0009124 r7:00000004 r6:00000000 r5:03400000 r4:c19e4000 [<c0079da8>] (sys_write+0x0/0x84) from [<c0008fa0>] (ret_fast_syscall+0x0/0x2c) r6:4004f7e0 r5:40796008 r4:00400000 Code: 42555300 54535953 643d4d45 65766972 (53007372) ---[ end trace 8f90267a5628d8bf ]--- Kernel panic - not syncing: Fatal exception in interrupt I don't get this exception when using my patch, posted in first email.
On Mon, Nov 21, 2011 at 02:02:06PM +0530, Vinod Koul wrote: > On Mon, 2011-11-21 at 10:01 +0200, Mika Westerberg wrote: > > On Mon, Nov 21, 2011 at 08:44:07AM +0100, Rafal Prylowski wrote: > > > > > > I'm calling dma_terminate_all from interrupt. It seems that tasklet_kill is not > > > allowed to be called from this context. > > > > Ah, right. > > > > One more try - this time we set a flag which prevents the tasktlet from > > referencing an empty list. > Rather than this why not actually check for list_empty and process only > when it is not empty? I was thinking that it should be an error if the active list is empty when the tasklet is run. > Also you should check the return of the ep93xx_dma_get_active() which > should return NULL if it didn't find anything in active list Right - if the list is allowed to be empty. I'll re-check the patch from Rafal. Maybe it's better to adapt with the fact that dma_terminate_all() can be called in any context any time and modify the driver accordingly (e.g like you say, return NULL if the list is empty handle it correctly).
On 2011-11-22 07:47, Mika Westerberg wrote: > Let me know if this works for you. Basically it's the patch from you except > that we use a flag to indicate if the channel is running or not. > It works correctly. All of my simple hdd tests completed without any problems. Thanks.
On Tue, 2011-11-22 at 07:59 +0200, Mika Westerberg wrote: > On Mon, Nov 21, 2011 at 02:02:06PM +0530, Vinod Koul wrote: > > On Mon, 2011-11-21 at 10:01 +0200, Mika Westerberg wrote: > > > On Mon, Nov 21, 2011 at 08:44:07AM +0100, Rafal Prylowski wrote: > > > > > > > > I'm calling dma_terminate_all from interrupt. It seems that tasklet_kill is not > > > > allowed to be called from this context. > > > > > > Ah, right. > > > > > > One more try - this time we set a flag which prevents the tasktlet from > > > referencing an empty list. > > > Rather than this why not actually check for list_empty and process only > > when it is not empty? > > I was thinking that it should be an error if the active list is empty when the > tasklet is run. well where would you return the error from tasklet? > > > Also you should check the return of the ep93xx_dma_get_active() which > > should return NULL if it didn't find anything in active list > > Right - if the list is allowed to be empty. > > I'll re-check the patch from Rafal. Maybe it's better to adapt with the fact > that dma_terminate_all() can be called in any context any time and modify the > driver accordingly (e.g like you say, return NULL if the list is empty handle > it correctly). Yes dma_terminate_all() is allowed to be called by the driver in any context. It may wish to terminate at any point and this can potentially lead to race condition when you do actual hardware right to terminate just when hardware sent the interrupt. And your tasklet is scheduled after the list becomes empty. So its better approach to check for list in tasklet and return of ep93xx_dma_get_active() for a valid descriptor
Index: linux-2.6/drivers/dma/ep93xx_dma.c =================================================================== --- linux-2.6.orig/drivers/dma/ep93xx_dma.c +++ linux-2.6/drivers/dma/ep93xx_dma.c @@ -459,9 +459,6 @@ static int m2m_hw_setup(struct ep93xx_dm * This IDE part is totally untested. Values below are taken * from the EP93xx Users's Guide and might not be correct. */ - control |= M2M_CONTROL_NO_HDSK; - control |= M2M_CONTROL_RSS_IDE; - control |= M2M_CONTROL_PW_16; if (data->direction == DMA_TO_DEVICE) { /* Worst case from the UG */ @@ -473,6 +470,9 @@ static int m2m_hw_setup(struct ep93xx_dm control |= M2M_CONTROL_SAH; control |= M2M_CONTROL_TM_RX; } + control |= M2M_CONTROL_NO_HDSK; + control |= M2M_CONTROL_RSS_IDE; + control |= M2M_CONTROL_PW_16; break; default: