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

Commit c88c2e06 authored by Francisco Jerez's avatar Francisco Jerez Committed by Ben Skeggs
Browse files

drm/nouveau: Move display init to a new nouveau_engine.

parent f1feda70
Loading
Loading
Loading
Loading
+4 −4
Original line number Diff line number Diff line
@@ -263,6 +263,9 @@ nouveau_pci_resume(struct pci_dev *pdev)
	if (dev_priv->gart_info.type == NOUVEAU_GART_AGP)
		nouveau_mem_reset_agp(dev);

	/* Make the CRTCs accessible */
	engine->display.early_init(dev);

	NV_INFO(dev, "POSTing device...\n");
	ret = nouveau_run_vbios_init(dev);
	if (ret)
@@ -325,10 +328,7 @@ nouveau_pci_resume(struct pci_dev *pdev)
			NV_ERROR(dev, "Could not pin/map cursor.\n");
	}

	if (dev_priv->card_type < NV_50)
		nv04_display_restore(dev);
	else
		nv50_display_init(dev);
	engine->display.init(dev);

	list_for_each_entry(crtc, &dev->mode_config.crtc_list, head) {
		struct nouveau_crtc *nv_crtc = nouveau_crtc(crtc);
+12 −1
Original line number Diff line number Diff line
@@ -351,6 +351,14 @@ struct nouveau_pgraph_engine {
				  uint32_t size, uint32_t pitch);
};

struct nouveau_display_engine {
	int (*early_init)(struct drm_device *);
	void (*late_takedown)(struct drm_device *);
	int (*create)(struct drm_device *);
	int (*init)(struct drm_device *);
	void (*destroy)(struct drm_device *);
};

struct nouveau_engine {
	struct nouveau_instmem_engine instmem;
	struct nouveau_mc_engine      mc;
@@ -358,6 +366,7 @@ struct nouveau_engine {
	struct nouveau_fb_engine      fb;
	struct nouveau_pgraph_engine  graph;
	struct nouveau_fifo_engine    fifo;
	struct nouveau_display_engine display;
};

struct nouveau_pll_vals {
@@ -1081,9 +1090,11 @@ extern int nv04_tv_create(struct drm_connector *, struct dcb_entry *);
extern int nv17_tv_create(struct drm_connector *, struct dcb_entry *);

/* nv04_display.c */
extern int nv04_display_early_init(struct drm_device *);
extern void nv04_display_late_takedown(struct drm_device *);
extern int nv04_display_create(struct drm_device *);
extern int nv04_display_init(struct drm_device *);
extern void nv04_display_destroy(struct drm_device *);
extern void nv04_display_restore(struct drm_device *);

/* nv04_crtc.c */
extern int nv04_crtc_create(struct drm_device *, int index);
+43 −13
Original line number Diff line number Diff line
@@ -84,6 +84,11 @@ static int nouveau_init_engine_ptrs(struct drm_device *dev)
		engine->fifo.destroy_context	= nv04_fifo_destroy_context;
		engine->fifo.load_context	= nv04_fifo_load_context;
		engine->fifo.unload_context	= nv04_fifo_unload_context;
		engine->display.early_init	= nv04_display_early_init;
		engine->display.late_takedown	= nv04_display_late_takedown;
		engine->display.create		= nv04_display_create;
		engine->display.init		= nv04_display_init;
		engine->display.destroy		= nv04_display_destroy;
		break;
	case 0x10:
		engine->instmem.init		= nv04_instmem_init;
@@ -126,6 +131,11 @@ static int nouveau_init_engine_ptrs(struct drm_device *dev)
		engine->fifo.destroy_context	= nv10_fifo_destroy_context;
		engine->fifo.load_context	= nv10_fifo_load_context;
		engine->fifo.unload_context	= nv10_fifo_unload_context;
		engine->display.early_init	= nv04_display_early_init;
		engine->display.late_takedown	= nv04_display_late_takedown;
		engine->display.create		= nv04_display_create;
		engine->display.init		= nv04_display_init;
		engine->display.destroy		= nv04_display_destroy;
		break;
	case 0x20:
		engine->instmem.init		= nv04_instmem_init;
@@ -168,6 +178,11 @@ static int nouveau_init_engine_ptrs(struct drm_device *dev)
		engine->fifo.destroy_context	= nv10_fifo_destroy_context;
		engine->fifo.load_context	= nv10_fifo_load_context;
		engine->fifo.unload_context	= nv10_fifo_unload_context;
		engine->display.early_init	= nv04_display_early_init;
		engine->display.late_takedown	= nv04_display_late_takedown;
		engine->display.create		= nv04_display_create;
		engine->display.init		= nv04_display_init;
		engine->display.destroy		= nv04_display_destroy;
		break;
	case 0x30:
		engine->instmem.init		= nv04_instmem_init;
@@ -210,6 +225,11 @@ static int nouveau_init_engine_ptrs(struct drm_device *dev)
		engine->fifo.destroy_context	= nv10_fifo_destroy_context;
		engine->fifo.load_context	= nv10_fifo_load_context;
		engine->fifo.unload_context	= nv10_fifo_unload_context;
		engine->display.early_init	= nv04_display_early_init;
		engine->display.late_takedown	= nv04_display_late_takedown;
		engine->display.create		= nv04_display_create;
		engine->display.init		= nv04_display_init;
		engine->display.destroy		= nv04_display_destroy;
		break;
	case 0x40:
	case 0x60:
@@ -253,6 +273,11 @@ static int nouveau_init_engine_ptrs(struct drm_device *dev)
		engine->fifo.destroy_context	= nv40_fifo_destroy_context;
		engine->fifo.load_context	= nv40_fifo_load_context;
		engine->fifo.unload_context	= nv40_fifo_unload_context;
		engine->display.early_init	= nv04_display_early_init;
		engine->display.late_takedown	= nv04_display_late_takedown;
		engine->display.create		= nv04_display_create;
		engine->display.init		= nv04_display_init;
		engine->display.destroy		= nv04_display_destroy;
		break;
	case 0x50:
	case 0x80: /* gotta love NVIDIA's consistency.. */
@@ -297,6 +322,11 @@ static int nouveau_init_engine_ptrs(struct drm_device *dev)
		engine->fifo.destroy_context	= nv50_fifo_destroy_context;
		engine->fifo.load_context	= nv50_fifo_load_context;
		engine->fifo.unload_context	= nv50_fifo_unload_context;
		engine->display.early_init	= nv50_display_early_init;
		engine->display.late_takedown	= nv50_display_late_takedown;
		engine->display.create		= nv50_display_create;
		engine->display.init		= nv50_display_init;
		engine->display.destroy		= nv50_display_destroy;
		break;
	default:
		NV_ERROR(dev, "NV%02x unsupported\n", dev_priv->chipset);
@@ -415,10 +445,15 @@ nouveau_card_init(struct drm_device *dev)
	engine = &dev_priv->engine;
	spin_lock_init(&dev_priv->context_switch_lock);

	/* Make the CRTCs and I2C buses accessible */
	ret = engine->display.early_init(dev);
	if (ret)
		goto out;

	/* Parse BIOS tables / Run init tables if card not POSTed */
	ret = nouveau_bios_init(dev);
	if (ret)
		goto out;
		goto out_display_early;

	ret = nouveau_mem_detect(dev);
	if (ret)
@@ -474,10 +509,7 @@ nouveau_card_init(struct drm_device *dev)
			goto out_graph;
	}

	if (dev_priv->card_type >= NV_50)
		ret = nv50_display_create(dev);
	else
		ret = nv04_display_create(dev);
	ret = engine->display.create(dev);
	if (ret)
		goto out_fifo;

@@ -511,10 +543,7 @@ nouveau_card_init(struct drm_device *dev)
out_irq:
	drm_irq_uninstall(dev);
out_display:
	if (dev_priv->card_type >= NV_50)
		nv50_display_destroy(dev);
	else
		nv04_display_destroy(dev);
	engine->display.destroy(dev);
out_fifo:
	if (!nouveau_noaccel)
		engine->fifo.takedown(dev);
@@ -538,6 +567,8 @@ nouveau_card_init(struct drm_device *dev)
	nouveau_gpuobj_late_takedown(dev);
out_bios:
	nouveau_bios_takedown(dev);
out_display_early:
	engine->display.late_takedown(dev);
out:
	vga_client_register(dev->pdev, NULL, NULL, NULL);
	return ret;
@@ -562,6 +593,7 @@ static void nouveau_card_takedown(struct drm_device *dev)
	engine->fb.takedown(dev);
	engine->timer.takedown(dev);
	engine->mc.takedown(dev);
	engine->display.late_takedown(dev);

	mutex_lock(&dev->struct_mutex);
	ttm_bo_clean_mm(&dev_priv->ttm.bdev, TTM_PL_VRAM);
@@ -798,13 +830,11 @@ void nouveau_lastclose(struct drm_device *dev)
int nouveau_unload(struct drm_device *dev)
{
	struct drm_nouveau_private *dev_priv = dev->dev_private;
	struct nouveau_engine *engine = &dev_priv->engine;

	drm_kms_helper_poll_fini(dev);
	nouveau_fbcon_fini(dev);
	if (dev_priv->card_type >= NV_50)
		nv50_display_destroy(dev);
	else
		nv04_display_destroy(dev);
	engine->display.destroy(dev);
	nouveau_card_takedown(dev);

	iounmap(dev_priv->mmio);
+30 −16
Original line number Diff line number Diff line
@@ -75,6 +75,32 @@ nv04_display_store_initial_head_owner(struct drm_device *dev)
	}
}

int
nv04_display_early_init(struct drm_device *dev)
{
	/* Unlock the VGA CRTCs. */
	NVLockVgaCrtcs(dev, false);

	/* Make sure the CRTCs aren't in slaved mode. */
	if (nv_two_heads(dev)) {
		nv04_display_store_initial_head_owner(dev);
		NVSetOwner(dev, 0);
	}

	return 0;
}

void
nv04_display_late_takedown(struct drm_device *dev)
{
	struct drm_nouveau_private *dev_priv = dev->dev_private;

	if (nv_two_heads(dev))
		NVSetOwner(dev, dev_priv->crtc_owner);

	NVLockVgaCrtcs(dev, true);
}

int
nv04_display_create(struct drm_device *dev)
{
@@ -87,13 +113,6 @@ nv04_display_create(struct drm_device *dev)

	NV_DEBUG_KMS(dev, "\n");

	NVLockVgaCrtcs(dev, false);

	if (nv_two_heads(dev)) {
		nv04_display_store_initial_head_owner(dev);
		NVSetOwner(dev, 0);
	}

	nouveau_hw_save_vga_fonts(dev, 1);

	drm_mode_config_init(dev);
@@ -176,7 +195,6 @@ nv04_display_create(struct drm_device *dev)
void
nv04_display_destroy(struct drm_device *dev)
{
	struct drm_nouveau_private *dev_priv = dev->dev_private;
	struct drm_encoder *encoder;
	struct drm_crtc *crtc;

@@ -204,20 +222,14 @@ nv04_display_destroy(struct drm_device *dev)
	drm_mode_config_cleanup(dev);

	nouveau_hw_save_vga_fonts(dev, 0);

	if (nv_two_heads(dev))
		NVSetOwner(dev, dev_priv->crtc_owner);
	NVLockVgaCrtcs(dev, true);
}

void
nv04_display_restore(struct drm_device *dev)
int
nv04_display_init(struct drm_device *dev)
{
	struct drm_encoder *encoder;
	struct drm_crtc *crtc;

	NVLockVgaCrtcs(dev, false);

	/* meh.. modeset apparently doesn't setup all the regs and depends
	 * on pre-existing state, for now load the state of the card *before*
	 * nouveau was loaded, and then do a modeset.
@@ -234,5 +246,7 @@ nv04_display_restore(struct drm_device *dev)

	list_for_each_entry(crtc, &dev->mode_config.crtc_list, head)
		crtc->funcs->restore(crtc);

	return 0;
}
+13 −3
Original line number Diff line number Diff line
@@ -177,6 +177,17 @@ nv50_evo_channel_new(struct drm_device *dev, struct nouveau_channel **pchan)
	return 0;
}

int
nv50_display_early_init(struct drm_device *dev)
{
	return 0;
}

void
nv50_display_late_takedown(struct drm_device *dev)
{
}

int
nv50_display_init(struct drm_device *dev)
{
@@ -528,7 +539,8 @@ int nv50_display_create(struct drm_device *dev)
	return 0;
}

int nv50_display_destroy(struct drm_device *dev)
void
nv50_display_destroy(struct drm_device *dev)
{
	struct drm_nouveau_private *dev_priv = dev->dev_private;

@@ -538,8 +550,6 @@ int nv50_display_destroy(struct drm_device *dev)

	nv50_display_disable(dev);
	nv50_evo_channel_del(&dev_priv->evo);

	return 0;
}

static u16
Loading