usb: keep track of packet owner.
Keep track of the device which owns the usb packet for async processing. Signed-off-by: Gerd Hoffmann <kraxel@redhat.com>
This commit is contained in:
		
							parent
							
								
									53aa8c0e2a
								
							
						
					
					
						commit
						4ff658fb6c
					
				
							
								
								
									
										32
									
								
								hw/usb.c
									
									
									
									
									
								
							
							
						
						
									
										32
									
								
								hw/usb.c
									
									
									
									
									
								
							| @ -313,6 +313,38 @@ int usb_handle_packet(USBDevice *dev, USBPacket *p) | ||||
| { | ||||
|     int ret; | ||||
| 
 | ||||
|     assert(p->owner == NULL); | ||||
|     ret = dev->info->handle_packet(dev, p); | ||||
|     if (ret == USB_RET_ASYNC) { | ||||
|         if (p->owner == NULL) { | ||||
|             p->owner = dev; | ||||
|         } else { | ||||
|             /* We'll end up here when usb_handle_packet is called
 | ||||
|              * recursively due to a hub being in the chain.  Nothing | ||||
|              * to do.  Leave p->owner pointing to the device, not the | ||||
|              * hub. */; | ||||
|         } | ||||
|     } | ||||
|     return ret; | ||||
| } | ||||
| 
 | ||||
| /* Notify the controller that an async packet is complete.  This should only
 | ||||
|    be called for packets previously deferred by returning USB_RET_ASYNC from | ||||
|    handle_packet. */ | ||||
| void usb_packet_complete(USBDevice *dev, USBPacket *p) | ||||
| { | ||||
|     /* Note: p->owner != dev is possible in case dev is a hub */ | ||||
|     assert(p->owner != NULL); | ||||
|     dev->port->ops->complete(dev, p); | ||||
|     p->owner = NULL; | ||||
| } | ||||
| 
 | ||||
| /* Cancel an active packet.  The packed must have been deferred by
 | ||||
|    returning USB_RET_ASYNC from handle_packet, and not yet | ||||
|    completed.  */ | ||||
| void usb_cancel_packet(USBPacket * p) | ||||
| { | ||||
|     assert(p->owner != NULL); | ||||
|     p->cancel_cb(p, p->cancel_opaque); | ||||
|     p->owner = NULL; | ||||
| } | ||||
|  | ||||
							
								
								
									
										18
									
								
								hw/usb.h
									
									
									
									
									
								
							
							
						
						
									
										18
									
								
								hw/usb.h
									
									
									
									
									
								
							| @ -262,11 +262,14 @@ struct USBPacket { | ||||
|     uint8_t *data; | ||||
|     int len; | ||||
|     /* Internal use by the USB layer.  */ | ||||
|     USBDevice *owner; | ||||
|     USBCallback *cancel_cb; | ||||
|     void *cancel_opaque; | ||||
| }; | ||||
| 
 | ||||
| int usb_handle_packet(USBDevice *dev, USBPacket *p); | ||||
| void usb_packet_complete(USBDevice *dev, USBPacket *p); | ||||
| void usb_cancel_packet(USBPacket * p); | ||||
| 
 | ||||
| /* Defer completion of a USB packet.  The hadle_packet routine should then
 | ||||
|    return USB_RET_ASYNC.  Packets that complete immediately (before | ||||
| @ -278,21 +281,6 @@ static inline void usb_defer_packet(USBPacket *p, USBCallback *cancel, | ||||
|     p->cancel_opaque = opaque; | ||||
| } | ||||
| 
 | ||||
| /* Notify the controller that an async packet is complete.  This should only
 | ||||
|    be called for packets previously deferred with usb_defer_packet, and | ||||
|    should never be called from within handle_packet.  */ | ||||
| static inline void usb_packet_complete(USBDevice *dev, USBPacket *p) | ||||
| { | ||||
|     dev->port->ops->complete(dev, p); | ||||
| } | ||||
| 
 | ||||
| /* Cancel an active packet.  The packed must have been deferred with
 | ||||
|    usb_defer_packet,  and not yet completed.  */ | ||||
| static inline void usb_cancel_packet(USBPacket * p) | ||||
| { | ||||
|     p->cancel_cb(p, p->cancel_opaque); | ||||
| } | ||||
| 
 | ||||
| void usb_attach(USBPort *port, USBDevice *dev); | ||||
| void usb_wakeup(USBDevice *dev); | ||||
| int usb_generic_handle_packet(USBDevice *s, USBPacket *p); | ||||
|  | ||||
		Loading…
	
	
			
			x
			
			
		
	
		Reference in New Issue
	
	Block a user
	 Gerd Hoffmann
						Gerd Hoffmann