From: Anton Blanchard <anton@samba.org>
To: Andi Kleen <ak@suse.de>
Cc: davem@redhat.com, linux-arch@vger.kernel.org
Subject: Re: pci_map_single return value
Date: Fri, 19 Mar 2004 11:14:48 +1100 [thread overview]
Message-ID: <20040319001448.GP28212@krispykreme> (raw)
In-Reply-To: <20040102133454.22daa451.ak@suse.de>
> > @@ -210,7 +222,10 @@
> > Returns: the number of physical segments mapped (this may be shorted
> > than <nents> passed in if the block layer determines that some
> > elements of the scatter/gather list are physically adjacent and thus
> > -may be mapped with a single entry).
> > +may be mapped with a single entry).
>
> Another addition here:
>
> Please note that the sg cannot be mapped again if it has been mapped once.
> The mapping process is allowed to destroy information in the sg.
>
> [some drivers do this currently and it causes problems]
>
> > +As with the other mapping interfaces, dma_map_sg can fail. When it
> > +does, 0 is returned and a driver should take appropriate action.
>
> Please make this stronger. A block driver should definitely abort the
> request, otherwise you can kiss your super block good-bye.
Better late than never. Andrew does this look OK to you?
Anton
--
Introduce dma_error() and pci_dma_error() which is used to detect
failures in pci_map_single.
--
===== Documentation/DMA-API.txt 1.5 vs edited =====
--- 1.5/Documentation/DMA-API.txt Thu Feb 5 01:01:19 2004
+++ edited/Documentation/DMA-API.txt Fri Mar 19 11:09:16 2004
@@ -279,6 +279,18 @@
cache width is.
int
+dma_error(dma_addr_t dma_addr)
+
+int
+pci_dma_error(dma_addr_t dma_addr)
+
+In some circumstances dma_map_single and dma_map_page will fail to create
+a mapping. A driver can check for these errors by testing the returned
+dma address with dma_error(). A non zero return value means the mapping
+could not be created and the driver should take appropriate action (eg
+reduce current DMA mapping usage or delay and try again later).
+
+int
dma_map_sg(struct device *dev, struct scatterlist *sg, int nents,
enum dma_data_direction direction)
int
@@ -290,7 +302,16 @@
Returns: the number of physical segments mapped (this may be shorted
than <nents> passed in if the block layer determines that some
elements of the scatter/gather list are physically adjacent and thus
-may be mapped with a single entry).
+may be mapped with a single entry).
+
+Please note that the sg cannot be mapped again if it has been mapped once.
+The mapping process is allowed to destroy information in the sg.
+
+As with the other mapping interfaces, dma_map_sg can fail. When it
+does, 0 is returned and a driver must take appropriate action. It is
+critical that the driver do something, in the case of a block driver
+aborting the request or even oopsing is better than doing nothing and
+corrupting the filesystem.
void
dma_unmap_sg(struct device *dev, struct scatterlist *sg, int nhwentries,
===== Documentation/DMA-mapping.txt 1.18 vs edited =====
--- 1.18/Documentation/DMA-mapping.txt Sun Mar 14 17:54:58 2004
+++ edited/Documentation/DMA-mapping.txt Fri Mar 19 10:55:33 2004
@@ -519,7 +519,7 @@
ends and the second one starts on a page boundary - in fact this is a huge
advantage for cards which either cannot do scatter-gather or have very
limited number of scatter-gather entries) and returns the actual number
-of sg entries it mapped them to.
+of sg entries it mapped them to. On failure 0 is returned.
Then you should loop count times (note: this can be less than nents times)
and use sg_dma_address() and sg_dma_len() macros where you previously
@@ -841,6 +841,27 @@
deleted.
2) More to come...
+
+ Handling Errors
+
+DMA address space is limited on some architectures and an allocation
+failure can be determined by:
+
+- checking if pci_alloc_consistent returns NULL or pci_map_sg returns 0
+
+- checking the returned dma_addr_t of pci_map_single and pci_map_page
+ by using pci_dma_error():
+
+ dma_addr_t dma_handle;
+
+ dma_handle = pci_map_single(dev, addr, size, direction);
+ if (pci_dma_error(dma_handle)) {
+ /*
+ * reduce current DMA mapping usage,
+ * delay and try again later or
+ * reset driver.
+ */
+ }
Closing
===== include/asm-generic/dma-mapping.h 1.5 vs edited =====
--- 1.5/include/asm-generic/dma-mapping.h Sun Mar 14 17:54:58 2004
+++ edited/include/asm-generic/dma-mapping.h Fri Mar 19 10:55:33 2004
@@ -140,6 +140,12 @@
pci_dma_sync_sg_for_device(to_pci_dev(dev), sg, nelems, (int)direction);
}
+static inline int
+dma_error(dma_addr_t dma_addr)
+{
+ return pci_dma_error(dma_addr);
+}
+
/* Now for the API extensions over the pci_ one */
#define dma_alloc_noncoherent(d, s, h, f) dma_alloc_coherent(d, s, h, f)
===== include/asm-generic/pci-dma-compat.h 1.4 vs edited =====
--- 1.4/include/asm-generic/pci-dma-compat.h Sun Mar 14 17:54:58 2004
+++ edited/include/asm-generic/pci-dma-compat.h Fri Mar 19 10:55:33 2004
@@ -98,4 +98,10 @@
dma_sync_sg_for_device(hwdev == NULL ? NULL : &hwdev->dev, sg, nelems, (enum dma_data_direction)direction);
}
+static inline int
+pci_dma_error(dma_addr_t dma_addr)
+{
+ return dma_error(dma_addr);
+}
+
#endif
===== include/asm-i386/dma-mapping.h 1.3 vs edited =====
--- 1.3/include/asm-i386/dma-mapping.h Sun Mar 14 17:54:58 2004
+++ edited/include/asm-i386/dma-mapping.h Fri Mar 19 10:55:33 2004
@@ -109,6 +109,12 @@
{
flush_write_buffers();
}
+
+static inline int
+dma_error(dma_addr_t dma_addr)
+{
+ return 0;
+}
static inline int
dma_supported(struct device *dev, u64 mask)
next parent reply other threads:[~2004-03-19 0:19 UTC|newest]
Thread overview: 10+ messages / expand[flat|nested] mbox.gz Atom feed top
[not found] <20031212155752.GD17683@krispykreme>
[not found] ` <20031212175104.07dc8444.ak@suse.de>
[not found] ` <20031212192131.GF17683@krispykreme>
[not found] ` <20031213220444.4c526afa.davem@redhat.com>
[not found] ` <20040102120121.GT28023@krispykreme>
[not found] ` <20040102133454.22daa451.ak@suse.de>
2004-03-19 0:14 ` Anton Blanchard [this message]
2004-03-19 0:41 ` pci_map_single return value David S. Miller
2004-03-19 0:55 ` Andrew Morton
2004-03-19 1:37 ` Anton Blanchard
2004-03-19 14:16 ` James Bottomley
2004-03-19 16:57 ` James Bottomley
2004-03-19 18:55 ` David S. Miller
2004-03-19 21:01 ` James Bottomley
2004-03-19 21:05 ` Andi Kleen
2004-03-20 0:13 ` James Bottomley
Reply instructions:
You may reply publicly to this message via plain-text email
using any one of the following methods:
* Save the following mbox file, import it into your mail client,
and reply-to-all from there: mbox
Avoid top-posting and favor interleaved quoting:
https://en.wikipedia.org/wiki/Posting_style#Interleaved_style
* Reply using the --to, --cc, and --in-reply-to
switches of git-send-email(1):
git send-email \
--in-reply-to=20040319001448.GP28212@krispykreme \
--to=anton@samba.org \
--cc=ak@suse.de \
--cc=davem@redhat.com \
--cc=linux-arch@vger.kernel.org \
/path/to/YOUR_REPLY
https://kernel.org/pub/software/scm/git/docs/git-send-email.html
* If your mail client supports setting the In-Reply-To header
via mailto: links, try the mailto: link
Be sure your reply has a Subject: header at the top and a blank line
before the message body.
This is an external index of several public inboxes,
see mirroring instructions on how to clone and mirror
all data and code used by this external index.