rpms/kernel/devel kernel.spec, 1.499, 1.500 linux-2.6-firewire-git-pending.patch, 1.15, 1.16

Jarod Wilson (jwilson) fedora-extras-commits at redhat.com
Wed Mar 12 21:49:13 UTC 2008


Author: jwilson

Update of /cvs/pkgs/rpms/kernel/devel
In directory cvs-int.fedora.redhat.com:/tmp/cvs-serv3578

Modified Files:
	kernel.spec linux-2.6-firewire-git-pending.patch 
Log Message:
* Wed Mar 12 2008 Jarod Wilson <jwilson at redhat.com>
- firewire: fix DMA coherency on x86_64 systems w/memory
  mapped over the 4GB boundary (may fix #434830)
- firewire: sync DMA for device, resolves at least one cause
  of panics in handle_at_packet() (bz.kernel.org #9617)



Index: kernel.spec
===================================================================
RCS file: /cvs/pkgs/rpms/kernel/devel/kernel.spec,v
retrieving revision 1.499
retrieving revision 1.500
diff -u -r1.499 -r1.500
--- kernel.spec	12 Mar 2008 19:18:33 -0000	1.499
+++ kernel.spec	12 Mar 2008 21:48:36 -0000	1.500
@@ -1754,6 +1754,12 @@
 %kernel_variant_files -a /%{image_install_path}/xen*-%{KVERREL} -e /etc/ld.so.conf.d/kernelcap-%{KVERREL}.conf %{with_xen} xen
 
 %changelog
+* Wed Mar 12 2008 Jarod Wilson <jwilson at redhat.com>
+- firewire: fix DMA coherency on x86_64 systems w/memory
+  mapped over the 4GB boundary (may fix #434830)
+- firewire: sync DMA for device, resolves at least one cause
+  of panics in handle_at_packet() (bz.kernel.org #9617)
+
 * Wed Mar 12 2008 Chuck Ebbert <cebbert at redhat.com>
 - Kill annoying ALSA debug messages
 

linux-2.6-firewire-git-pending.patch:

Index: linux-2.6-firewire-git-pending.patch
===================================================================
RCS file: /cvs/pkgs/rpms/kernel/devel/linux-2.6-firewire-git-pending.patch,v
retrieving revision 1.15
retrieving revision 1.16
diff -u -r1.15 -r1.16
--- linux-2.6-firewire-git-pending.patch	10 Mar 2008 14:12:04 -0000	1.15
+++ linux-2.6-firewire-git-pending.patch	12 Mar 2008 21:48:36 -0000	1.16
@@ -789,3 +789,115 @@
 http://arcgraph.de/sr/
 
 
+Currently, we do nothing to guarantee we have a consistent DMA buffer for
+asynchronous receive packets. Rather than doing several sync's following a
+dma_map_single() to get consistent buffers, just switch to using
+dma_alloc_coherent().
+
+Resolves constant buffer failures on my own x86_64 laptop w/4GB of RAM and
+likely to fix a number of other failures witnessed on x86_64 systems with
+4GB of RAM or more.
+
+Signed-off-by: Jarod Wilson <jwilson at redhat.com>
+
+---
+
+ drivers/firewire/fw-ohci.c |   18 +++++-------------
+ 1 files changed, 5 insertions(+), 13 deletions(-)
+
+diff --git a/drivers/firewire/fw-ohci.c b/drivers/firewire/fw-ohci.c
+index 28ea78c..081a434 100644
+--- a/drivers/firewire/fw-ohci.c
++++ b/drivers/firewire/fw-ohci.c
+@@ -284,16 +284,10 @@ static int ar_context_add_page(struct ar_context *ctx)
+ 	dma_addr_t ab_bus;
+ 	size_t offset;
+ 
+-	ab = (struct ar_buffer *) __get_free_page(GFP_ATOMIC);
++	ab = dma_alloc_coherent(dev, PAGE_SIZE, &ab_bus, GFP_ATOMIC);
+ 	if (ab == NULL)
+ 		return -ENOMEM;
+ 
+-	ab_bus = dma_map_single(dev, ab, PAGE_SIZE, DMA_BIDIRECTIONAL);
+-	if (dma_mapping_error(ab_bus)) {
+-		free_page((unsigned long) ab);
+-		return -ENOMEM;
+-	}
+-
+ 	memset(&ab->descriptor, 0, sizeof(ab->descriptor));
+ 	ab->descriptor.control        = cpu_to_le16(DESCRIPTOR_INPUT_MORE |
+ 						    DESCRIPTOR_STATUS |
+@@ -304,8 +298,6 @@ static int ar_context_add_page(struct ar_context *ctx)
+ 	ab->descriptor.res_count      = cpu_to_le16(PAGE_SIZE - offset);
+ 	ab->descriptor.branch_address = 0;
+ 
+-	dma_sync_single_for_device(dev, ab_bus, PAGE_SIZE, DMA_BIDIRECTIONAL);
+-
+ 	ctx->last_buffer->descriptor.branch_address = cpu_to_le32(ab_bus | 1);
+ 	ctx->last_buffer->next = ab;
+ 	ctx->last_buffer = ab;
+@@ -409,6 +401,7 @@ static void ar_context_tasklet(unsigned long data)
+ 
+ 	if (d->res_count == 0) {
+ 		size_t size, rest, offset;
++		dma_addr_t buffer_bus;
+ 
+ 		/*
+ 		 * This descriptor is finished and we may have a
+@@ -417,9 +410,7 @@ static void ar_context_tasklet(unsigned long data)
+ 		 */
+ 
+ 		offset = offsetof(struct ar_buffer, data);
+-		dma_unmap_single(ohci->card.device,
+-			le32_to_cpu(ab->descriptor.data_address) - offset,
+-			PAGE_SIZE, DMA_BIDIRECTIONAL);
++		buffer_bus = le32_to_cpu(ab->descriptor.data_address) - offset;
+ 
+ 		buffer = ab;
+ 		ab = ab->next;
+@@ -435,7 +426,8 @@ static void ar_context_tasklet(unsigned long data)
+ 		while (buffer < end)
+ 			buffer = handle_ar_packet(ctx, buffer);
+ 
+-		free_page((unsigned long)buffer);
++		dma_free_coherent(ohci->card.device, PAGE_SIZE,
++				  buffer, buffer_bus);
+ 		ar_context_add_page(ctx);
+ 	} else {
+ 		buffer = ctx->pointer;
+
+
+
+Per DMA API docs, when using dma_map_single(), DMA_TO_DEVICE synchronization
+must be done after the last modification of the memory region by software
+before it can be handed off to the device and safely read. Such a sync is
+currently missing from firewire_ohci:at_context_queue_packet().
+
+At least on my setup, where I could within seconds reliably reproduce a panic
+in handle_at_packet() by simply dd'ing from two drives on different controllers,
+the panic is gone.
+
+See http://bugzilla.kernel.org/show_bug.cgi?id=9617
+
+Signed-off-by: Jarod Wilson <jwilson at redhat.com>
+
+---
+
+ drivers/firewire/fw-ohci.c |    4 ++++
+ 1 files changed, 4 insertions(+), 0 deletions(-)
+
+diff --git a/drivers/firewire/fw-ohci.c b/drivers/firewire/fw-ohci.c
+index 081a434..fc45868 100644
+--- a/drivers/firewire/fw-ohci.c
++++ b/drivers/firewire/fw-ohci.c
+@@ -780,6 +780,10 @@ at_context_queue_packet(struct context *ctx, struct fw_packet *packet)
+ 
+ 	context_append(ctx, d, z, 4 - z);
+ 
++	/* Sync the DMA buffer up for the device to read from */
++	dma_sync_single_for_device(ohci->card.device, payload_bus,
++				   packet->payload_length, DMA_TO_DEVICE);
++
+ 	/* If the context isn't already running, start it up. */
+ 	reg = reg_read(ctx->ohci, CONTROL_SET(ctx->regs));
+ 	if ((reg & CONTEXT_RUN) == 0)




More information about the fedora-extras-commits mailing list