diff --git a/dde_linux/Makefile b/dde_linux/Makefile index 5379eec27..1954c5512 100644 --- a/dde_linux/Makefile +++ b/dde_linux/Makefile @@ -48,7 +48,9 @@ CONTENT_USB_HOST += ohci.h ohci-hcd.c ohci-hub.c ohci-dbg.c ohci-mem.c \ ohci-q.c ohci-pci.c CONTENT_USB_HOST += uhci-hcd.h uhci-hcd.c uhci-debug.c uhci-q.c uhci-hub.c \ uhci-pci.c -CONTENT_USB_HOST += pci-quirks.h pci-quirks.c xhci-ext-caps.h +CONTENT_USB_HOST += xhci-dbg.c xhci-ext-caps.h xhci-hub.c xhci-mem.c \ + xhci-plat.c xhci-ring.c xhci.h xhci.c +CONTENT_USB_HOST += pci-quirks.h pci-quirks.c CONTENT += $(addprefix drivers/usb/host/,$(CONTENT_USB_HOST)) # USB storage driver @@ -78,6 +80,11 @@ CONTENT_NET += asix_devices.c asix_common.c ax88172a.c asix.h CONTENT += $(addprefix drivers/net/usb/,$(CONTENT_NET)) CONTENT += include/linux/usb/usbnet.h include/linux/netdev_features.h +# DWC3 controller +CONTENT_DWC3 = core.c core.h dwc3-exynos.c host.c io.h +CONTENT += $(addprefix drivers/usb/dwc3/,$(CONTENT_DWC3)) +CONTENT += include/linux/platform_data/dwc3-exynos.h + # OMAP CONTENT += include/linux/platform_data/usb-omap.h @@ -117,6 +124,8 @@ $(CONTRIB_DIR)/.prepared: $(DOWNLOAD_DIR)/$(LINUX_TBZ2) $(ECHO) "applying patches to '$(CONTRIB_DIR)/'" $(VERBOSE)for i in $(PATCHES); do patch -d $(CONTRIB_DIR) -p1 < $$i; done $(VERBOSE)ln -sf ../../uapi/linux/usb/ch11.h $(CONTRIB_DIR)/include/linux/usb/ch11.h + $(VERBOSE)touch $(CONTRIB_DIR)/drivers/usb/dwc3/gadget.h + $(VERBOSE)touch $(CONTRIB_DIR)/drivers/usb/dwc3/debug.h $(DOWNLOAD_DIR): diff --git a/dde_linux/lib/mk/platform_arndale/usb.mk b/dde_linux/lib/mk/platform_arndale/usb.mk index 1b292be17..387f451c9 100644 --- a/dde_linux/lib/mk/platform_arndale/usb.mk +++ b/dde_linux/lib/mk/platform_arndale/usb.mk @@ -3,9 +3,17 @@ SRC_C += usbnet.c asix_devices.c asix_common.c ax88172a.c include $(REP_DIR)/lib/mk/usb.inc include $(REP_DIR)/lib/mk/arm/usb.inc -CC_OPT += -DCONFIG_USB_EHCI_S5P -DCONFIG_USB_EHCI_TT_NEWSCHED -DCONFIG_OF +CC_OPT += -DCONFIG_USB_EHCI_S5P -DCONFIG_USB_EHCI_TT_NEWSCHED -DCONFIG_OF -DCONFIG_USB_DWC3_HOST \ + -DCONFIG_USB_OTG_UTILS -DCONFIG_USB_XHCI_PLATFORM INC_DIR += $(CONTRIB_DIR)/arch/arm/plat-samsung/include SRC_CC += platform.cc +#DWC3 +SRC_C += dwc3-exynos.c host.c core.c + +#XHCI +SRC_C += xhci-dbg.c xhci-hub.c xhci-mem.c xhci-plat.c xhci-ring.c xhci.c + vpath platform.cc $(LIB_DIR)/arm/platform_arndale -vpath %.c $(CONTRIB_DIR)/drivers/net/usb +vpath %.c $(CONTRIB_DIR)/drivers/usb/dwc3 +vpath %.c $(CONTRIB_DIR)/drivers/net/usb diff --git a/dde_linux/lib/mk/usb.inc b/dde_linux/lib/mk/usb.inc index cea599ab4..754df0fab 100644 --- a/dde_linux/lib/mk/usb.inc +++ b/dde_linux/lib/mk/usb.inc @@ -10,7 +10,7 @@ CONTRIB_DIR := $(REP_DIR)/contrib DRIVERS_DIR := $(CONTRIB_DIR)/drivers USB_DIR := $(DRIVERS_DIR)/usb -CC_OLEVEL = -O0 +CC_OLEVEL = -O2 # # The order of include-search directories is important, we need to look into diff --git a/dde_linux/patches/dwc3.patch b/dde_linux/patches/dwc3.patch new file mode 100644 index 000000000..7781948db --- /dev/null +++ b/dde_linux/patches/dwc3.patch @@ -0,0 +1,13 @@ +diff -r f6df37e9f744 drivers/usb/dwc3/core.c +--- a/drivers/usb/dwc3/core.c Mon Apr 29 17:06:54 2013 +0200 ++++ b/drivers/usb/dwc3/core.c Mon Apr 29 17:08:04 2013 +0200 +@@ -480,7 +480,8 @@ + goto err0; + } + +- mode = DWC3_MODE(dwc->hwparams.hwparams0); ++ /* force host mode which is needed for Exynos5 */ ++ mode = DWC3_MODE_HOST; + + switch (mode) { + case DWC3_MODE_DEVICE: diff --git a/dde_linux/patches/mem.patch b/dde_linux/patches/mem.patch index 43e586894..58c0616ac 100644 --- a/dde_linux/patches/mem.patch +++ b/dde_linux/patches/mem.patch @@ -1,6 +1,6 @@ -diff -r d22e0f3e9541 drivers/hid/usbhid/hid-core.c ---- a/drivers/hid/usbhid/hid-core.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/hid/usbhid/hid-core.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/hid/usbhid/hid-core.c +--- a/drivers/hid/usbhid/hid-core.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/hid/usbhid/hid-core.c Mon Apr 29 17:30:30 2013 +0200 @@ -895,7 +895,7 @@ &usbhid->inbuf_dma); usbhid->outbuf = usb_alloc_coherent(dev, usbhid->bufsize, GFP_KERNEL, @@ -19,9 +19,9 @@ diff -r d22e0f3e9541 drivers/hid/usbhid/hid-core.c dbg_hid("couldn't allocate rdesc memory\n"); return -ENOMEM; } -diff -r d22e0f3e9541 drivers/net/usb/usbnet.c ---- a/drivers/net/usb/usbnet.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/net/usb/usbnet.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/net/usb/usbnet.c +--- a/drivers/net/usb/usbnet.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/net/usb/usbnet.c Mon Apr 29 17:30:30 2013 +0200 @@ -234,7 +234,7 @@ period = max ((int) dev->status->desc.bInterval, (dev->udev->speed == USB_SPEED_HIGH) ? 7 : 3); @@ -85,9 +85,9 @@ diff -r d22e0f3e9541 drivers/net/usb/usbnet.c if (!req) goto fail_free_buf; -diff -r d22e0f3e9541 drivers/usb/core/config.c ---- a/drivers/usb/core/config.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/core/config.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/core/config.c +--- a/drivers/usb/core/config.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/core/config.c Mon Apr 29 17:30:30 2013 +0200 @@ -689,7 +689,7 @@ if (!dev->rawdescriptors) goto err2; @@ -106,9 +106,9 @@ diff -r d22e0f3e9541 drivers/usb/core/config.c if (!bigbuffer) { result = -ENOMEM; goto err; -diff -r d22e0f3e9541 drivers/usb/core/devices.c ---- a/drivers/usb/core/devices.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/core/devices.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/core/devices.c +--- a/drivers/usb/core/devices.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/core/devices.c Mon Apr 29 17:30:30 2013 +0200 @@ -513,7 +513,7 @@ return 0; /* allocate 2^1 pages = 8K (on i386); @@ -118,9 +118,9 @@ diff -r d22e0f3e9541 drivers/usb/core/devices.c if (!pages_start) return -ENOMEM; -diff -r d22e0f3e9541 drivers/usb/core/hub.c ---- a/drivers/usb/core/hub.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/core/hub.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/core/hub.c +--- a/drivers/usb/core/hub.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/core/hub.c Mon Apr 29 17:30:30 2013 +0200 @@ -1049,7 +1049,7 @@ hcd = bus_to_hcd(hdev->bus); if (hcd->driver->update_hub_device) { @@ -184,9 +184,9 @@ diff -r d22e0f3e9541 drivers/usb/core/hub.c if (buf == NULL) { dev_err(&udev->dev, "no mem to re-read configs after reset\n"); /* assume the worst */ -diff -r d22e0f3e9541 drivers/usb/core/message.c ---- a/drivers/usb/core/message.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/core/message.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/core/message.c +--- a/drivers/usb/core/message.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/core/message.c Mon Apr 29 17:30:30 2013 +0200 @@ -50,7 +50,7 @@ init_completion(&ctx.done); urb->context = &ctx; @@ -246,9 +246,60 @@ diff -r d22e0f3e9541 drivers/usb/core/message.c if (!new_interfaces[n]) { dev_err(&dev->dev, "Out of memory\n"); ret = -ENOMEM; -diff -r d22e0f3e9541 drivers/usb/storage/alauda.c ---- a/drivers/usb/storage/alauda.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/alauda.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/host/xhci-hub.c +--- a/drivers/usb/host/xhci-hub.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/host/xhci-hub.c Mon Apr 29 17:30:30 2013 +0200 +@@ -275,7 +275,7 @@ + + ret = 0; + virt_dev = xhci->devs[slot_id]; +- cmd = xhci_alloc_command(xhci, false, true, GFP_NOIO); ++ cmd = xhci_alloc_command(xhci, false, true, GFP_KERNEL); + if (!cmd) { + xhci_dbg(xhci, "Couldn't allocate command structure.\n"); + return -ENOMEM; +diff -r a1568b909999 drivers/usb/host/xhci.c +--- a/drivers/usb/host/xhci.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/host/xhci.c Mon Apr 29 17:30:30 2013 +0200 +@@ -1706,7 +1706,7 @@ + * process context, not interrupt context (or so documenation + * for usb_set_interface() and usb_set_configuration() claim). + */ +- if (xhci_endpoint_init(xhci, virt_dev, udev, ep, GFP_NOIO) < 0) { ++ if (xhci_endpoint_init(xhci, virt_dev, udev, ep, GFP_KERNEL) < 0) { + dev_dbg(&udev->dev, "%s - could not initialize ep %#x\n", + __func__, ep->desc.bEndpointAddress); + return -ENOMEM; +@@ -3363,10 +3363,10 @@ + /* Allocate the command structure that holds the struct completion. + * Assume we're in process context, since the normal device reset + * process has to wait for the device anyway. Storage devices are +- * reset as part of error handling, so use GFP_NOIO instead of ++ * reset as part of error handling, so use GFP_KERNEL instead of + * GFP_KERNEL. + */ +- reset_device_cmd = xhci_alloc_command(xhci, false, true, GFP_NOIO); ++ reset_device_cmd = xhci_alloc_command(xhci, false, true, GFP_KERNEL); + if (!reset_device_cmd) { + xhci_dbg(xhci, "Couldn't allocate command structure.\n"); + return -ENOMEM; +@@ -3610,11 +3610,11 @@ + } + spin_unlock_irqrestore(&xhci->lock, flags); + } +- /* Use GFP_NOIO, since this function can be called from ++ /* Use GFP_KERNEL, since this function can be called from + * xhci_discover_or_reset_device(), which may be called as part of + * mass storage driver error handling. + */ +- if (!xhci_alloc_virt_device(xhci, xhci->slot_id, udev, GFP_NOIO)) { ++ if (!xhci_alloc_virt_device(xhci, xhci->slot_id, udev, GFP_KERNEL)) { + xhci_warn(xhci, "Could not allocate xHCI USB device data structures\n"); + goto disable_slot; + } +diff -r a1568b909999 drivers/usb/storage/alauda.c +--- a/drivers/usb/storage/alauda.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/alauda.c Mon Apr 29 17:30:30 2013 +0200 @@ -448,8 +448,8 @@ num_zones = MEDIA_INFO(us).capacity >> (MEDIA_INFO(us).zoneshift @@ -307,9 +358,9 @@ diff -r d22e0f3e9541 drivers/usb/storage/alauda.c if (!us->extra) { US_DEBUGP("init_alauda: Gah! Can't allocate storage for" "alauda info struct!\n"); -diff -r d22e0f3e9541 drivers/usb/storage/datafab.c ---- a/drivers/usb/storage/datafab.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/datafab.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/storage/datafab.c +--- a/drivers/usb/storage/datafab.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/datafab.c Mon Apr 29 17:30:30 2013 +0200 @@ -174,7 +174,7 @@ // bounce buffer and the actual transfer buffer. @@ -355,9 +406,9 @@ diff -r d22e0f3e9541 drivers/usb/storage/datafab.c if (!us->extra) { US_DEBUGP("datafab_transport: Gah! " "Can't allocate storage for Datafab info struct!\n"); -diff -r d22e0f3e9541 drivers/usb/storage/jumpshot.c ---- a/drivers/usb/storage/jumpshot.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/jumpshot.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/storage/jumpshot.c +--- a/drivers/usb/storage/jumpshot.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/jumpshot.c Mon Apr 29 17:30:30 2013 +0200 @@ -188,7 +188,7 @@ // bounce buffer and the actual transfer buffer. @@ -394,9 +445,9 @@ diff -r d22e0f3e9541 drivers/usb/storage/jumpshot.c if (!us->extra) { US_DEBUGP("jumpshot_transport: Gah! Can't allocate storage for jumpshot info struct!\n"); return USB_STOR_TRANSPORT_ERROR; -diff -r d22e0f3e9541 drivers/usb/storage/karma.c ---- a/drivers/usb/storage/karma.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/karma.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/storage/karma.c +--- a/drivers/usb/storage/karma.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/karma.c Mon Apr 29 17:30:30 2013 +0200 @@ -182,11 +182,11 @@ static int rio_karma_init(struct us_data *us) { @@ -411,9 +462,9 @@ diff -r d22e0f3e9541 drivers/usb/storage/karma.c if (!data->recv) { kfree(data); goto out; -diff -r d22e0f3e9541 drivers/usb/storage/onetouch.c ---- a/drivers/usb/storage/onetouch.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/onetouch.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/storage/onetouch.c +--- a/drivers/usb/storage/onetouch.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/onetouch.c Mon Apr 29 17:30:30 2013 +0200 @@ -163,7 +163,7 @@ usb_kill_urb(onetouch->irq); break; @@ -423,9 +474,9 @@ diff -r d22e0f3e9541 drivers/usb/storage/onetouch.c dev_err(&onetouch->irq->dev->dev, "usb_submit_urb failed\n"); break; -diff -r d22e0f3e9541 drivers/usb/storage/realtek_cr.c ---- a/drivers/usb/storage/realtek_cr.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/realtek_cr.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/storage/realtek_cr.c +--- a/drivers/usb/storage/realtek_cr.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/realtek_cr.c Mon Apr 29 17:30:30 2013 +0200 @@ -367,7 +367,7 @@ u8 cmnd[12] = { 0 }; u8 *buf; @@ -462,9 +513,9 @@ diff -r d22e0f3e9541 drivers/usb/storage/realtek_cr.c if (!buf) return USB_STOR_TRANSPORT_ERROR; -diff -r d22e0f3e9541 drivers/usb/storage/sddr09.c ---- a/drivers/usb/storage/sddr09.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/sddr09.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/storage/sddr09.c +--- a/drivers/usb/storage/sddr09.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/sddr09.c Mon Apr 29 17:30:30 2013 +0200 @@ -692,7 +692,7 @@ return result; } @@ -530,9 +581,9 @@ diff -r d22e0f3e9541 drivers/usb/storage/sddr09.c if (!us->extra) return -ENOMEM; us->extra_destructor = sddr09_card_info_destructor; -diff -r d22e0f3e9541 drivers/usb/storage/sddr55.c ---- a/drivers/usb/storage/sddr55.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/sddr55.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/storage/sddr55.c +--- a/drivers/usb/storage/sddr55.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/sddr55.c Mon Apr 29 17:30:30 2013 +0200 @@ -216,7 +216,7 @@ len = min((unsigned int) sectors, (unsigned int) info->blocksize >> @@ -580,9 +631,9 @@ diff -r d22e0f3e9541 drivers/usb/storage/sddr55.c if (!us->extra) return USB_STOR_TRANSPORT_ERROR; us->extra_destructor = sddr55_card_info_destructor; -diff -r d22e0f3e9541 drivers/usb/storage/shuttle_usbat.c ---- a/drivers/usb/storage/shuttle_usbat.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/shuttle_usbat.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/storage/shuttle_usbat.c +--- a/drivers/usb/storage/shuttle_usbat.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/shuttle_usbat.c Mon Apr 29 17:30:30 2013 +0200 @@ -1068,7 +1068,7 @@ if (!us || !info) return USB_STOR_TRANSPORT_ERROR; @@ -628,9 +679,9 @@ diff -r d22e0f3e9541 drivers/usb/storage/shuttle_usbat.c if (!us->extra) { US_DEBUGP("init_usbat: Gah! Can't allocate storage for usbat info struct!\n"); return 1; -diff -r d22e0f3e9541 drivers/usb/storage/transport.c ---- a/drivers/usb/storage/transport.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/transport.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/storage/transport.c +--- a/drivers/usb/storage/transport.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/transport.c Mon Apr 29 17:30:30 2013 +0200 @@ -151,7 +151,7 @@ us->current_urb->transfer_dma = us->iobuf_dma; @@ -649,9 +700,9 @@ diff -r d22e0f3e9541 drivers/usb/storage/transport.c if (result) { US_DEBUGP("usb_sg_init returned %d\n", result); return USB_STOR_XFER_ERROR; -diff -r d22e0f3e9541 drivers/usb/storage/usb.c ---- a/drivers/usb/storage/usb.c Mon Apr 22 16:20:42 2013 +0200 -+++ b/drivers/usb/storage/usb.c Mon Apr 22 16:22:55 2013 +0200 +diff -r a1568b909999 drivers/usb/storage/usb.c +--- a/drivers/usb/storage/usb.c Mon Apr 29 17:08:12 2013 +0200 ++++ b/drivers/usb/storage/usb.c Mon Apr 29 17:30:30 2013 +0200 @@ -453,7 +453,7 @@ usb_set_intfdata(intf, us); diff --git a/dde_linux/src/lib/usb/arm/platform_arndale/platform.cc b/dde_linux/src/lib/usb/arm/platform_arndale/platform.cc index f126b6213..e4f6cb0f3 100644 --- a/dde_linux/src/lib/usb/arm/platform_arndale/platform.cc +++ b/dde_linux/src/lib/usb/arm/platform_arndale/platform.cc @@ -12,7 +12,9 @@ */ /* Genode */ +#include #include +#include #include /* Emulation */ @@ -21,13 +23,18 @@ /* Linux */ #include +#include using namespace Genode; enum { - EHCI_BASE = 0x12110000, - GPIO_BASE = 0x11400000, - EHCI_IRQ = 103, + EHCI_BASE = 0x12110000, + DWC3_BASE = 0x12000000, + DWC3_PHY_BASE = 0x12100000, + GPIO_BASE = 0x11400000, + EHCI_IRQ = 103, + DWC3_IRQ = 104, + PM_BASE = 0x10040000, }; static resource _ehci[] = @@ -36,7 +43,14 @@ static resource _ehci[] = { EHCI_IRQ, EHCI_IRQ, "ehci-irq", IORESOURCE_IRQ }, }; +static resource _dwc3[] = +{ + { DWC3_BASE, DWC3_BASE + 0xcfff, "dwc3", IORESOURCE_MEM }, + { DWC3_IRQ, DWC3_IRQ, "dwc3-irq", IORESOURCE_IRQ }, +}; + static struct s5p_ehci_platdata _ehci_data; +static struct dwc3_exynos_data _dwc3_data; /** @@ -136,16 +150,16 @@ static void arndale_ehci_init() extern "C" void module_ehci_hcd_init(); -extern "C" int module_usbnet_init(); -extern "C" int module_asix_driver_init(); +extern "C" void module_usbnet_init(); +extern "C" void module_asix_driver_init(); +extern "C" void module_dwc3_exynos_driver_init(); +extern "C" void module_dwc3_driver_init(); +extern "C" void module_xhci_hcd_init(); -void platform_hcd_init(Services *services) +void ehci_setup(Services *services) { - /* register network */ - if (services->nic) { - module_usbnet_init(); + if (services->nic) module_asix_driver_init(); - } /* register EHCI controller */ module_ehci_hcd_init(); @@ -155,7 +169,7 @@ void platform_hcd_init(Services *services) /* setup EHCI-controller platform device */ platform_device *pdev = (platform_device *)kzalloc(sizeof(platform_device), 0); - pdev->name = "s5p-ehci"; + pdev->name = (char *)"s5p-ehci"; pdev->id = 0; pdev->num_resources = 2; pdev->resource = _ehci; @@ -168,3 +182,170 @@ void platform_hcd_init(Services *services) platform_device_register(pdev); } + +struct Power : Genode::Mmio +{ + struct Usbdrd_phy_control : Register<0x704, 32> { }; + struct Usbhost_phy_control : Register<0x708, 32> { }; + + Power(addr_t const base) : Mmio(base) + { + write(1); + write(1); + } +}; + +struct Phy_usb3 : Genode::Mmio +{ + struct Link_system : Register<0x4, 32> + { + struct Fladj : Bitfield<1, 6> { }; + struct Ehci_version_control : Bitfield<27, 1> { }; + }; + + struct Phy_utmi : Register<0x8, 32> { }; + + struct Phy_clk_rst : Register<0x10, 32> + { + struct Common_onn : Bitfield<0, 1> { }; + struct Port_reset : Bitfield<1, 1> { }; + struct Ref_clk_sel : Bitfield<2, 2> { }; + struct Retenablen : Bitfield<4, 1> { }; + struct Fsel : Bitfield<5, 6> { }; + struct Mpll_mult : Bitfield<11, 7> { }; + struct Ref_ssp_en : Bitfield<19, 1> { }; + struct Ssc_en : Bitfield<20, 1> { }; + struct Ssc_ref_clk_sel : Bitfield<23, 8> { }; + }; + + struct Phy_reg0 : Register<0x14, 32> { }; + + struct Phy_param0 : Register<0x1c, 32> + { + struct Loss_level : Bitfield<26, 5> { }; + struct Ref_use_pad : Bitfield<31, 1> { }; + }; + + struct Phy_param1 : Register<0x20, 32> + { + struct Pcs_txdeemph : Bitfield<0, 5> { }; + }; + + struct Phy_test : Register<0x28, 32> + { + struct Power_down_ssb_hsb : Bitfield<2, 2> { }; + }; + + struct Phy_batchg : Register<0x30, 32> + { + struct Utmi_clksel : Bitfield<2, 1> { }; + }; + + struct Phy_resume : Register<0x34, 32> { }; + + Phy_usb3 (addr_t const base) : Mmio(base) + { + Timer::Connection timer; + + /* reset */ + write(0); + + /* clock source */ + write(0); + + /* set Loss-of-Signal Detector sensitivity */ + write(0x9); + write(0); + + /* + * Setting the Frame length Adj value[6:1] to default 0x20 + * See xHCI 1.0 spec, 5.2.4 + */ + write(1); + write(0x20); + + /* set Tx De-Emphasis level */ + write(0x1c); + + /* set clock */ + write(1); + + /* PHYTEST POWERDOWN Control */ + write(0); + + /* UTMI power */ + enum { OTG_DISABLE = (1 << 6) }; + write(OTG_DISABLE); + + /* setup clock */ + Phy_clk_rst::access_t clk = 0; + + /* set external clock */ + Phy_clk_rst::Ref_clk_sel::set(clk, 3); + /* 24 MHz */ + Phy_clk_rst::Fsel::set(clk, 0x5); + Phy_clk_rst::Mpll_mult::set(clk, 0x68); + Phy_clk_rst::Ssc_ref_clk_sel::set(clk, 0x88); + + /* port reset */ + Phy_clk_rst::Port_reset::set(clk, 1); + + /* digital power supply in normal operating mode */ + Phy_clk_rst::Retenablen::set(clk, 1); + /* enable ref clock for SS function */ + Phy_clk_rst::Ref_ssp_en::set(clk, 1); + /* enable spread spectrum */ + Phy_clk_rst::Ssc_en::set(clk, 1); + /* power down HS Bias and PLL blocks in suspend mode */ + Phy_clk_rst::Common_onn::set(clk, 1); + + write(clk); + timer.usleep(10); + write(0); + } +}; + +static void arndale_xhci_init() +{ + /* enable power of USB3 */ + Attached_io_mem_dataspace io_pm(PM_BASE, 0x1000); + Power power((addr_t)io_pm.local_addr()); + + /* setup PHY */ + Attached_io_mem_dataspace io_phy(DWC3_PHY_BASE, 0x1000); + Phy_usb3 phy((addr_t)io_phy.local_addr()); +} + +void xhci_setup() +{ + arndale_xhci_init(); + + module_dwc3_exynos_driver_init(); + module_dwc3_driver_init(); + module_xhci_hcd_init(); + + /* setup DWC3-controller platform device */ + platform_device *pdev = (platform_device *)kzalloc(sizeof(platform_device), 0); + pdev->name = (char *)"exynos-dwc3"; + pdev->id = 0; + pdev->num_resources = 2; + pdev->resource = _dwc3; + pdev->dev.platform_data = &_dwc3_data; + + /*needed for DMA buffer allocation. See 'hcd_buffer_alloc' in 'buffer.c' */ + static u64 dma_mask = ~(u64)0; + pdev->dev.dma_mask = &dma_mask; + pdev->dev.coherent_dma_mask = ~0; + + platform_device_register(pdev); +} + +void platform_hcd_init(Services *services) +{ + /* register network */ + if (services->nic) + module_usbnet_init(); + + ehci_setup(services); + xhci_setup(); +} diff --git a/dde_linux/src/lib/usb/arm/platform_device.c b/dde_linux/src/lib/usb/arm/platform_device.c index ef3a90151..c28790447 100644 --- a/dde_linux/src/lib/usb/arm/platform_device.c +++ b/dde_linux/src/lib/usb/arm/platform_device.c @@ -50,6 +50,7 @@ int platform_driver_register(struct platform_driver *drv) return driver_register(&drv->driver); } + struct resource *platform_get_resource(struct platform_device *dev, unsigned int type, unsigned int num) { @@ -65,6 +66,7 @@ struct resource *platform_get_resource(struct platform_device *dev, return NULL; } + struct resource *platform_get_resource_byname(struct platform_device *dev, unsigned int type, const char *name) @@ -95,12 +97,75 @@ int platform_get_irq(struct platform_device *dev, unsigned int num) return r ? r->start : -1; } + int platform_device_register(struct platform_device *pdev) { pdev->dev.bus = &platform_bus_type; pdev->dev.name = pdev->name; /* XXX: Fill with magic value to see page fault */ - pdev->dev.parent = (struct device *)0xaaaaaaaa; + if (!pdev->dev.parent) + pdev->dev.parent = (struct device *)0xaaaaaaaa; device_add(&pdev->dev); return 0; } + + +struct platform_device *platform_device_alloc(const char *name, int id) +{ + struct platform_device *pdev = kzalloc(sizeof(struct platform_device), GFP_KERNEL); + + if (!pdev) + return 0; + + int len = strlen(name); + pdev->name = kzalloc(len + 1, GFP_KERNEL); + + if (!pdev->name) { + kfree(pdev); + return 0; + } + + memcpy(pdev->name, name, len); + pdev->name[len] = 0; + pdev->id = id; + + return pdev; +} + + +int platform_device_add_data(struct platform_device *pdev, const void *data, + size_t size) +{ + void *d = NULL; + + if (data && !(d = kmemdup(data, size, GFP_KERNEL))) + return -ENOMEM; + + kfree(pdev->dev.platform_data); + pdev->dev.platform_data = d; + + return 0; +} + + +int platform_device_add(struct platform_device *pdev) +{ + return platform_device_register(pdev); +} + +int platform_device_add_resources(struct platform_device *pdev, + const struct resource *res, unsigned int num) +{ + struct resource *r = NULL; + + if (res) { + r = kmemdup(res, sizeof(struct resource) * num, GFP_KERNEL); + if (!r) + return -ENOMEM; + } + + kfree(pdev->resource); + pdev->resource = r; + pdev->num_resources = num; + return 0; +} diff --git a/dde_linux/src/lib/usb/dummies.c b/dde_linux/src/lib/usb/dummies.c index 1fe4d4527..bfdb19ee6 100644 --- a/dde_linux/src/lib/usb/dummies.c +++ b/dde_linux/src/lib/usb/dummies.c @@ -77,6 +77,9 @@ int roundup_pow_of_two(u32 n) { TRACE; return 0; } void print_hex_dump(const char *level, const char *prefix_str, int prefix_type, int rowsize, int groupsize, const void *buf, size_t len, bool ascii) { TRACE; } +int printk_ratelimit() { TRACE; return 0; } +bool printk_timed_ratelimit(unsigned long *caller_jiffies, + unsigned int interval_msec) { TRACE; return false; } /********************************** @@ -190,7 +193,8 @@ s64 ktime_us_delta(const ktime_t later, const ktime_t earlier) { TRACE; return 0 int del_timer_sync(struct timer_list *timer) { TRACE; return 0; } unsigned long round_jiffies(unsigned long j) { TRACE; return 1; } - +void add_timer(struct timer_list *timer) { TRACE; } +void set_timer_slack(struct timer_list *time, int slack_hz) { TRACE; } /********************* ** linux/hrtimer.h ** @@ -203,13 +207,6 @@ void hrtimer_init(struct hrtimer *timer, clockid_t clock_id, enum hrtimer_mode m int hrtimer_cancel(struct hrtimer *timer) { TRACE; return 0; } -/******************* - ** linux/delay.h ** - *******************/ - -void mdelay(unsigned long msecs) { TRACE; } - - /*********************** ** linux/workquque.h ** ***********************/ @@ -320,6 +317,8 @@ int pm_runtime_set_active(struct device *dev) { TRACE; return 0; } void pm_suspend_ignore_children(struct device *dev, bool enable) { TRACE; } void pm_runtime_enable(struct device *dev) { TRACE; } void pm_runtime_disable(struct device *dev) { TRACE; } +void pm_runtime_allow(struct device *dev) { TRACE; } +void pm_runtime_forbid(struct device *dev) { TRACE; } void pm_runtime_set_suspended(struct device *dev) { TRACE; } void pm_runtime_get_noresume(struct device *dev) { TRACE; } void pm_runtime_put_noidle(struct device *dev) { TRACE; } @@ -424,8 +423,10 @@ void devres_free(void *res) { TRACE; } *****************************/ void *platform_get_drvdata(const struct platform_device *pdev) { TRACE; return NULL; } -void platform_set_drvdata(struct platform_device *pdev, void *data) { TRACE; } - +void platform_set_drvdata(struct platform_device *pdev, void *data) { TRACE; printk("ret: %p\n", __builtin_return_address(0)); } +int platform_device_del(struct platform_device *pdev) { TRACE; return 0; } +int platform_device_put(struct platform_device *pdev) { TRACE; return 0; } +void platform_device_unregister(struct platform_device *pdev) { TRACE; } /******************** ** linux/dcache.h ** @@ -606,6 +607,7 @@ void free_irq(unsigned int i, void *p) { TRACE; } *********************/ void synchronize_irq(unsigned int irq) { TRACE; } +bool in_interrupt(void) { TRACE; return 1; } /***************** @@ -1012,6 +1014,14 @@ u16 crc16(u16 crc, const u8 *buffer, size_t len) { TRACE; return 0; } u16 bitrev16(u16 in) { TRACE; return 0; } +/************************ + ** linux/radix-tree.h ** + ************************/ + +void *radix_tree_lookup(struct radix_tree_root *root, unsigned long index) { TRACE; return 0; } +int radix_tree_insert(struct radix_tree_root *root, unsigned long index, void *item) { TRACE; return 0; } +void *radix_tree_delete(struct radix_tree_root *root, unsigned long index) { TRACE; return 0; } + /****************** ** linux/gpio.h ** ******************/ @@ -1033,6 +1043,8 @@ int gpio_request_one(unsigned gpio, unsigned long flags, const char *label) { TR ** linux/phy.h ** ******************/ +#include + struct mii_bus *mdiobus_alloc(void) { TRACE; return 0; } int mdiobus_register(struct mii_bus *bus) { TRACE; return 0; } void mdiobus_unregister(struct mii_bus *bus) { TRACE; } @@ -1052,5 +1064,35 @@ struct phy_device * phy_connect(struct net_device *dev, const char *bus_id, phy_interface_t interface) { TRACE; return 0; } void phy_disconnect(struct phy_device *phydev) { TRACE; } +#ifdef CONFIG_USB_OTG_UTILS +struct usb_phy *devm_usb_get_phy_by_phandle(struct device *dev, + const char *phandle, u8 index) +{ TRACE; return 0; } +struct usb_phy *devm_usb_get_phy(struct device *dev, + enum usb_phy_type type) +{ + static struct usb_phy _p; + TRACE; + return &_p; +} +#endif + +/**************** + ** linux/of.h ** + ****************/ + +bool of_property_read_bool(const struct device_node *np, const char *propname) { TRACE; return false; } + + + +/****************************** + ** drivers/usb/dwc3/debug.h ** + ******************************/ + +struct dwc3; + +int dwc3_debugfs_init(struct dwc3 *d){ SKIP; return 0; } +void dwc3_debugfs_exit(struct dwc3 *d) { SKIP; } + diff --git a/dde_linux/src/lib/usb/include/arm/platform/lx_emul.h b/dde_linux/src/lib/usb/include/arm/platform/lx_emul.h index 72a126bcd..36853c7b9 100644 --- a/dde_linux/src/lib/usb/include/arm/platform/lx_emul.h +++ b/dde_linux/src/lib/usb/include/arm/platform/lx_emul.h @@ -24,7 +24,7 @@ enum { struct platform_device { - const char *name; + char *name; int id; struct device dev; u32 num_resources; @@ -53,6 +53,12 @@ enum { ** linux/platform_device.h ** *****************************/ +#define module_platform_driver(__platform_driver) \ + module_driver(__platform_driver, platform_driver_register, \ + platform_driver_unregister) + +enum { PLATFORM_DEVID_AUTO = -2 }; + struct platform_driver { int (*probe)(struct platform_device *); int (*remove)(struct platform_device *); @@ -71,6 +77,18 @@ int platform_get_irq_byname(struct platform_device *, const char *); int platform_driver_register(struct platform_driver *); int platform_device_register(struct platform_device *); +void platform_device_unregister(struct platform_device *); + +struct platform_device *platform_device_alloc(const char *name, int id); +int platform_device_add_data(struct platform_device *pdev, const void *data, + size_t size); +int platform_device_add_resources(struct platform_device *pdev, + const struct resource *res, unsigned int num); + +int platform_device_add(struct platform_device *pdev); +int platform_device_del(struct platform_device *pdev); + +int platform_device_put(struct platform_device *pdev); #define to_platform_device(x) container_of((x), struct platform_device, dev) @@ -206,6 +224,13 @@ struct phy_device * phy_connect(struct net_device *dev, const char *bus_id, void phy_disconnect(struct phy_device *phydev); +/******************************* + ** linux/usb/nop-usb-xceiv.h ** + *******************************/ + +struct nop_usb_xceiv_platform_data { int type; }; + + /******************************* ** linux/usb/samsung_usb_phy ** *******************************/ diff --git a/dde_linux/src/lib/usb/include/lx_emul.h b/dde_linux/src/lib/usb/include/lx_emul.h index c76a50af5..821f30aa0 100644 --- a/dde_linux/src/lib/usb/include/lx_emul.h +++ b/dde_linux/src/lib/usb/include/lx_emul.h @@ -326,11 +326,13 @@ __u64 __swab64p(const __u64 *); #define cpu_to_le32 __cpu_to_le32 #define cpu_to_be32 __cpu_to_be32 #define cpu_to_le32s __cpu_to_le32s +#define cpu_to_le64 __cpu_to_le64 #define le16_to_cpup __le16_to_cpup #define be16_to_cpup __be16_to_cpup #define le32_to_cpup __le32_to_cpup #define le32_to_cpus __le32_to_cpus #define be32_to_cpup __be32_to_cpup +#define le64_to_cpu __le64_to_cpu struct __una_u16 { u16 x; } __attribute__((packed)); @@ -338,6 +340,7 @@ struct __una_u32 { u32 x; } __attribute__((packed)); struct __una_u64 { u64 x; } __attribute__((packed)); u16 get_unaligned_le16(const void *p); +void put_unaligned_le16(u16 val, void *p); void put_unaligned_le32(u32 val, void *p); u32 get_unaligned_le32(const void *p); @@ -551,6 +554,23 @@ static inline size_t min(size_t a, size_t b) { typeof (x) _x = (x); \ _x < 0 ? -_x : _x; }) +#define lower_32_bits(n) ((u32)(n)) +#define upper_32_bits(n) ((u32)(((n) >> 16) >> 16)) + +#define roundup(x, y) ( \ +{ \ + const typeof(y) __y = y; \ + (((x) + (__y - 1)) / __y) * __y; \ +}) + +#define clamp_val(val, min, max) ({ \ + typeof(val) __val = (val); \ + typeof(val) __min = (min); \ + typeof(val) __max = (max); \ + __val = __val < __min ? __min: __val; \ + __val > __max ? __max: __val; }) + + #define ARRAY_SIZE(arr) (sizeof(arr) / sizeof((arr)[0])) #define BUILD_BUG_ON(condition) @@ -582,6 +602,13 @@ int kstrtouint(const char *s, unsigned int base, unsigned int *res); (((__x) - ((__d) / 2)) / (__d)); \ }) +#define PTR_ALIGN(p, a) ({ \ + unsigned long _p = (unsigned long)p; \ + _p = (_p + a - 1) & ~(a - 1); \ + p = (typeof(p))_p; \ + p; \ +}) + int strict_strtoul(const char *s, unsigned int base, unsigned long *res); long simple_strtoul(const char *cp, char **endp, unsigned int base); @@ -631,12 +658,8 @@ void print_hex_dump(const char *level, const char *prefix_str, #define pr_warning(fmt, ...) printk(KERN_WARNING fmt, ##__VA_ARGS__) #define pr_warn pr_warning -#define printk_ratelimit() \ - ({ dde_kit_debug("printk_ratelimit called - not implemented\n"); (0); }) - -static inline bool printk_timed_ratelimit(unsigned long *caller_jiffies, - unsigned int interval_msec) { - return false; } +bool printk_ratelimit(); +bool printk_timed_ratelimit(unsigned long *, unsigned int); /********************************** @@ -677,6 +700,14 @@ int fls(int x); #define for_each_set_bit(bit, addr, size) for ((bit) = 0; !bit; bit++, dev_err(0, "for_each_set_bit should not be called\n")) +/***************************************** + ** asm-generic//bitops/const_hweight.h ** + *****************************************/ + +/* count number of 1s in 'w' */ +#define hweight32(w) __builtin_popcount((unsigned)w) + + /******************** ** linux/string.h ** ********************/ @@ -929,6 +960,7 @@ struct timer_list { void (*function)(unsigned long); unsigned long data; void *timer; + unsigned long expires; }; void init_timer(struct timer_list *); @@ -940,6 +972,9 @@ void setup_timer(struct timer_list *timer,void (*function)(unsigned long), int timer_pending(const struct timer_list * timer); unsigned long round_jiffies(unsigned long j); +void add_timer(struct timer_list *timer); +void set_timer_slack(struct timer_list *time, int slack_hz); + /********************* ** linux/hrtimer.h ** @@ -1355,6 +1390,8 @@ int pm_runtime_set_active(struct device *dev); void pm_suspend_ignore_children(struct device *dev, bool enable); void pm_runtime_enable(struct device *dev); void pm_runtime_disable(struct device *dev); +void pm_runtime_allow(struct device *dev); +void pm_runtime_forbid(struct device *dev); void pm_runtime_set_suspended(struct device *dev); void pm_runtime_get_noresume(struct device *dev); void pm_runtime_put_noidle(struct device *dev); @@ -1410,6 +1447,9 @@ bool device_can_wakeup(struct device *dev); #define dev_printk(level, dev, format, arg...) \ dde_kit_printf("dev_printk: " format, ## arg) +#define dev_warn_ratelimited(dev, format, arg...) \ + dde_kit_printf("dev_warn_ratelimited: " format "\n", ## arg) + enum { BUS_NOTIFY_ADD_DEVICE = 0x00000001, BUS_NOTIFY_DEL_DEVICE = 0x00000002, @@ -1455,6 +1495,8 @@ struct class char *(*devnode)(struct device *dev, mode_t *mode); }; +struct dma_parms; + /* DEVICE */ struct device { const char *name; @@ -1473,6 +1515,7 @@ struct device { struct class *class; void *driver_data; struct device_node *of_node; + struct device_dma_parameters *dma_parms; }; struct device_attribute { @@ -1622,6 +1665,8 @@ void dma_free_coherent(struct device *, size_t, void *, dma_addr_t); *************************/ #define DMA_BIT_MASK(n) (((n) == 64) ? ~0ULL : ((1ULL<<(n))-1)) +static inline int dma_set_coherent_mask(struct device *dev, u64 mask) { dev->coherent_dma_mask = mask; return 0; } +int dma_set_mask(struct device *dev, u64 mask); /********************* ** linux/uaccess.h ** @@ -1985,13 +2030,16 @@ void *ioremap(resource_size_t offset, unsigned long size); void iounmap(volatile void *addr); void *devm_ioremap(struct device *dev, resource_size_t offset, unsigned long size); +void *devm_ioremap_nocache(struct device *dev, resource_size_t offset, + unsigned long size); + /** * Map I/O memory write combined */ void *ioremap_wc(resource_size_t phys_addr, unsigned long size); -#define ioremap_nocache ioremap_wc +#define ioremap_nocache ioremap #define writel(value, addr) (*(volatile uint32_t *)(addr) = (value)) #define readl(addr) (*(volatile uint32_t *)(addr)) @@ -2036,6 +2084,9 @@ struct resource *request_region(resource_size_t start, resource_size_t n, const char *name); struct resource *request_mem_region(resource_size_t start, resource_size_t n, const char *name); +struct resource * devm_request_mem_region(struct device *dev, resource_size_t start, + resource_size_t n, const char *name); + void release_region(resource_size_t start, resource_size_t n); void release_mem_region(resource_size_t start, resource_size_t n); @@ -2064,6 +2115,7 @@ void free_irq(unsigned int, void *); *********************/ void synchronize_irq(unsigned int irq); +bool in_interrupt(void); /***************** @@ -3388,6 +3440,32 @@ typedef enum { } phy_interface_t; +/************************ + ** linux/usb/gadget.h ** + ************************/ + +struct usb_ep { }; +struct usb_request { }; +struct usb_gadget { }; + + +/**************** + ** linux/of.h ** + ****************/ + +bool of_property_read_bool(const struct device_node *np, const char *propname); + + +/************************ + ** linux/radix-tree.h ** + ************************/ + +#define INIT_RADIX_TREE(root, mask) dde_kit_printf("INIT_RADIX_TREE not impelemnted\n") +struct radix_tree_root { }; +void *radix_tree_lookup(struct radix_tree_root *root, unsigned long index); +int radix_tree_insert(struct radix_tree_root *, unsigned long, void *); +void *radix_tree_delete(struct radix_tree_root *, unsigned long); + /********************************** ** Platform specific defintions ** **********************************/ diff --git a/dde_linux/src/lib/usb/lx_emul.cc b/dde_linux/src/lib/usb/lx_emul.cc index b64a04555..795419267 100644 --- a/dde_linux/src/lib/usb/lx_emul.cc +++ b/dde_linux/src/lib/usb/lx_emul.cc @@ -57,7 +57,7 @@ class Genode::Slab_backend_alloc : public Genode::Allocator, enum { VM_SIZE = 10 * 1024 * 1024, /* size of VM region to reserve */ - BLOCK_SIZE = 768 * 1024, /* 1 MB */ + BLOCK_SIZE = 1024 * 1024, /* 1 MB */ ELEMENTS = VM_SIZE / BLOCK_SIZE, /* MAX number of dataspaces in VM */ }; @@ -156,8 +156,6 @@ class Genode::Slab_backend_alloc : public Genode::Allocator, class Genode::Slab_alloc : public Genode::Slab { private: - - Slab_backend_alloc *_allocator; size_t _calculate_block_size(size_t object_size) { @@ -168,16 +166,14 @@ class Genode::Slab_alloc : public Genode::Slab public: Slab_alloc(size_t object_size, Slab_backend_alloc *allocator) - : Slab(object_size, _calculate_block_size(object_size), 0, allocator), - _allocator(allocator) { } + : Slab(object_size, _calculate_block_size(object_size), 0, allocator) + { } inline addr_t alloc() { addr_t result; return (Slab::alloc(slab_size(), (void **)&result) ? result : 0); } - - addr_t phys_addr(addr_t addr) { return _allocator->phys_addr(addr); } }; @@ -198,6 +194,7 @@ class Malloc typedef Genode::Slab_alloc Slab_alloc; typedef Genode::Slab_backend_alloc Slab_backend_alloc; + Slab_backend_alloc *_back_allocator; Slab_alloc *_allocator[NUM_SLABS]; bool _cached; /* cached or un-cached memory */ addr_t _start; /* VM region of this allocator */ @@ -232,7 +229,8 @@ class Malloc public: Malloc(Slab_backend_alloc *alloc, bool cached) - : _cached(cached), _start(alloc->start()), _end(alloc->end()) + : _back_allocator(alloc), _cached(cached), _start(alloc->start()), + _end(alloc->end()) { /* init slab allocators */ for (unsigned i = SLAB_START_LOG2; i <= SLAB_STOP_LOG2; i++) @@ -275,7 +273,7 @@ class Malloc /* save */ addr_t ptr = addr; addr_t align_val = (1U << align); - addr_t align_mask = align_val - 2; + addr_t align_mask = align_val - 1; /* align */ addr = (addr + align_val) & ~align_mask; /* write start address before aligned address */ @@ -283,7 +281,7 @@ class Malloc } if (phys) - *phys = _allocator[msb - SLAB_START_LOG2]->phys_addr(addr); + *phys = _back_allocator->phys_addr(addr); return (addr_t *)addr; } @@ -298,9 +296,7 @@ class Malloc Genode::addr_t phys_addr(void *a) { - using namespace Genode; - addr_t *addr = (addr_t *)a; - return _allocator[_slab_index(&addr)]->phys_addr((addr_t)a); + return _back_allocator->phys_addr((addr_t)a); } /** @@ -648,7 +644,6 @@ void *_ioremap(resource_size_t phys_addr, unsigned long size, int wc) PERR("Failed to request I/O memory: [%zx,%lx)", phys_addr, phys_addr + size); return 0; } - return (void *)map_addr; } @@ -664,6 +659,7 @@ void *ioremap(resource_size_t offset, unsigned long size) return _ioremap(offset, size, 0); } + void *devm_ioremap(struct device *dev, resource_size_t offset, unsigned long size) { @@ -671,6 +667,13 @@ void *devm_ioremap(struct device *dev, resource_size_t offset, } +void *devm_ioremap_nocache(struct device *dev, resource_size_t offset, + unsigned long size) +{ + return ioremap(offset, size); +} + + /******************** ** linux/device.h ** ********************/ @@ -680,7 +683,7 @@ void *devm_ioremap(struct device *dev, resource_size_t offset, */ class Driver : public Genode::List::Element { - public: + private: struct device_driver *_drv; /* Linux driver */ @@ -726,7 +729,7 @@ class Driver : public Genode::List::Element dev->driver = _drv; if (dev->bus->probe) { - dde_kit_log(DEBUG_DRIVER, "Probing device bus"); + dde_kit_log(DEBUG_DRIVER, "Probing device bus %p", dev->bus->probe); return dev->bus->probe(dev); } else if (_drv->probe) { dde_kit_log(DEBUG_DRIVER, "Probing driver: %s", _drv->name); @@ -824,6 +827,12 @@ u16 get_unaligned_le16(const void *p) } +void put_unaligned_le16(u16 val, void *p) +{ + struct __una_u16 *ptr = (struct __una_u16 *)p; + ptr->x = val; +} + u32 get_unaligned_le32(const void *p) { const struct __una_u32 *ptr = (const struct __una_u32 *)p; @@ -883,6 +892,7 @@ void udelay(unsigned long usecs) void msleep(unsigned int msecs) { _timer.msleep(msecs); } +void mdelay(unsigned long msecs) { msleep(msecs); } /********************* @@ -929,7 +939,12 @@ void dma_pool_destroy(struct dma_pool *d) void *dma_pool_alloc(struct dma_pool *d, gfp_t f, dma_addr_t *dma) { - return Malloc::dma()->alloc(d->size, d->align, (Genode::addr_t*)dma); + void *addr; + addr = dma_alloc_coherent(0, d->size, dma, 0); + + dde_kit_log(DEBUG_DMA, "addr: %p size %zx align %x phys: %lx pool %p", + addr, d->size, d->align, *dma, d); + return addr; } @@ -996,6 +1011,7 @@ int dma_map_sg_attrs(struct device *dev, struct scatterlist *sg, int nents, enum dma_data_direction dir, struct dma_attrs *attrs) { return nents; } +int dma_set_mask(struct device *dev, u64 mask) { TRACE; return 0; } /********************* ** linux/kthread.h ** @@ -1064,6 +1080,16 @@ resource_size_t resource_size(const struct resource *res) return res->end - res->start + 1; } +struct resource * devm_request_mem_region(struct device *dev, resource_size_t start, + resource_size_t n, const char *name) +{ + struct resource *r = (struct resource *)kzalloc(sizeof(struct resource), GFP_KERNEL); + r->start = start; + r->end = start + n - 1; + r->name = name; + + return r; +} /**************** ** Networking **