⭐ 欢迎来到虫虫下载站! | 📦 资源下载 📁 资源专辑 ℹ️ 关于我们
⭐ 虫虫下载站

📄 i830_dma.c

📁 linux-2.6.15.6
💻 C
📖 第 1 页 / 共 3 页
字号:
static void i830EmitTexVerified(drm_device_t * dev, unsigned int *code){	drm_i830_private_t *dev_priv = dev->dev_private;	int i, j = 0;	unsigned int tmp;	RING_LOCALS;	if (code[I830_TEXREG_MI0] == GFX_OP_MAP_INFO ||	    (code[I830_TEXREG_MI0] & ~(0xf * LOAD_TEXTURE_MAP0)) ==	    (STATE3D_LOAD_STATE_IMMEDIATE_2 | 4)) {		BEGIN_LP_RING(I830_TEX_SETUP_SIZE);		OUT_RING(code[I830_TEXREG_MI0]);	/* TM0LI */		OUT_RING(code[I830_TEXREG_MI1]);	/* TM0S0 */		OUT_RING(code[I830_TEXREG_MI2]);	/* TM0S1 */		OUT_RING(code[I830_TEXREG_MI3]);	/* TM0S2 */		OUT_RING(code[I830_TEXREG_MI4]);	/* TM0S3 */		OUT_RING(code[I830_TEXREG_MI5]);	/* TM0S4 */		for (i = 6; i < I830_TEX_SETUP_SIZE; i++) {			tmp = code[i];			OUT_RING(tmp);			j++;		}		if (j & 1)			OUT_RING(0);		ADVANCE_LP_RING();	} else		printk("rejected packet %x\n", code[0]);}static void i830EmitTexBlendVerified(drm_device_t * dev,				     unsigned int *code, unsigned int num){	drm_i830_private_t *dev_priv = dev->dev_private;	int i, j = 0;	unsigned int tmp;	RING_LOCALS;	if (!num)		return;	BEGIN_LP_RING(num + 1);	for (i = 0; i < num; i++) {		tmp = code[i];		OUT_RING(tmp);		j++;	}	if (j & 1)		OUT_RING(0);	ADVANCE_LP_RING();}static void i830EmitTexPalette(drm_device_t * dev,			       unsigned int *palette, int number, int is_shared){	drm_i830_private_t *dev_priv = dev->dev_private;	int i;	RING_LOCALS;	return;	BEGIN_LP_RING(258);	if (is_shared == 1) {		OUT_RING(CMD_OP_MAP_PALETTE_LOAD |			 MAP_PALETTE_NUM(0) | MAP_PALETTE_BOTH);	} else {		OUT_RING(CMD_OP_MAP_PALETTE_LOAD | MAP_PALETTE_NUM(number));	}	for (i = 0; i < 256; i++) {		OUT_RING(palette[i]);	}	OUT_RING(0);	/* KW:  WHERE IS THE ADVANCE_LP_RING?  This is effectively a noop!	 */}/* Need to do some additional checking when setting the dest buffer. */static void i830EmitDestVerified(drm_device_t * dev, unsigned int *code){	drm_i830_private_t *dev_priv = dev->dev_private;	unsigned int tmp;	RING_LOCALS;	BEGIN_LP_RING(I830_DEST_SETUP_SIZE + 10);	tmp = code[I830_DESTREG_CBUFADDR];	if (tmp == dev_priv->front_di1 || tmp == dev_priv->back_di1) {		if (((int)outring) & 8) {			OUT_RING(0);			OUT_RING(0);		}		OUT_RING(CMD_OP_DESTBUFFER_INFO);		OUT_RING(BUF_3D_ID_COLOR_BACK |			 BUF_3D_PITCH(dev_priv->back_pitch * dev_priv->cpp) |			 BUF_3D_USE_FENCE);		OUT_RING(tmp);		OUT_RING(0);		OUT_RING(CMD_OP_DESTBUFFER_INFO);		OUT_RING(BUF_3D_ID_DEPTH | BUF_3D_USE_FENCE |			 BUF_3D_PITCH(dev_priv->depth_pitch * dev_priv->cpp));		OUT_RING(dev_priv->zi1);		OUT_RING(0);	} else {		DRM_ERROR("bad di1 %x (allow %x or %x)\n",			  tmp, dev_priv->front_di1, dev_priv->back_di1);	}	/* invarient:	 */	OUT_RING(GFX_OP_DESTBUFFER_VARS);	OUT_RING(code[I830_DESTREG_DV1]);	OUT_RING(GFX_OP_DRAWRECT_INFO);	OUT_RING(code[I830_DESTREG_DR1]);	OUT_RING(code[I830_DESTREG_DR2]);	OUT_RING(code[I830_DESTREG_DR3]);	OUT_RING(code[I830_DESTREG_DR4]);	/* Need to verify this */	tmp = code[I830_DESTREG_SENABLE];	if ((tmp & ~0x3) == GFX_OP_SCISSOR_ENABLE) {		OUT_RING(tmp);	} else {		DRM_ERROR("bad scissor enable\n");		OUT_RING(0);	}	OUT_RING(GFX_OP_SCISSOR_RECT);	OUT_RING(code[I830_DESTREG_SR1]);	OUT_RING(code[I830_DESTREG_SR2]);	OUT_RING(0);	ADVANCE_LP_RING();}static void i830EmitStippleVerified(drm_device_t * dev, unsigned int *code){	drm_i830_private_t *dev_priv = dev->dev_private;	RING_LOCALS;	BEGIN_LP_RING(2);	OUT_RING(GFX_OP_STIPPLE);	OUT_RING(code[1]);	ADVANCE_LP_RING();}static void i830EmitState(drm_device_t * dev){	drm_i830_private_t *dev_priv = dev->dev_private;	drm_i830_sarea_t *sarea_priv = dev_priv->sarea_priv;	unsigned int dirty = sarea_priv->dirty;	DRM_DEBUG("%s %x\n", __FUNCTION__, dirty);	if (dirty & I830_UPLOAD_BUFFERS) {		i830EmitDestVerified(dev, sarea_priv->BufferState);		sarea_priv->dirty &= ~I830_UPLOAD_BUFFERS;	}	if (dirty & I830_UPLOAD_CTX) {		i830EmitContextVerified(dev, sarea_priv->ContextState);		sarea_priv->dirty &= ~I830_UPLOAD_CTX;	}	if (dirty & I830_UPLOAD_TEX0) {		i830EmitTexVerified(dev, sarea_priv->TexState[0]);		sarea_priv->dirty &= ~I830_UPLOAD_TEX0;	}	if (dirty & I830_UPLOAD_TEX1) {		i830EmitTexVerified(dev, sarea_priv->TexState[1]);		sarea_priv->dirty &= ~I830_UPLOAD_TEX1;	}	if (dirty & I830_UPLOAD_TEXBLEND0) {		i830EmitTexBlendVerified(dev, sarea_priv->TexBlendState[0],					 sarea_priv->TexBlendStateWordsUsed[0]);		sarea_priv->dirty &= ~I830_UPLOAD_TEXBLEND0;	}	if (dirty & I830_UPLOAD_TEXBLEND1) {		i830EmitTexBlendVerified(dev, sarea_priv->TexBlendState[1],					 sarea_priv->TexBlendStateWordsUsed[1]);		sarea_priv->dirty &= ~I830_UPLOAD_TEXBLEND1;	}	if (dirty & I830_UPLOAD_TEX_PALETTE_SHARED) {		i830EmitTexPalette(dev, sarea_priv->Palette[0], 0, 1);	} else {		if (dirty & I830_UPLOAD_TEX_PALETTE_N(0)) {			i830EmitTexPalette(dev, sarea_priv->Palette[0], 0, 0);			sarea_priv->dirty &= ~I830_UPLOAD_TEX_PALETTE_N(0);		}		if (dirty & I830_UPLOAD_TEX_PALETTE_N(1)) {			i830EmitTexPalette(dev, sarea_priv->Palette[1], 1, 0);			sarea_priv->dirty &= ~I830_UPLOAD_TEX_PALETTE_N(1);		}		/* 1.3:		 */#if 0		if (dirty & I830_UPLOAD_TEX_PALETTE_N(2)) {			i830EmitTexPalette(dev, sarea_priv->Palette2[0], 0, 0);			sarea_priv->dirty &= ~I830_UPLOAD_TEX_PALETTE_N(2);		}		if (dirty & I830_UPLOAD_TEX_PALETTE_N(3)) {			i830EmitTexPalette(dev, sarea_priv->Palette2[1], 1, 0);			sarea_priv->dirty &= ~I830_UPLOAD_TEX_PALETTE_N(2);		}#endif	}	/* 1.3:	 */	if (dirty & I830_UPLOAD_STIPPLE) {		i830EmitStippleVerified(dev, sarea_priv->StippleState);		sarea_priv->dirty &= ~I830_UPLOAD_STIPPLE;	}	if (dirty & I830_UPLOAD_TEX2) {		i830EmitTexVerified(dev, sarea_priv->TexState2);		sarea_priv->dirty &= ~I830_UPLOAD_TEX2;	}	if (dirty & I830_UPLOAD_TEX3) {		i830EmitTexVerified(dev, sarea_priv->TexState3);		sarea_priv->dirty &= ~I830_UPLOAD_TEX3;	}	if (dirty & I830_UPLOAD_TEXBLEND2) {		i830EmitTexBlendVerified(dev,					 sarea_priv->TexBlendState2,					 sarea_priv->TexBlendStateWordsUsed2);		sarea_priv->dirty &= ~I830_UPLOAD_TEXBLEND2;	}	if (dirty & I830_UPLOAD_TEXBLEND3) {		i830EmitTexBlendVerified(dev,					 sarea_priv->TexBlendState3,					 sarea_priv->TexBlendStateWordsUsed3);		sarea_priv->dirty &= ~I830_UPLOAD_TEXBLEND3;	}}/* ================================================================ * Performance monitoring functions */static void i830_fill_box(drm_device_t * dev,			  int x, int y, int w, int h, int r, int g, int b){	drm_i830_private_t *dev_priv = dev->dev_private;	u32 color;	unsigned int BR13, CMD;	RING_LOCALS;	BR13 = (0xF0 << 16) | (dev_priv->pitch * dev_priv->cpp) | (1 << 24);	CMD = XY_COLOR_BLT_CMD;	x += dev_priv->sarea_priv->boxes[0].x1;	y += dev_priv->sarea_priv->boxes[0].y1;	if (dev_priv->cpp == 4) {		BR13 |= (1 << 25);		CMD |= (XY_COLOR_BLT_WRITE_ALPHA | XY_COLOR_BLT_WRITE_RGB);		color = (((0xff) << 24) | (r << 16) | (g << 8) | b);	} else {		color = (((r & 0xf8) << 8) |			 ((g & 0xfc) << 3) | ((b & 0xf8) >> 3));	}	BEGIN_LP_RING(6);	OUT_RING(CMD);	OUT_RING(BR13);	OUT_RING((y << 16) | x);	OUT_RING(((y + h) << 16) | (x + w));	if (dev_priv->current_page == 1) {		OUT_RING(dev_priv->front_offset);	} else {		OUT_RING(dev_priv->back_offset);	}	OUT_RING(color);	ADVANCE_LP_RING();}static void i830_cp_performance_boxes(drm_device_t * dev){	drm_i830_private_t *dev_priv = dev->dev_private;	/* Purple box for page flipping	 */	if (dev_priv->sarea_priv->perf_boxes & I830_BOX_FLIP)		i830_fill_box(dev, 4, 4, 8, 8, 255, 0, 255);	/* Red box if we have to wait for idle at any point	 */	if (dev_priv->sarea_priv->perf_boxes & I830_BOX_WAIT)		i830_fill_box(dev, 16, 4, 8, 8, 255, 0, 0);	/* Blue box: lost context?	 */	if (dev_priv->sarea_priv->perf_boxes & I830_BOX_LOST_CONTEXT)		i830_fill_box(dev, 28, 4, 8, 8, 0, 0, 255);	/* Yellow box for texture swaps	 */	if (dev_priv->sarea_priv->perf_boxes & I830_BOX_TEXTURE_LOAD)		i830_fill_box(dev, 40, 4, 8, 8, 255, 255, 0);	/* Green box if hardware never idles (as far as we can tell)	 */	if (!(dev_priv->sarea_priv->perf_boxes & I830_BOX_RING_EMPTY))		i830_fill_box(dev, 64, 4, 8, 8, 0, 255, 0);	/* Draw bars indicating number of buffers allocated	 * (not a great measure, easily confused)	 */	if (dev_priv->dma_used) {		int bar = dev_priv->dma_used / 10240;		if (bar > 100)			bar = 100;		if (bar < 1)			bar = 1;		i830_fill_box(dev, 4, 16, bar, 4, 196, 128, 128);		dev_priv->dma_used = 0;	}	dev_priv->sarea_priv->perf_boxes = 0;}static void i830_dma_dispatch_clear(drm_device_t * dev, int flags,				    unsigned int clear_color,				    unsigned int clear_zval,				    unsigned int clear_depthmask){	drm_i830_private_t *dev_priv = dev->dev_private;	drm_i830_sarea_t *sarea_priv = dev_priv->sarea_priv;	int nbox = sarea_priv->nbox;	drm_clip_rect_t *pbox = sarea_priv->boxes;	int pitch = dev_priv->pitch;	int cpp = dev_priv->cpp;	int i;	unsigned int BR13, CMD, D_CMD;	RING_LOCALS;	if (dev_priv->current_page == 1) {		unsigned int tmp = flags;		flags &= ~(I830_FRONT | I830_BACK);		if (tmp & I830_FRONT)			flags |= I830_BACK;		if (tmp & I830_BACK)			flags |= I830_FRONT;	}	i830_kernel_lost_context(dev);	switch (cpp) {	case 2:		BR13 = (0xF0 << 16) | (pitch * cpp) | (1 << 24);		D_CMD = CMD = XY_COLOR_BLT_CMD;		break;	case 4:		BR13 = (0xF0 << 16) | (pitch * cpp) | (1 << 24) | (1 << 25);		CMD = (XY_COLOR_BLT_CMD | XY_COLOR_BLT_WRITE_ALPHA |		       XY_COLOR_BLT_WRITE_RGB);		D_CMD = XY_COLOR_BLT_CMD;		if (clear_depthmask & 0x00ffffff)			D_CMD |= XY_COLOR_BLT_WRITE_RGB;		if (clear_depthmask & 0xff000000)			D_CMD |= XY_COLOR_BLT_WRITE_ALPHA;		break;	default:		BR13 = (0xF0 << 16) | (pitch * cpp) | (1 << 24);		D_CMD = CMD = XY_COLOR_BLT_CMD;		break;	}	if (nbox > I830_NR_SAREA_CLIPRECTS)		nbox = I830_NR_SAREA_CLIPRECTS;	for (i = 0; i < nbox; i++, pbox++) {		if (pbox->x1 > pbox->x2 ||		    pbox->y1 > pbox->y2 ||		    pbox->x2 > dev_priv->w || pbox->y2 > dev_priv->h)			continue;		if (flags & I830_FRONT) {			DRM_DEBUG("clear front\n");			BEGIN_LP_RING(6);			OUT_RING(CMD);			OUT_RING(BR13);			OUT_RING((pbox->y1 << 16) | pbox->x1);			OUT_RING((pbox->y2 << 16) | pbox->x2);			OUT_RING(dev_priv->front_offset);			OUT_RING(clear_color);			ADVANCE_LP_RING();		}		if (flags & I830_BACK) {			DRM_DEBUG("clear back\n");			BEGIN_LP_RING(6);			OUT_RING(CMD);			OUT_RING(BR13);			OUT_RING((pbox->y1 << 16) | pbox->x1);			OUT_RING((pbox->y2 << 16) | pbox->x2);			OUT_RING(dev_priv->back_offset);			OUT_RING(clear_color);			ADVANCE_LP_RING();		}		if (flags & I830_DEPTH) {			DRM_DEBUG("clear depth\n");			BEGIN_LP_RING(6);			OUT_RING(D_CMD);			OUT_RING(BR13);			OUT_RING((pbox->y1 << 16) | pbox->x1);			OUT_RING((pbox->y2 << 16) | pbox->x2);			OUT_RING(dev_priv->depth_offset);			OUT_RING(clear_zval);			ADVANCE_LP_RING();		}	}}static void i830_dma_dispatch_swap(drm_device_t * dev){	drm_i830_private_t *dev_priv = dev->dev_private;	drm_i830_sarea_t *sarea_priv = dev_priv->sarea_priv;	int nbox = sarea_priv->nbox;	drm_clip_rect_t *pbox = sarea_priv->boxes;	int pitch = dev_priv->pitch;	int cpp = dev_priv->cpp;	int i;	unsigned int CMD, BR13;	RING_LOCALS;	DRM_DEBUG("swapbuffers\n");	i830_kernel_lost_context(dev);	if (dev_priv->do_boxes)		i830_cp_performance_boxes(dev);	switch (cpp) {	case 2:		BR13 = (pitch * cpp) | (0xCC << 16) | (1 << 24);		CMD = XY_SRC_COPY_BLT_CMD;		break;	case 4:		BR13 = (pitch * cpp) | (0xCC << 16) | (1 << 24) | (1 << 25);		CMD = (XY_SRC_COPY_BLT_CMD | XY_SRC_COPY_BLT_WRITE_ALPHA |		       XY_SRC_COPY_BLT_WRITE_RGB);		break;	default:		BR13 = (pitch * cpp) | (0xCC << 16) | (1 << 24);		CMD = XY_SRC_COPY_BLT_CMD;		break;	}	if (nbox > I830_NR_SAREA_CLIPRECTS)		nbox = I830_NR_SAREA_CLIPRECTS;	for (i = 0; i < nbox; i++, pbox++) {		if (pbox->x1 > pbox->x2 ||		    pbox->y1 > pbox->y2 ||		    pbox->x2 > dev_priv->w || pbox->y2 > dev_priv->h)			continue;		DRM_DEBUG("dispatch swap %d,%d-%d,%d!\n",			  pbox->x1, pbox->y1, pbox->x2, pbox->y2);		BEGIN_LP_RING(8);		OUT_RING(CMD);		OUT_RING(BR13);		OUT_RING((pbox->y1 << 16) | pbox->x1);		OUT_RING((pbox->y2 << 16) | pbox->x2);		if (dev_priv->current_page == 0)			OUT_RING(dev_priv->front_offset);		else			OUT_RING(dev_priv->back_offset);		OUT_RING((pbox->y1 << 16) | pbox->x1);		OUT_RING(BR13 & 0xffff);		if (dev_priv->current_page == 0)			OUT_RING(dev_priv->back_offset);		else			OUT_RING(dev_priv->front_offset);		ADVANCE_LP_RING();	}}static void i830_dma_dispatch_flip(drm_device_t * dev){	drm_i830_private_t *dev_priv = dev->dev_private;	RING_LOCALS;	DRM_DEBUG("%s: page=%d pfCurrentPage=%d\n",		  __FUNCTION__,		  dev_priv->current_page,		  dev_priv->sarea_priv->pf_current_page);	i830_kernel_lost_context(dev);	if (dev_priv->do_boxes) {		dev_priv->sarea_priv->perf_boxes |= I830_BOX_FLIP;		i830_cp_performance_boxes(dev);	}

⌨️ 快捷键说明

复制代码 Ctrl + C
搜索代码 Ctrl + F
全屏模式 F11
切换主题 Ctrl + Shift + D
显示快捷键 ?
增大字号 Ctrl + =
减小字号 Ctrl + -