USB: usbmon: end ugly tricks with DMA peeking
This patch fixes crashes when usbmon attempts to access GART aperture. The old code attempted to take a bus address and convert it into a virtual address, which clearly was impossible on systems with actual IOMMUs. Let us not persist in this foolishness, and use transfer_buffer in all cases instead. I think downsides are negligible. The ones I see are: - A driver may pass an address of one buffer down as transfer_buffer, and entirely different entity mapped for DMA, resulting in misleading output of usbmon. Note, however, that PIO based controllers would do transfer the same data that usbmon sees here. - Out of tree drivers may crash usbmon if they store garbage in transfer_buffer. I inspected the in-tree drivers, and clarified the documentation in comments. - Drivers that use get_user_pages will not be possible to monitor. I only found one driver with this problem (drivers/staging/rspiusb). - Same happens with with usb_storage transferring from highmem, but it works fine on 64-bit systems, so I think it's not a concern. At least we don't crash anymore. Why didn't we do this in 2.6.10? That's because back in those days it was popular not to fill in transfer_buffer, so almost all traffic would be invisible (e.g. all of HID was like that). But now, the tree is almost 100% PIO friendly, so we can do the right thing at last. Signed-off-by: Pete Zaitcev <zaitcev@redhat.com> Signed-off-by: Greg Kroah-Hartman <gregkh@suse.de>
This commit is contained in:
committed by
Greg Kroah-Hartman
parent
f4e2332cfc
commit
4e9e920035
@@ -64,20 +64,6 @@ void mon_text_exit(void);
|
||||
int __init mon_bin_init(void);
|
||||
void mon_bin_exit(void);
|
||||
|
||||
/*
|
||||
* DMA interface.
|
||||
*
|
||||
* XXX The vectored side needs a serious re-thinking. Abstracting vectors,
|
||||
* like in Paolo's original patch, produces a double pkmap. We need an idea.
|
||||
*/
|
||||
extern char mon_dmapeek(unsigned char *dst, dma_addr_t dma_addr, int len);
|
||||
|
||||
struct mon_reader_bin;
|
||||
extern void mon_dmapeek_vec(const struct mon_reader_bin *rp,
|
||||
unsigned int offset, dma_addr_t dma_addr, unsigned int len);
|
||||
extern unsigned int mon_copy_to_buff(const struct mon_reader_bin *rp,
|
||||
unsigned int offset, const unsigned char *from, unsigned int len);
|
||||
|
||||
/*
|
||||
*/
|
||||
extern struct mutex mon_lock;
|
||||
|
Reference in New Issue
Block a user