Commit bd2e597d authored by Ben Skeggs's avatar Ben Skeggs
Browse files

drm/nv84: add support for the PCRYPT engine



Signed-off-by: default avatarBen Skeggs <bskeggs@redhat.com>
parent b8c157d3
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -18,6 +18,7 @@ nouveau-y := nouveau_drv.o nouveau_state.o nouveau_channel.o nouveau_mem.o \
             nv04_graph.o nv10_graph.o nv20_graph.o \
             nv40_graph.o nv50_graph.o nvc0_graph.o \
             nv40_grctx.o nv50_grctx.o \
             nv84_crypt.o \
             nv04_instmem.o nv50_instmem.o nvc0_instmem.o \
             nv50_crtc.o nv50_dac.o nv50_sor.o \
             nv50_cursor.o nv50_display.o nv50_fbcon.o \
+12 −0
Original line number Diff line number Diff line
@@ -112,6 +112,7 @@ nouveau_channel_alloc(struct drm_device *dev, struct nouveau_channel **chan_ret,
	struct drm_nouveau_private *dev_priv = dev->dev_private;
	struct nouveau_pgraph_engine *pgraph = &dev_priv->engine.graph;
	struct nouveau_fifo_engine *pfifo = &dev_priv->engine.fifo;
	struct nouveau_crypt_engine *pcrypt = &dev_priv->engine.crypt;
	struct nouveau_channel *chan;
	unsigned long flags;
	int user, ret;
@@ -214,6 +215,14 @@ nouveau_channel_alloc(struct drm_device *dev, struct nouveau_channel **chan_ret,
		return ret;
	}

	if (pcrypt->create_context) {
		ret = pcrypt->create_context(chan);
		if (ret) {
			nouveau_channel_put(&chan);
			return ret;
		}
	}

	/* Construct inital RAMFC for new channel */
	ret = pfifo->create_context(chan);
	if (ret) {
@@ -280,6 +289,7 @@ nouveau_channel_put_unlocked(struct nouveau_channel **pchan)
	struct drm_nouveau_private *dev_priv = dev->dev_private;
	struct nouveau_fifo_engine *pfifo = &dev_priv->engine.fifo;
	struct nouveau_pgraph_engine *pgraph = &dev_priv->engine.graph;
	struct nouveau_crypt_engine *pcrypt = &dev_priv->engine.crypt;
	unsigned long flags;
	int ret;

@@ -328,6 +338,8 @@ nouveau_channel_put_unlocked(struct nouveau_channel **pchan)
	/* destroy the engine specific contexts */
	pfifo->destroy_context(chan);
	pgraph->destroy_context(chan);
	if (pcrypt->destroy_context)
		pcrypt->destroy_context(chan);

	pfifo->reassign(dev, true);

+1 −0
Original line number Diff line number Diff line
@@ -299,6 +299,7 @@ nouveau_pci_resume(struct pci_dev *pdev)
	engine->timer.init(dev);
	engine->fb.init(dev);
	engine->graph.init(dev);
	engine->crypt.init(dev);
	engine->fifo.init(dev);

	NV_INFO(dev, "Restoring GPU objects...\n");
+24 −0
Original line number Diff line number Diff line
@@ -132,6 +132,11 @@ enum nouveau_flags {

#define NVOBJ_ENGINE_SW		0
#define NVOBJ_ENGINE_GR		1
#define NVOBJ_ENGINE_PPP	2
#define NVOBJ_ENGINE_COPY	3
#define NVOBJ_ENGINE_VP		4
#define NVOBJ_ENGINE_CRYPT      5
#define NVOBJ_ENGINE_BSP	6
#define NVOBJ_ENGINE_DISPLAY	0xcafe0001
#define NVOBJ_ENGINE_INT	0xdeadbeef

@@ -208,6 +213,7 @@ struct nouveau_channel {
	/* PGRAPH context */
	/* XXX may be merge 2 pointers as private data ??? */
	struct nouveau_gpuobj *ramin_grctx;
	struct nouveau_gpuobj *crypt_ctx;
	void *pgraph_ctx;

	/* NV50 VM */
@@ -444,6 +450,16 @@ struct nouveau_pm_engine {
	int (*temp_get)(struct drm_device *);
};

struct nouveau_crypt_engine {
	bool registered;

	int  (*init)(struct drm_device *);
	void (*takedown)(struct drm_device *);
	int  (*create_context)(struct nouveau_channel *);
	void (*destroy_context)(struct nouveau_channel *);
	void (*tlb_flush)(struct drm_device *dev);
};

struct nouveau_engine {
	struct nouveau_instmem_engine instmem;
	struct nouveau_mc_engine      mc;
@@ -454,6 +470,7 @@ struct nouveau_engine {
	struct nouveau_display_engine display;
	struct nouveau_gpio_engine    gpio;
	struct nouveau_pm_engine      pm;
	struct nouveau_crypt_engine   crypt;
};

struct nouveau_pll_vals {
@@ -1113,6 +1130,13 @@ extern void nvc0_graph_destroy_context(struct nouveau_channel *);
extern int  nvc0_graph_load_context(struct nouveau_channel *);
extern int  nvc0_graph_unload_context(struct drm_device *);

/* nv84_crypt.c */
extern int  nv84_crypt_init(struct drm_device *dev);
extern void nv84_crypt_fini(struct drm_device *dev);
extern int  nv84_crypt_create_context(struct nouveau_channel *);
extern void nv84_crypt_destroy_context(struct nouveau_channel *);
extern void nv84_crypt_tlb_flush(struct drm_device *dev);

/* nv04_instmem.c */
extern int  nv04_instmem_init(struct drm_device *);
extern void nv04_instmem_takedown(struct drm_device *);
+16 −0
Original line number Diff line number Diff line
@@ -1230,6 +1230,22 @@ nouveau_irq_handler(DRM_IRQ_ARGS)
		status &= ~NV_PMC_INTR_0_PGRAPH_PENDING;
	}

	if (status & 0x00004000) {
		u32 stat = nv_rd32(dev, 0x102130);
		u32 mthd = nv_rd32(dev, 0x102190);
		u32 data = nv_rd32(dev, 0x102194);
		u32 inst = nv_rd32(dev, 0x102188) & 0x7fffffff;

		NV_INFO(dev, "PCRYPT_INTR: 0x%08x 0x%08x 0x%08x 0x%08x\n",
			stat, mthd, data, inst);
		nv_wr32(dev, 0x102130, stat);
		nv_wr32(dev, 0x10200c, 0x10);

		nv50_fb_vm_trap(dev, nouveau_ratelimit(), "PCRYPT");
		status &= ~0x00004000;

	}

	if (status & NV_PMC_INTR_0_CRTCn_PENDING) {
		nouveau_crtc_irq_handler(dev, (status>>24)&3);
		status &= ~NV_PMC_INTR_0_CRTCn_PENDING;
Loading