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

📄 cyberpro.c

📁 移植到2410开发板上的源代码
💻 C
📖 第 1 页 / 共 4 页
字号:
		if (w.x > dp->buf.width)			w.x = dp->buf.width;		if (w.y > dp->buf.height)			w.y = dp->buf.height;		if (w.width < dp->capt.width)			w.width = dp->capt.width;		if (w.height < dp->capt.height)			w.height = dp->capt.height;		if (w.x + w.width > dp->buf.width)			w.width = dp->buf.width - w.x;		if (w.y + w.height > dp->buf.height)			w.height = dp->buf.height - w.y;		/*		 * We've tried to make the values fit, but		 * they just won't.		 */		if (w.width < dp->capt.width || w.height < dp->capt.height)			return -EINVAL;		diff = dp->ovl->dst.x != w.x ||		       dp->ovl->dst.y != w.y ||		       dp->ovl->dst.width != w.width  ||		       dp->ovl->dst.height != w.height ||		       dp->ovl->dst.chromakey != w.chromakey ||		       dp->ovl->dst.flags != w.flags;		if (!dp->win_set || diff) {			dp->ovl->dst.x         = w.x;			dp->ovl->dst.y         = w.y;			dp->ovl->dst.width     = w.width;			dp->ovl->dst.height    = w.height;			dp->ovl->dst.chromakey = w.chromakey;			dp->ovl->dst.flags     = w.flags;			if (dp->ovl_active)				dp->ovl->ctl(dp, dp->ovl, 0);			dp->ovl->set_win(dp, dp->ovl);			if (dp->ovl_active)				dp->ovl->ctl(dp, dp->ovl, 1);			diff = w.flags & VIDEO_WINDOW_INTERLACE ? 1 : 0;			if (!dp->win_set || dp->interlace != diff) {				dp->interlace = diff;				cyberpro_set_interlace(dp);			}		}		dp->win_set = 1;		return 0;	}	case VIDIOCSFBUF:	/* set frame buffer info */	{		struct video_buffer b;		int ret;		if (!capable(CAP_SYS_ADMIN) || !capable(CAP_SYS_RAWIO))			return -EPERM;		if (dp->cap_active)			return -EINVAL;		if (copy_from_user(&b, arg, sizeof(b)))			return -EFAULT;		ret = cyberpro_set_buffer(dp, &b);		if (ret == 0) {			dp->buf_set = 1;			dp->win_set = 0;		}		return ret;	}	case VIDIOCCAPTURE:	{		int on;		if (get_user(on, (int *)arg))			return -EFAULT;		if (( on &&  dp->ovl_active) ||		    (!on && !dp->ovl_active))			return 0;		if (on && (!dp->buf_set || !dp->win_set))			return -EINVAL;		cyberpro_capture(dp, on);		dp->cap_active = on;		dp->ovl->ctl(dp, dp->ovl, on);		dp->ovl_active = on;		return 0;	}#ifdef USE_MMAP	case VIDIOCSYNC:	{		DECLARE_WAITQUEUE(wait, current);		int buf;		/*		 * The buffer must have been mmaped		 * for this call to work.		 */		if (!dp->mmaped)			return -EINVAL;		if (get_user(buf, (int *)arg))			return -EFAULT;		if (buf < 0 || buf >= NR_FRAMES)			return -EINVAL;		switch (dp->frame[buf].status) {		case FRAME_FREE:			return -EINVAL;		case FRAME_WAITING:		case FRAME_GRABBING:			add_wait_queue(&dp->frame_wait, &wait);			while (1) {				set_current_state(TASK_INTERRUPTIBLE);				if (signal_pending(current))					break;				if (dp->frame[buf].status == FRAME_DONE)					break;				schedule();			}			set_current_state(TASK_RUNNING);			remove_wait_queue(&dp->frame_wait, &wait);			if (signal_pending(current))				return -EINTR;			/*FALLTHROUGH*/		case FRAME_DONE:			dp->frame[buf].status = FRAME_FREE;			break;		}		return 0;	}	case VIDIOCMCAPTURE:	{		struct video_mmap vmap;		/*		 * The buffer must have been mmaped		 * for this call to work.		 */		if (!dp->mmaped)			return -EINVAL;		if (copy_from_user(&vmap, arg, sizeof(vmap)))			return -EFAULT;		/*		 * We can only capture in our source format/size.		 */		if (vmap.frame  >= NR_FRAMES ||		    vmap.format != dp->stream_fmt ||		    vmap.width  != dp->capt.width ||		    vmap.height != dp->capt.height)			return -EINVAL;		if (dp->frame[vmap.frame].status == FRAME_WAITING ||		    dp->frame[vmap.frame].status == FRAME_GRABBING)			return -EBUSY;		dp->frame[vmap.frame].status = FRAME_WAITING;		return 0;	}	case VIDIOCGMBUF:	{		struct video_mbuf vmb;		unsigned int i;		vmb.frames = NR_FRAMES;		vmb.size   = dp->frame_size * NR_FRAMES;		for (i = 0; i < NR_FRAMES; i++)			vmb.offsets[i] = dp->frame[i].offset;		return copy_to_user(arg, &vmb, sizeof(vmb)) ? -EFAULT : 0;	}#endif	case VIDIOCSCAPTURE:	{		struct video_capture capt;#ifndef ALLOW_SCAPTURE_WHILE_CAP		if (dp->cap_active)			return -EINVAL;#endif		if (copy_from_user(&capt, arg, sizeof(capt)))			return -EFAULT;		if (capt.x < 0 || capt.width < 0 ||		    capt.y < 0 || capt.height < 0 ||		    capt.x + capt.width > dp->cap.maxwidth ||		    capt.y + capt.height > dp->cap.maxheight)			return -EINVAL;		/*		 * The capture width must be a multiple of 4		 */		if (dp->capt.width & 3)			return -EINVAL;		dp->capt.x = capt.x;		dp->capt.y = capt.y;		dp->capt.width = capt.width;		dp->capt.height = capt.height;#ifdef ALLOW_SCAPTURE_WHILE_CAP		if (dp->ovl_active)			dp->ovl->ctl(dp, dp->ovl, 0);		if (dp->cap_active)			cyberpro_capture(dp, 0);#endif		cyberpro_capture_set_win(dp);		/*		 * Update the overlay window information		 */		dp->ovl->src.width  = capt.width;		dp->ovl->src.height = capt.height;		dp->ovl->set_src(dp, dp->ovl);		if (dp->win_set)			dp->ovl->set_win(dp, dp->ovl);#ifdef ALLOW_SCAPTURE_WHILE_CAP		if (dp->cap_active)			cyberpro_capture(dp, 1);		if (dp->ovl_active)			dp->ovl->ctl(dp, dp->ovl, 1);#endif		return 0;	}	case VIDIOCGTUNER:	/* no tuner */	case VIDIOCSTUNER:		return -EINVAL;	}	return -EINVAL;}#ifdef USE_MMAPstatic intcyberpro_grabber_mmap(struct video_device *dev, const char *addr, unsigned long size){	struct cyberpro_vidinfo *dp = dev->priv;	unsigned long vaddr = (unsigned long)addr;	pgprot_t prot;	int frame_idx, ret = -EINVAL;#if defined(__arm__)	prot = __pgprot(L_PTE_PRESENT | L_PTE_YOUNG | L_PTE_USER | L_PTE_WRITE | L_PTE_DIRTY);#elif defined(__i386__)	prot = __pgprot(_PAGE_PRESENT | _PAGE_RW | _PAGE_USER | _PAGE_ACCESSED);	if (boot_cpu_data.x86 > 3)		pgprot_val(prot) |= _PAGE_PCD;#else#error "Unsupported architecture"#endif	/*	 * The mmap() request must have the correct size.	 */	if (size != NR_FRAMES * dp->frame_size)		goto out;	/*	 * If it's already mapped, don't re-do	 */	if (dp->mmaped)		goto out;	dp->mmaped = 1;	/*	 * Map in each frame	 */	for (frame_idx = 0; frame_idx < NR_FRAMES; frame_idx++) {		struct framebuf *frame;		int pgidx;		frame = dp->frame + frame_idx;		ret = cyberpro_alloc_frame_buffer(dp, frame);		/*		 * If an error occurs, we can be lazy and leave what we've		 * been able to do.  Our release function will free any		 * allocated buffers, and do_mmap_pgoff() will zap any		 * inserted mappings.		 */		if (ret)			goto out2;		/*		 * Map in each page on a page by page basis.  This is just		 * a little on the inefficient side, but it's only run once.		 */		for (pgidx = 0; pgidx < NR_PAGES; pgidx++) {			unsigned long virt;			virt = page_address(frame->pages[pgidx]);			ret = remap_page_range(vaddr, virt_to_phys((void *)virt),					       PAGE_SIZE, prot);			if (ret)				goto out2;			vaddr += PAGE_SIZE;		}	} out2:	if (ret)		dp->mmaped = 0; out:	return ret;}#endifstatic int __init cyberpro_grabber_init_done(struct video_device *dev){	struct cyberpro_vidinfo *dp;	struct cyberpro_info *info = dev->priv;	int ret;	dp = kmalloc(sizeof(*dp), GFP_KERNEL);	if (!dp)		return -ENOMEM;	memset(dp, 0, sizeof(*dp));	dev->priv		= dp;	dp->info		= *info;	dp->dev			= dev;	dp->bus			= &cyberpro_i2c_bus;	dp->regs		= info->regs;	dp->irq			= info->dev->irq;	strcpy(dp->cap.name, dev->name);	dp->cap.type		= dev->type;	dp->cap.channels	= 1;	dp->cap.audios		= 0;	dp->cap.minwidth	= 32;	dp->cap.maxwidth	= 716;	dp->cap.minheight	= 32;	dp->cap.maxheight	= 576;	dp->pic.brightness	= 32768;	dp->pic.hue		= 32768;	dp->pic.colour		= 32768;	dp->pic.contrast	= 32768;	dp->pic.whiteness	= 0;	dp->pic.depth		= 8;	dp->pic.palette		= VIDEO_PALETTE_YUV422;	/* dp->buf is setup by the user		*/	/* dp->cap_mem_offset setup by dp->buf	*/	dp->norm		= VIDEO_MODE_AUTO;	/*	 * The extended overlay window	 */	dp->ext.init		= cyberpro_ext_init;	dp->ext.set_src		= cyberpro_ext_set_src;	dp->ext.set_win		= cyberpro_ext_set_win;	dp->ext.ctl		= cyberpro_ext_ctl;	/*	 * The V2 overlay window	 */	dp->v2.init		= cyberpro_v2_init;	dp->v2.set_src		= cyberpro_v2_set_src;	dp->v2.set_win		= cyberpro_v2_set_win;	dp->v2.ctl		= cyberpro_v2_ctl;	/*	 * The X2 overlay window	 */	dp->x2.init		= cyberpro_x2_init;	dp->x2.set_src		= cyberpro_x2_set_src;	dp->x2.set_win		= cyberpro_x2_set_win;	dp->x2.ctl		= cyberpro_x2_ctl;	/*	 * Set the overlay window which we shall be using	 */	dp->ovl = &dp->ext;	dp->cap_mode1 = EXT_CAP_MODE1_ALTFIFO;	/*	 * Initialise hardware specific values.	 *  - CCIR656 8bit mode (YUV422 data)	 *  - Ignore Hgood signal	 *  - Invert Odd/Even field signal	 */	dp->cap_mode1 |= EXT_CAP_MODE1_CCIR656 | EXT_CAP_MODE1_8BIT;	dp->cap_mode2  = EXT_CAP_MODE2_FIXSONY | EXT_CAP_MODE2_DATEND |			 EXT_CAP_MODE2_CCIRINVOE;	dp->stream_fmt = VIDEO_PALETTE_YUV422;	init_waitqueue_head(&dp->vbl_wait);	cyberpro_frames_init(dp);	/*	 * wake up the decoder	 */	decoder_sleep(0);	dp->bus->data = dp;	strncpy(dp->bus->name, dev->name, sizeof(dp->bus->name));	pci_set_master(dp->info.dev);	ret = i2c_register_bus(dp->bus);	/*	 * If we successfully registered the bus, but didn't initialise	 * the decoder (because its driver is not present), request	 * that it is loaded.	 */	if (ret == 0 && !dp->decoder)		request_module("saa7111");	/*	 * If that didn't work, then we're out of luck.	 */	if (ret == 0 && !dp->decoder) {		i2c_unregister_bus(dp->bus);		ret = -ENXIO;	}	if (ret) {		kfree(dp);		/*		 * put the decoder back to sleep		 */		decoder_sleep(1);	}	return ret;}static struct video_device cyberpro_grabber = {	name:		"",	type:		VID_TYPE_CAPTURE   | VID_TYPE_OVERLAY |			VID_TYPE_CHROMAKEY | VID_TYPE_SCALES  |			VID_TYPE_SUBCAPTURE,	hardware:	0,	open:		cyberpro_grabber_open,	close:		cyberpro_grabber_close,	read:		cyberpro_grabber_read,	write:		cyberpro_grabber_write,	ioctl:		cyberpro_grabber_ioctl,#ifdef USE_MMAP	mmap:		cyberpro_grabber_mmap,#endif	initialize:	cyberpro_grabber_init_done,};int init_cyber2000fb_viddev(void){	struct cyberpro_info info;	if (!cyber2000fb_attach(&info, 0))		return -ENXIO;	strncpy(cyberpro_grabber.name, info.dev_name, sizeof(cyberpro_grabber.name));	cyberpro_grabber.priv = &info;	return video_register_device(&cyberpro_grabber, VFL_TYPE_GRABBER, -1);}/* * This can be cleaned up when the SAA7111 code is fixed. */#ifdef MODULEstatic int __init cyberpro_init(void){	disable_irq(35);	return init_cyber2000fb_viddev();}static void __exit cyberpro_exit(void){	video_unregister_device(&cyberpro_grabber);	kfree(cyberpro_grabber.priv);	i2c_unregister_bus(&cyberpro_i2c_bus);	/*	 * put the decoder back to sleep	 */	decoder_sleep(1);	cyber2000fb_detach(0);}module_init(cyberpro_init);module_exit(cyberpro_exit);#endif

⌨️ 快捷键说明

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