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 a public inbox, see mirroring instructions
for how to clone and mirror all data and code used for this inbox