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

📄 cx23885-417.c

📁 trident tm5600的linux驱动
💻 C
📖 第 1 页 / 共 4 页
字号:
	regval = MC417_MIWR | MC417_MIRD | MC417_MICS | MC417_MIRDY;	cx_write(MC417_RWD, regval);	/* Read data byte 3 */	regval = MC417_MIRD | MC417_MIRDY | MCI_REGISTER_DATA_BYTE3;	cx_write(MC417_RWD, regval);	regval = MC417_MIWR | MC417_MIRDY | MCI_REGISTER_DATA_BYTE3;	cx_write(MC417_RWD, regval);	tempval = cx_read(MC417_RWD);	dataval |= ((tempval & 0x000000FF) << 24);	regval = MC417_MIWR | MC417_MIRD | MC417_MICS | MC417_MIRDY;	cx_write(MC417_RWD, regval);	*value  = dataval;	return retval;}int mc417_memory_write(struct cx23885_dev *dev, u32 address, u32 value){	u32 regval;	/* Enable MC417 GPIO outputs except for MC417_MIRDY,	 * which is an input.	 */	cx_write(MC417_OEN, MC417_MIRDY);	/* Write data byte 0 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_DATA_BYTE0 |		(value & 0x000000FF);	cx_write(MC417_RWD, regval);	/* Transition CS/WR to effect write transaction across bus. */	regval |= MC417_MICS | MC417_MIWR;	cx_write(MC417_RWD, regval);	/* Write data byte 1 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_DATA_BYTE1 |		((value >> 8) & 0x000000FF);	cx_write(MC417_RWD, regval);	regval |= MC417_MICS | MC417_MIWR;	cx_write(MC417_RWD, regval);	/* Write data byte 2 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_DATA_BYTE2 |		((value >> 16) & 0x000000FF);	cx_write(MC417_RWD, regval);	regval |= MC417_MICS | MC417_MIWR;	cx_write(MC417_RWD, regval);	/* Write data byte 3 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_DATA_BYTE3 |		((value >> 24) & 0x000000FF);	cx_write(MC417_RWD, regval);	regval |= MC417_MICS | MC417_MIWR;	cx_write(MC417_RWD, regval);	/* Write address byte 2 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_ADDRESS_BYTE2 |		MCI_MODE_MEMORY_WRITE | ((address >> 16) & 0x3F);	cx_write(MC417_RWD, regval);	regval |= MC417_MICS | MC417_MIWR;	cx_write(MC417_RWD, regval);	/* Write address byte 1 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_ADDRESS_BYTE1 |		((address >> 8) & 0xFF);	cx_write(MC417_RWD, regval);	regval |= MC417_MICS | MC417_MIWR;	cx_write(MC417_RWD, regval);	/* Write address byte 0 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_ADDRESS_BYTE0 |		(address & 0xFF);	cx_write(MC417_RWD, regval);	regval |= MC417_MICS | MC417_MIWR;	cx_write(MC417_RWD, regval);	/* Wait for the trans to complete (MC417_MIRDY asserted). */	return mc417_wait_ready(dev);}int mc417_memory_read(struct cx23885_dev *dev, u32 address, u32 *value){	int retval;	u32 regval;	u32 tempval;	u32 dataval;	/* Enable MC417 GPIO outputs except for MC417_MIRDY,	 * which is an input.	 */	cx_write(MC417_OEN, MC417_MIRDY);	/* Write address byte 2 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_ADDRESS_BYTE2 |		MCI_MODE_MEMORY_READ | ((address >> 16) & 0x3F);	cx_write(MC417_RWD, regval);	regval |= MC417_MICS | MC417_MIWR;	cx_write(MC417_RWD, regval);	/* Write address byte 1 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_ADDRESS_BYTE1 |		((address >> 8) & 0xFF);	cx_write(MC417_RWD, regval);	regval |= MC417_MICS | MC417_MIWR;	cx_write(MC417_RWD, regval);	/* Write address byte 0 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_ADDRESS_BYTE0 |		(address & 0xFF);	cx_write(MC417_RWD, regval);	regval |= MC417_MICS | MC417_MIWR;	cx_write(MC417_RWD, regval);	/* Wait for the trans to complete (MC417_MIRDY asserted). */	retval = mc417_wait_ready(dev);	/* switch the DAT0-7 GPIO[10:3] to input mode */	cx_write(MC417_OEN, MC417_MIRDY | MC417_MIDATA);	/* Read data byte 3 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_DATA_BYTE3;	cx_write(MC417_RWD, regval);	/* Transition RD to effect read transaction across bus. */	regval = MC417_MIWR | MC417_MIRDY | MCI_MEMORY_DATA_BYTE3;	cx_write(MC417_RWD, regval);	/* Collect byte */	tempval = cx_read(MC417_RWD);	dataval = ((tempval & 0x000000FF) << 24);	/* Bring CS and RD high. */	regval = MC417_MIWR | MC417_MIRD | MC417_MICS | MC417_MIRDY;	cx_write(MC417_RWD, regval);	/* Read data byte 2 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_DATA_BYTE2;	cx_write(MC417_RWD, regval);	regval = MC417_MIWR | MC417_MIRDY | MCI_MEMORY_DATA_BYTE2;	cx_write(MC417_RWD, regval);	tempval = cx_read(MC417_RWD);	dataval |= ((tempval & 0x000000FF) << 16);	regval = MC417_MIWR | MC417_MIRD | MC417_MICS | MC417_MIRDY;	cx_write(MC417_RWD, regval);	/* Read data byte 1 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_DATA_BYTE1;	cx_write(MC417_RWD, regval);	regval = MC417_MIWR | MC417_MIRDY | MCI_MEMORY_DATA_BYTE1;	cx_write(MC417_RWD, regval);	tempval = cx_read(MC417_RWD);	dataval |= ((tempval & 0x000000FF) << 8);	regval = MC417_MIWR | MC417_MIRD | MC417_MICS | MC417_MIRDY;	cx_write(MC417_RWD, regval);	/* Read data byte 0 */	regval = MC417_MIRD | MC417_MIRDY | MCI_MEMORY_DATA_BYTE0;	cx_write(MC417_RWD, regval);	regval = MC417_MIWR | MC417_MIRDY | MCI_MEMORY_DATA_BYTE0;	cx_write(MC417_RWD, regval);	tempval = cx_read(MC417_RWD);	dataval |= (tempval & 0x000000FF);	regval = MC417_MIWR | MC417_MIRD | MC417_MICS | MC417_MIRDY;	cx_write(MC417_RWD, regval);	*value  = dataval;	return retval;}/* ------------------------------------------------------------------ *//* MPEG encoder API */static char *cmd_to_str(int cmd){	switch (cmd) {	case CX2341X_ENC_PING_FW:		return  "PING_FW";	case CX2341X_ENC_START_CAPTURE:		return  "START_CAPTURE";	case CX2341X_ENC_STOP_CAPTURE:		return  "STOP_CAPTURE";	case CX2341X_ENC_SET_AUDIO_ID:		return  "SET_AUDIO_ID";	case CX2341X_ENC_SET_VIDEO_ID:		return  "SET_VIDEO_ID";	case CX2341X_ENC_SET_PCR_ID:		return  "SET_PCR_PID";	case CX2341X_ENC_SET_FRAME_RATE:		return  "SET_FRAME_RATE";	case CX2341X_ENC_SET_FRAME_SIZE:		return  "SET_FRAME_SIZE";	case CX2341X_ENC_SET_BIT_RATE:		return  "SET_BIT_RATE";	case CX2341X_ENC_SET_GOP_PROPERTIES:		return  "SET_GOP_PROPERTIES";	case CX2341X_ENC_SET_ASPECT_RATIO:		return  "SET_ASPECT_RATIO";	case CX2341X_ENC_SET_DNR_FILTER_MODE:		return  "SET_DNR_FILTER_PROPS";	case CX2341X_ENC_SET_DNR_FILTER_PROPS:		return  "SET_DNR_FILTER_PROPS";	case CX2341X_ENC_SET_CORING_LEVELS:		return  "SET_CORING_LEVELS";	case CX2341X_ENC_SET_SPATIAL_FILTER_TYPE:		return  "SET_SPATIAL_FILTER_TYPE";	case CX2341X_ENC_SET_VBI_LINE:		return  "SET_VBI_LINE";	case CX2341X_ENC_SET_STREAM_TYPE:		return  "SET_STREAM_TYPE";	case CX2341X_ENC_SET_OUTPUT_PORT:		return  "SET_OUTPUT_PORT";	case CX2341X_ENC_SET_AUDIO_PROPERTIES:		return  "SET_AUDIO_PROPERTIES";	case CX2341X_ENC_HALT_FW:		return  "HALT_FW";	case CX2341X_ENC_GET_VERSION:		return  "GET_VERSION";	case CX2341X_ENC_SET_GOP_CLOSURE:		return  "SET_GOP_CLOSURE";	case CX2341X_ENC_GET_SEQ_END:		return  "GET_SEQ_END";	case CX2341X_ENC_SET_PGM_INDEX_INFO:		return  "SET_PGM_INDEX_INFO";	case CX2341X_ENC_SET_VBI_CONFIG:		return  "SET_VBI_CONFIG";	case CX2341X_ENC_SET_DMA_BLOCK_SIZE:		return  "SET_DMA_BLOCK_SIZE";	case CX2341X_ENC_GET_PREV_DMA_INFO_MB_10:		return  "GET_PREV_DMA_INFO_MB_10";	case CX2341X_ENC_GET_PREV_DMA_INFO_MB_9:		return  "GET_PREV_DMA_INFO_MB_9";	case CX2341X_ENC_SCHED_DMA_TO_HOST:		return  "SCHED_DMA_TO_HOST";	case CX2341X_ENC_INITIALIZE_INPUT:		return  "INITIALIZE_INPUT";	case CX2341X_ENC_SET_FRAME_DROP_RATE:		return  "SET_FRAME_DROP_RATE";	case CX2341X_ENC_PAUSE_ENCODER:		return  "PAUSE_ENCODER";	case CX2341X_ENC_REFRESH_INPUT:		return  "REFRESH_INPUT";	case CX2341X_ENC_SET_COPYRIGHT:		return  "SET_COPYRIGHT";	case CX2341X_ENC_SET_EVENT_NOTIFICATION:		return  "SET_EVENT_NOTIFICATION";	case CX2341X_ENC_SET_NUM_VSYNC_LINES:		return  "SET_NUM_VSYNC_LINES";	case CX2341X_ENC_SET_PLACEHOLDER:		return  "SET_PLACEHOLDER";	case CX2341X_ENC_MUTE_VIDEO:		return  "MUTE_VIDEO";	case CX2341X_ENC_MUTE_AUDIO:		return  "MUTE_AUDIO";	case CX2341X_ENC_MISC:		return  "MISC";	default:		return "UNKNOWN";	}}static int cx23885_mbox_func(void *priv,			     u32 command,			     int in,			     int out,			     u32 data[CX2341X_MBOX_MAX_DATA]){	struct cx23885_dev *dev = priv;	unsigned long timeout;	u32 value, flag, retval = 0;	int i;	dprintk(3, "%s: command(0x%X) = %s\n", __func__, command,		cmd_to_str(command));	/* this may not be 100% safe if we can't read any memory location	   without side effects */	mc417_memory_read(dev, dev->cx23417_mailbox - 4, &value);	if (value != 0x12345678) {		printk(KERN_ERR			"Firmware and/or mailbox pointer not initialized "			"or corrupted, signature = 0x%x, cmd = %s\n", value,			cmd_to_str(command));		return -1;	}	/* This read looks at 32 bits, but flag is only 8 bits.	 * Seems we also bail if CMD or TIMEOUT bytes are set???	 */	mc417_memory_read(dev, dev->cx23417_mailbox, &flag);	if (flag) {		printk(KERN_ERR "ERROR: Mailbox appears to be in use "			"(%x), cmd = %s\n", flag, cmd_to_str(command));		return -1;	}	flag |= 1; /* tell 'em we're working on it */	mc417_memory_write(dev, dev->cx23417_mailbox, flag);	/* write command + args + fill remaining with zeros */	/* command code */	mc417_memory_write(dev, dev->cx23417_mailbox + 1, command);	mc417_memory_write(dev, dev->cx23417_mailbox + 3,		IVTV_API_STD_TIMEOUT); /* timeout */	for (i = 0; i < in; i++) {		mc417_memory_write(dev, dev->cx23417_mailbox + 4 + i, data[i]);		dprintk(3, "API Input %d = %d\n", i, data[i]);	}	for (; i < CX2341X_MBOX_MAX_DATA; i++)		mc417_memory_write(dev, dev->cx23417_mailbox + 4 + i, 0);	flag |= 3; /* tell 'em we're done writing */	mc417_memory_write(dev, dev->cx23417_mailbox, flag);	/* wait for firmware to handle the API command */	timeout = jiffies + msecs_to_jiffies(10);	for (;;) {		mc417_memory_read(dev, dev->cx23417_mailbox, &flag);		if (0 != (flag & 4))			break;		if (time_after(jiffies, timeout)) {			printk(KERN_ERR "ERROR: API Mailbox timeout\n");			return -1;		}		udelay(10);	}	/* read output values */	for (i = 0; i < out; i++) {		mc417_memory_read(dev, dev->cx23417_mailbox + 4 + i, data + i);		dprintk(3, "API Output %d = %d\n", i, data[i]);	}	mc417_memory_read(dev, dev->cx23417_mailbox + 2, &retval);	dprintk(3, "API result = %d\n", retval);	flag = 0;	mc417_memory_write(dev, dev->cx23417_mailbox, flag);	return retval;}/* We don't need to call the API often, so using just one * mailbox will probably suffice */static int cx23885_api_cmd(struct cx23885_dev *dev,			   u32 command,			   u32 inputcnt,			   u32 outputcnt,			   ...){	u32 data[CX2341X_MBOX_MAX_DATA];	va_list vargs;	int i, err;	dprintk(3, "%s() cmds = 0x%08x\n", __func__, command);	va_start(vargs, outputcnt);	for (i = 0; i < inputcnt; i++)		data[i] = va_arg(vargs, int);	err = cx23885_mbox_func(dev, command, inputcnt, outputcnt, data);	for (i = 0; i < outputcnt; i++) {		int *vptr = va_arg(vargs, int *);		*vptr = data[i];	}	va_end(vargs);	return err;}static int cx23885_find_mailbox(struct cx23885_dev *dev){	u32 signature[4] = {		0x12345678, 0x34567812, 0x56781234, 0x78123456	};	int signaturecnt = 0;	u32 value;	int i;	dprintk(2, "%s()\n", __func__);	for (i = 0; i < CX23885_FIRM_IMAGE_SIZE; i++) {		mc417_memory_read(dev, i, &value);		if (value == signature[signaturecnt])			signaturecnt++;		else			signaturecnt = 0;		if (4 == signaturecnt) {			dprintk(1, "Mailbox signature found at 0x%x\n", i+1);			return i+1;		}	}	printk(KERN_ERR "Mailbox signature values not found!\n");	return -1;}static int cx23885_load_firmware(struct cx23885_dev *dev){	static const unsigned char magic[8] = {		0xa7, 0x0d, 0x00, 0x00, 0x66, 0xbb, 0x55, 0xaa	};	const struct firmware *firmware;	int i, retval = 0;	u32 value = 0;	u32 gpio_output = 0;	u32 checksum = 0;	u32 *dataptr;	dprintk(2, "%s()\n", __func__);	/* Save GPIO settings before reset of APU */	retval |= mc417_memory_read(dev, 0x9020, &gpio_output);	retval |= mc417_memory_read(dev, 0x900C, &value);	retval  = mc417_register_write(dev,		IVTV_REG_VPU, 0xFFFFFFED);	retval |= mc417_register_write(dev,		IVTV_REG_HW_BLOCKS, IVTV_CMD_HW_BLOCKS_RST);	retval |= mc417_register_write(dev,		IVTV_REG_ENC_SDRAM_REFRESH, 0x80000800);	retval |= mc417_register_write(dev,		IVTV_REG_ENC_SDRAM_PRECHARGE, 0x1A);	retval |= mc417_register_write(dev,		IVTV_REG_APU, 0);	if (retval != 0) {		printk(KERN_ERR "%s: Error with mc417_register_write\n",			__func__);		return -1;	}	retval = request_firmware(&firmware, CX23885_FIRM_IMAGE_NAME,				  &dev->pci->dev);	if (retval != 0) {		printk(KERN_ERR			"ERROR: Hotplug firmware request failed (%s).\n",			CX2341X_FIRM_ENC_FILENAME);		printk(KERN_ERR "Please fix your hotplug setup, the board will "			"not work without firmware loaded!\n");		return -1;	}	if (firmware->size != CX23885_FIRM_IMAGE_SIZE) {		printk(KERN_ERR "ERROR: Firmware size mismatch "			"(have %zd, expected %d)\n",			firmware->size, CX23885_FIRM_IMAGE_SIZE);		release_firmware(firmware);		return -1;	}	if (0 != memcmp(firmware->data, magic, 8)) {		printk(KERN_ERR			"ERROR: Firmware magic mismatch, wrong file?\n");		release_firmware(firmware);

⌨️ 快捷键说明

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