diff --git a/drivers/gpu/drm/hyperv/hyperv_drm_drv.c b/drivers/gpu/drm/hyperv/hyperv_drm_drv.c index 6d11e7938c83..f84d39762a72 100644 --- a/drivers/gpu/drm/hyperv/hyperv_drm_drv.c +++ b/drivers/gpu/drm/hyperv/hyperv_drm_drv.c @@ -23,9 +23,6 @@ #define DRIVER_MAJOR 1 #define DRIVER_MINOR 0 -#define PCI_VENDOR_ID_MICROSOFT 0x1414 -#define PCI_DEVICE_ID_HYPERV_VIDEO 0x5353 - DEFINE_DRM_GEM_FOPS(hv_fops); static struct drm_driver hyperv_driver = { @@ -133,7 +130,6 @@ static int hyperv_vmbus_probe(struct hv_device *hdev, } ret = hyperv_setup_vram(hv, hdev); - if (ret) goto err_vmbus_close; @@ -150,18 +146,20 @@ static int hyperv_vmbus_probe(struct hv_device *hdev, ret = hyperv_mode_config_init(hv); if (ret) - goto err_vmbus_close; + goto err_free_mmio; ret = drm_dev_register(dev, 0); if (ret) { drm_err(dev, "Failed to register drm driver.\n"); - goto err_vmbus_close; + goto err_free_mmio; } drm_fbdev_generic_setup(dev, 0); return 0; +err_free_mmio: + vmbus_free_mmio(hv->mem->start, hv->fb_size); err_vmbus_close: vmbus_close(hdev->channel); err_hv_set_drv_data: diff --git a/drivers/hv/hv_fcopy.c b/drivers/hv/hv_fcopy.c index 660036da7449..922d83eb7ddf 100644 --- a/drivers/hv/hv_fcopy.c +++ b/drivers/hv/hv_fcopy.c @@ -129,7 +129,7 @@ static void fcopy_send_data(struct work_struct *dummy) /* * The strings sent from the host are encoded in - * in utf16; convert it to utf8 strings. + * utf16; convert it to utf8 strings. * The host assures us that the utf16 strings will not exceed * the max lengths specified. We will however, reserve room * for the string terminating character - in the utf16s_utf8s() diff --git a/drivers/hv/vmbus_drv.c b/drivers/hv/vmbus_drv.c index 23c680d1a0f5..3c833ea60db6 100644 --- a/drivers/hv/vmbus_drv.c +++ b/drivers/hv/vmbus_drv.c @@ -35,6 +35,7 @@ #include #include #include +#include #include #include "hyperv_vmbus.h" @@ -2262,26 +2263,43 @@ static int vmbus_acpi_remove(struct acpi_device *device) static void vmbus_reserve_fb(void) { - int size; + resource_size_t start = 0, size; + struct pci_dev *pdev; + + if (efi_enabled(EFI_BOOT)) { + /* Gen2 VM: get FB base from EFI framebuffer */ + start = screen_info.lfb_base; + size = max_t(__u32, screen_info.lfb_size, 0x800000); + } else { + /* Gen1 VM: get FB base from PCI */ + pdev = pci_get_device(PCI_VENDOR_ID_MICROSOFT, + PCI_DEVICE_ID_HYPERV_VIDEO, NULL); + if (!pdev) + return; + + if (pdev->resource[0].flags & IORESOURCE_MEM) { + start = pci_resource_start(pdev, 0); + size = pci_resource_len(pdev, 0); + } + + /* + * Release the PCI device so hyperv_drm or hyperv_fb driver can + * grab it later. + */ + pci_dev_put(pdev); + } + + if (!start) + return; + /* * Make a claim for the frame buffer in the resource tree under the * first node, which will be the one below 4GB. The length seems to * be underreported, particularly in a Generation 1 VM. So start out * reserving a larger area and make it smaller until it succeeds. */ - - if (screen_info.lfb_base) { - if (efi_enabled(EFI_BOOT)) - size = max_t(__u32, screen_info.lfb_size, 0x800000); - else - size = max_t(__u32, screen_info.lfb_size, 0x4000000); - - for (; !fb_mmio && (size >= 0x100000); size >>= 1) { - fb_mmio = __request_region(hyperv_mmio, - screen_info.lfb_base, size, - fb_mmio_name, 0); - } - } + for (; !fb_mmio && (size >= 0x100000); size >>= 1) + fb_mmio = __request_region(hyperv_mmio, start, size, fb_mmio_name, 0); } /** @@ -2313,7 +2331,7 @@ int vmbus_allocate_mmio(struct resource **new, struct hv_device *device_obj, bool fb_overlap_ok) { struct resource *iter, *shadow; - resource_size_t range_min, range_max, start; + resource_size_t range_min, range_max, start, end; const char *dev_n = dev_name(&device_obj->device); int retval; @@ -2348,6 +2366,14 @@ int vmbus_allocate_mmio(struct resource **new, struct hv_device *device_obj, range_max = iter->end; start = (range_min + align - 1) & ~(align - 1); for (; start + size - 1 <= range_max; start += align) { + end = start + size - 1; + + /* Skip the whole fb_mmio region if not fb_overlap_ok */ + if (!fb_overlap_ok && fb_mmio && + (((start >= fb_mmio->start) && (start <= fb_mmio->end)) || + ((end >= fb_mmio->start) && (end <= fb_mmio->end)))) + continue; + shadow = __request_region(iter, start, size, NULL, IORESOURCE_BUSY); if (!shadow) diff --git a/drivers/net/ethernet/microsoft/mana/gdma_main.c b/drivers/net/ethernet/microsoft/mana/gdma_main.c index 5f9240182351..00d8198072ae 100644 --- a/drivers/net/ethernet/microsoft/mana/gdma_main.c +++ b/drivers/net/ethernet/microsoft/mana/gdma_main.c @@ -1465,10 +1465,6 @@ static void mana_gd_shutdown(struct pci_dev *pdev) pci_disable_device(pdev); } -#ifndef PCI_VENDOR_ID_MICROSOFT -#define PCI_VENDOR_ID_MICROSOFT 0x1414 -#endif - static const struct pci_device_id mana_id_table[] = { { PCI_DEVICE(PCI_VENDOR_ID_MICROSOFT, MANA_PF_DEVICE_ID) }, { PCI_DEVICE(PCI_VENDOR_ID_MICROSOFT, MANA_VF_DEVICE_ID) }, diff --git a/drivers/video/fbdev/hyperv_fb.c b/drivers/video/fbdev/hyperv_fb.c index 886c564787f1..b58b445bb529 100644 --- a/drivers/video/fbdev/hyperv_fb.c +++ b/drivers/video/fbdev/hyperv_fb.c @@ -74,10 +74,6 @@ #define SYNTHVID_DEPTH_WIN8 32 #define SYNTHVID_FB_SIZE_WIN8 (8 * 1024 * 1024) -#define PCI_VENDOR_ID_MICROSOFT 0x1414 -#define PCI_DEVICE_ID_HYPERV_VIDEO 0x5353 - - enum pipe_msg_type { PIPE_MSG_INVALID, PIPE_MSG_DATA, diff --git a/include/linux/pci_ids.h b/include/linux/pci_ids.h index 6feade66efdb..15b49e655ce3 100644 --- a/include/linux/pci_ids.h +++ b/include/linux/pci_ids.h @@ -2079,6 +2079,9 @@ #define PCI_DEVICE_ID_ICE_1712 0x1712 #define PCI_DEVICE_ID_VT1724 0x1724 +#define PCI_VENDOR_ID_MICROSOFT 0x1414 +#define PCI_DEVICE_ID_HYPERV_VIDEO 0x5353 + #define PCI_VENDOR_ID_OXSEMI 0x1415 #define PCI_DEVICE_ID_OXSEMI_12PCI840 0x8403 #define PCI_DEVICE_ID_OXSEMI_PCIe840 0xC000 diff --git a/tools/hv/hv_kvp_daemon.c b/tools/hv/hv_kvp_daemon.c index 1e6fd6ca513b..27f5e7dfc2f7 100644 --- a/tools/hv/hv_kvp_daemon.c +++ b/tools/hv/hv_kvp_daemon.c @@ -44,7 +44,7 @@ /* * KVP protocol: The user mode component first registers with the - * the kernel component. Subsequently, the kernel component requests, data + * kernel component. Subsequently, the kernel component requests, data * for the specified keys. In response to this message the user mode component * fills in the value corresponding to the specified key. We overload the * sequence field in the cn_msg header to define our KVP message types. @@ -772,11 +772,11 @@ static int kvp_process_ip_address(void *addrp, const char *str; if (family == AF_INET) { - addr = (struct sockaddr_in *)addrp; + addr = addrp; str = inet_ntop(family, &addr->sin_addr, tmp, 50); addr_length = INET_ADDRSTRLEN; } else { - addr6 = (struct sockaddr_in6 *)addrp; + addr6 = addrp; str = inet_ntop(family, &addr6->sin6_addr.s6_addr, tmp, 50); addr_length = INET6_ADDRSTRLEN; }