Donate to e Foundation | Murena handsets with /e/OS | Own a part of Murena! Learn more

Commit 2f5394c3 authored by Ben Skeggs's avatar Ben Skeggs
Browse files

drm/nouveau: map first page of mmio early and determine chipset earlier



Signed-off-by: default avatarBen Skeggs <bskeggs@redhat.com>
parent 4cbb0f8d
Loading
Loading
Loading
Loading
+2 −2
Original line number Original line Diff line number Diff line
@@ -695,14 +695,14 @@ struct nv04_mode_state {
};
};


enum nouveau_card_type {
enum nouveau_card_type {
	NV_04      = 0x00,
	NV_04      = 0x04,
	NV_10      = 0x10,
	NV_10      = 0x10,
	NV_20      = 0x20,
	NV_20      = 0x20,
	NV_30      = 0x30,
	NV_30      = 0x30,
	NV_40      = 0x40,
	NV_40      = 0x40,
	NV_50      = 0x50,
	NV_50      = 0x50,
	NV_C0      = 0xc0,
	NV_C0      = 0xc0,
	NV_D0      = 0xd0
	NV_D0      = 0xd0,
};
};


struct drm_nouveau_private {
struct drm_nouveau_private {
+60 −61
Original line number Original line Diff line number Diff line
@@ -993,7 +993,7 @@ static int nouveau_remove_conflicting_drivers(struct drm_device *dev)
int nouveau_load(struct drm_device *dev, unsigned long flags)
int nouveau_load(struct drm_device *dev, unsigned long flags)
{
{
	struct drm_nouveau_private *dev_priv;
	struct drm_nouveau_private *dev_priv;
	uint32_t reg0, strap;
	uint32_t reg0 = ~0, strap;
	resource_size_t mmio_start_offs;
	resource_size_t mmio_start_offs;
	int ret;
	int ret;


@@ -1012,49 +1012,21 @@ int nouveau_load(struct drm_device *dev, unsigned long flags)
	NV_DEBUG(dev, "vendor: 0x%X device: 0x%X class: 0x%X\n",
	NV_DEBUG(dev, "vendor: 0x%X device: 0x%X class: 0x%X\n",
		 dev->pci_vendor, dev->pci_device, dev->pdev->class);
		 dev->pci_vendor, dev->pci_device, dev->pdev->class);


	/* resource 0 is mmio regs */
	/* first up, map the start of mmio and determine the chipset */
	/* resource 1 is linear FB */
	dev_priv->mmio = ioremap(pci_resource_start(dev->pdev, 0), PAGE_SIZE);
	/* resource 2 is RAMIN (mmio regs + 0x1000000) */
	if (dev_priv->mmio) {
	/* resource 6 is bios */

	/* map the mmio regs */
	mmio_start_offs = pci_resource_start(dev->pdev, 0);
	dev_priv->mmio = ioremap(mmio_start_offs, 0x00800000);
	if (!dev_priv->mmio) {
		NV_ERROR(dev, "Unable to initialize the mmio mapping. "
			 "Please report your setup to " DRIVER_EMAIL "\n");
		ret = -EINVAL;
		goto err_priv;
	}
	NV_DEBUG(dev, "regs mapped ok at 0x%llx\n",
					(unsigned long long)mmio_start_offs);

#ifdef __BIG_ENDIAN
#ifdef __BIG_ENDIAN
	/* Put the card in BE mode if it's not */
		/* put the card into big-endian mode if it's not */
		if (nv_rd32(dev, NV03_PMC_BOOT_1) != 0x01000001)
		if (nv_rd32(dev, NV03_PMC_BOOT_1) != 0x01000001)
			nv_wr32(dev, NV03_PMC_BOOT_1, 0x01000001);
			nv_wr32(dev, NV03_PMC_BOOT_1, 0x01000001);

		DRM_MEMORYBARRIER();
		DRM_MEMORYBARRIER();
#endif
#endif


	/* Time to determine the card architecture */
		/* determine chipset and derive architecture from it */
		reg0 = nv_rd32(dev, NV03_PMC_BOOT_0);
		reg0 = nv_rd32(dev, NV03_PMC_BOOT_0);

	/* We're dealing with >=NV10 */
		if ((reg0 & 0x0f000000) > 0) {
		if ((reg0 & 0x0f000000) > 0) {
		/* Bit 27-20 contain the architecture in hex */
			dev_priv->chipset = (reg0 & 0xff00000) >> 20;
			dev_priv->chipset = (reg0 & 0xff00000) >> 20;
	/* NV04 or NV05 */
	} else if ((reg0 & 0xff00fff0) == 0x20004000) {
		if (reg0 & 0x00f00000)
			dev_priv->chipset = 0x05;
		else
			dev_priv->chipset = 0x04;
	} else
		dev_priv->chipset = 0xff;

			switch (dev_priv->chipset & 0xf0) {
			switch (dev_priv->chipset & 0xf0) {
	case 0x00:
			case 0x10:
			case 0x10:
			case 0x20:
			case 0x20:
			case 0x30:
			case 0x30:
@@ -1077,14 +1049,41 @@ int nouveau_load(struct drm_device *dev, unsigned long flags)
				dev_priv->card_type = NV_D0;
				dev_priv->card_type = NV_D0;
				break;
				break;
			default:
			default:
		NV_INFO(dev, "Unsupported chipset 0x%08x\n", reg0);
				break;
			}
		} else
		if ((reg0 & 0xff00fff0) == 0x20004000) {
			if (reg0 & 0x00f00000)
				dev_priv->chipset = 0x05;
			else
				dev_priv->chipset = 0x04;
			dev_priv->card_type = NV_04;
		}

		iounmap(dev_priv->mmio);
	}

	if (!dev_priv->card_type) {
		NV_ERROR(dev, "unsupported chipset 0x%08x\n", reg0);
		ret = -EINVAL;
		ret = -EINVAL;
		goto err_mmio;
		goto err_priv;
	}
	}


	NV_INFO(dev, "Detected an NV%2x generation card (0x%08x)\n",
	NV_INFO(dev, "Detected an NV%2x generation card (0x%08x)\n",
		     dev_priv->card_type, reg0);
		     dev_priv->card_type, reg0);


	/* map the mmio regs */
	mmio_start_offs = pci_resource_start(dev->pdev, 0);
	dev_priv->mmio = ioremap(mmio_start_offs, 0x00800000);
	if (!dev_priv->mmio) {
		NV_ERROR(dev, "Unable to initialize the mmio mapping. "
			 "Please report your setup to " DRIVER_EMAIL "\n");
		ret = -EINVAL;
		goto err_priv;
	}
	NV_DEBUG(dev, "regs mapped ok at 0x%llx\n",
					(unsigned long long)mmio_start_offs);

	/* determine frequency of timing crystal */
	/* determine frequency of timing crystal */
	strap = nv_rd32(dev, 0x101000);
	strap = nv_rd32(dev, 0x101000);
	if ( dev_priv->chipset < 0x17 ||
	if ( dev_priv->chipset < 0x17 ||