Ejemplo n.º 1
0
/* new function to close fifo */
int s3cfb_close_fifo(int id, int (*do_priv)(void *), void *param, int sleep)
{
	struct s3cfb_window *win = ctrl->fb[id]->par;

	dev_dbg(ctrl->dev, "[fb%d] close fifo\n", win->id);

	if (sleep)
		win->path = DATA_PATH_FIFO;
	else
		win->path = DATA_PATH_DMA;

	s3cfb_set_vsync_interrupt(ctrl, 1);
	s3cfb_wait_for_vsync();
	s3cfb_set_vsync_interrupt(ctrl, 0);

	s3cfb_display_off(ctrl);
	s3cfb_check_line_count(ctrl);
	s3cfb_disable_window(id);

	if (do_priv) {
		if (do_priv(param)) {
			dev_err(ctrl->dev, "failed to run for private fifo close\n");
			s3cfb_enable_window(id);
			s3cfb_display_on(ctrl);
			return -EFAULT;
		}
	}

	s3cfb_display_on(ctrl);

	return 0;
}
Ejemplo n.º 2
0
/* new function to open fifo */
int s3cfb_open_fifo(int id, int ch, int (*do_priv)(void *), void *param)
{
	struct s3cfb_window *win = ctrl->fb[id]->par;

	dev_dbg(ctrl->dev, "[fb%d] open fifo\n", win->id);

	win->path = DATA_PATH_FIFO;
	win->local_channel = ch;

	s3cfb_set_vsync_interrupt(ctrl, 1);
	s3cfb_wait_for_vsync();
	s3cfb_set_vsync_interrupt(ctrl, 0);

	if (do_priv) {
		if (do_priv(param)) {
			dev_err(ctrl->dev, "failed to run for private fifo open\n");
			s3cfb_enable_window(id);
			return -EFAULT;
		}
	}

	s3cfb_set_window_control(ctrl, id);
	s3cfb_enable_window(id);

	return 0;
}
Ejemplo n.º 3
0
/* for backward compatibilities */
void s3cfb_enable_local(int id, int in_yuv, int ch)
{
	struct s3cfb_window *win = ctrl->fb[id]->par;

	win->path = DATA_PATH_FIFO;
	win->local_channel = ch;

	s3cfb_set_vsync_interrupt(ctrl, 1);
	s3cfb_wait_for_vsync();
	s3cfb_set_vsync_interrupt(ctrl, 0);

	s3cfb_set_window_control(ctrl, id);
	s3cfb_enable_window(id);
}
Ejemplo n.º 4
0
/* for backward compatibilities */
void s3cfb_enable_dma(int id)
{
	struct s3cfb_window *win = ctrl->fb[id]->par;

	win->path = DATA_PATH_DMA;

	s3cfb_set_vsync_interrupt(ctrl, 1);
	s3cfb_wait_for_vsync();
	s3cfb_set_vsync_interrupt(ctrl, 0);

	s3cfb_disable_window(id);
	s3cfb_display_off(ctrl);
	s3cfb_set_window_control(ctrl, id);
	s3cfb_display_on(ctrl);
}
Ejemplo n.º 5
0
int s3cfb_ioctl(struct fb_info *fb, unsigned int cmd, unsigned long arg)
{
	struct fb_var_screeninfo *var = &fb->var;
	struct s3cfb_window *win = fb->par;
	struct s3cfb_global *fbdev = get_fimd_global(fb->node);
	struct s3cfb_lcd *lcd = fbdev->lcd;
	int ret = 0;

	union {
		struct s3cfb_user_window user_window;
		struct s3cfb_user_plane_alpha user_alpha;
		struct s3cfb_user_chroma user_chroma;
		int vsync;
	} p;

	switch (cmd) {
	case FBIO_WAITFORVSYNC:
		s3cfb_wait_for_vsync(fbdev);
		break;

	case S3CFB_WIN_POSITION:
		if (copy_from_user(&p.user_window,
				   (struct s3cfb_user_window __user *)arg,
				   sizeof(p.user_window)))
			ret = -EFAULT;
		else {
			if (p.user_window.x < 0)
				p.user_window.x = 0;

			if (p.user_window.y < 0)
				p.user_window.y = 0;

			if (p.user_window.x + var->xres > lcd->width)
				win->x = lcd->width - var->xres;
			else
				win->x = p.user_window.x;

			if (p.user_window.y + var->yres > lcd->height)
				win->y = lcd->height - var->yres;
			else
				win->y = p.user_window.y;

			s3cfb_set_window_position(fbdev, win->id);
		}
		break;

	case S3CFB_WIN_SET_PLANE_ALPHA:
		if (copy_from_user(&p.user_alpha,
				   (struct s3cfb_user_plane_alpha __user *)arg,
				   sizeof(p.user_alpha)))
			ret = -EFAULT;
		else {
			win->alpha.mode = PLANE_BLENDING;
			win->alpha.channel = p.user_alpha.channel;
			win->alpha.value =
			    S3CFB_AVALUE(p.user_alpha.red,
					 p.user_alpha.green, p.user_alpha.blue);

			s3cfb_set_alpha_blending(fbdev, win->id);
		}
		break;

	case S3CFB_WIN_SET_CHROMA:
		if (copy_from_user(&p.user_chroma,
				   (struct s3cfb_user_chroma __user *)arg,
				   sizeof(p.user_chroma)))
			ret = -EFAULT;
		else {
			win->chroma.enabled = p.user_chroma.enabled;
			win->chroma.key = S3CFB_CHROMA(p.user_chroma.red,
						       p.user_chroma.green,
						       p.user_chroma.blue);

			s3cfb_set_chroma_key(fbdev, win->id);
		}
		break;

	case S3CFB_SET_VSYNC_INT:
		if (get_user(p.vsync, (int __user *)arg))
			ret = -EFAULT;
		else {
			if (p.vsync)
				s3cfb_set_global_interrupt(fbdev, 1);
			s3cfb_set_vsync_interrupt(fbdev, p.vsync);
		}
		break;

#if MALI_USE_UNIFIED_MEMORY_PROVIDER
	case S3CFB_GET_FB_UMP_SECURE_ID_0:
		{
			u32 __user *psecureid = (u32 __user *) arg;
			ump_secure_id secure_id;

			dev_info(fbdev->dev, "ump_dd_secure_id_get\n");
			secure_id = ump_dd_secure_id_get(ump_wrapped_buffer);
			dev_info(fbdev->dev,
				"Saving secure id 0x%x in userptr %p\n"
				, (unsigned int)secure_id, psecureid);
			dev_dbg(fbdev->dev,
				"Saving secure id 0x%x in userptr %p\n"
				, (unsigned int)secure_id, psecureid);
			return put_user((unsigned int)secure_id, psecureid);
		}
		break;
#endif
	}

	return ret;
}
Ejemplo n.º 6
0
static int s3cfb_ioctl(struct fb_info *fb, unsigned int cmd, unsigned long arg)
{
	struct s3cfb_global *fbdev =
		platform_get_drvdata(to_platform_device(fb->device));
	struct fb_var_screeninfo *var = &fb->var;
	struct s3cfb_window *win = fb->par;
	struct s3cfb_lcd *lcd = fbdev->lcd;
	struct fb_fix_screeninfo *fix = &fb->fix;
	struct s3cfb_next_info next_fb_info;

	int ret = 0;

	union {
		struct s3cfb_user_window user_window;
		struct s3cfb_user_plane_alpha user_alpha;
		struct s3cfb_user_chroma user_chroma;
		int vsync;
	} p;

	switch (cmd) {
	case FBIO_WAITFORVSYNC:
		s3cfb_wait_for_vsync(fbdev);
		break;

	// Custom IOCTL added to return the VSYNC timestamp
	case S3CFB_WAIT_FOR_VSYNC:
		ret = s3cfb_wait_for_vsync(fbdev);
		if(ret > 0) {
			u64 nsecs = ktime_to_ns(fbdev->vsync_timestamp);
			copy_to_user((void*)arg, &nsecs, sizeof(u64));
		}
		break;

	case S3CFB_WIN_POSITION:
		if (copy_from_user(&p.user_window,
				   (struct s3cfb_user_window __user *)arg,
				   sizeof(p.user_window)))
			ret = -EFAULT;
		else {
			if (p.user_window.x < 0)
				p.user_window.x = 0;

			if (p.user_window.y < 0)
				p.user_window.y = 0;

			if (p.user_window.x + var->xres > lcd->width)
				win->x = lcd->width - var->xres;
			else
				win->x = p.user_window.x;

			if (p.user_window.y + var->yres > lcd->height)
				win->y = lcd->height - var->yres;
			else
				win->y = p.user_window.y;

			s3cfb_set_window_position(fbdev, win->id);
		}
		break;

	case S3CFB_WIN_SET_PLANE_ALPHA:
		if (copy_from_user(&p.user_alpha,
				   (struct s3cfb_user_plane_alpha __user *)arg,
				   sizeof(p.user_alpha)))
			ret = -EFAULT;
		else {
			win->alpha.mode = PLANE_BLENDING;
			win->alpha.channel = p.user_alpha.channel;
			win->alpha.value =
			    S3CFB_AVALUE(p.user_alpha.red,
					 p.user_alpha.green, p.user_alpha.blue);

			s3cfb_set_alpha_blending(fbdev, win->id);
		}
		break;

	case S3CFB_WIN_SET_CHROMA:
		if (copy_from_user(&p.user_chroma,
				   (struct s3cfb_user_chroma __user *)arg,
				   sizeof(p.user_chroma)))
			ret = -EFAULT;
		else {
			win->chroma.enabled = p.user_chroma.enabled;
			win->chroma.key = S3CFB_CHROMA(p.user_chroma.red,
						       p.user_chroma.green,
						       p.user_chroma.blue);

			s3cfb_set_chroma_key(fbdev, win->id);
		}
		break;

	case S3CFB_SET_VSYNC_INT:
		if (get_user(p.vsync, (int __user *)arg))
			ret = -EFAULT;
		else {
			if (p.vsync)
				s3cfb_set_global_interrupt(fbdev, 1);

			s3cfb_set_vsync_interrupt(fbdev, p.vsync);
		}
		break;

	case S3CFB_GET_CURR_FB_INFO:
		next_fb_info.phy_start_addr = fix->smem_start;
		next_fb_info.xres = var->xres;
		next_fb_info.yres = var->yres;
		next_fb_info.xres_virtual = var->xres_virtual;
		next_fb_info.yres_virtual = var->yres_virtual;
		next_fb_info.xoffset = var->xoffset;
		next_fb_info.yoffset = var->yoffset;
		next_fb_info.lcd_offset_x = 0;
		next_fb_info.lcd_offset_y = 0;

		if (copy_to_user((void *)arg,
				 (struct s3cfb_next_info *) &next_fb_info,
				 sizeof(struct s3cfb_next_info)))
			return -EFAULT;
		break;
	}

	return ret;
}
Ejemplo n.º 7
0
static int s3cfb_ioctl(struct fb_info *fb, unsigned int cmd, unsigned long arg)
{
	struct s3cfb_global *fbdev =
		platform_get_drvdata(to_platform_device(fb->device));
	struct fb_var_screeninfo *var = &fb->var;
	struct s3cfb_window *win = fb->par;
	struct s3cfb_lcd *lcd = fbdev->lcd;
	struct fb_fix_screeninfo *fix = &fb->fix;
	struct s3cfb_next_info next_fb_info;

	volatile unsigned int * LCDControllerBase = NULL;
	int framebuffer_addr = 0;

	int ret = 0;

	union {
		struct s3cfb_user_window user_window;
		struct s3cfb_user_plane_alpha user_alpha;
		struct s3cfb_user_chroma user_chroma;
		int vsync;
	} p;

	switch (cmd) {
	case FBIO_WAITFORVSYNC:
		s3cfb_wait_for_vsync(fbdev);
		break;

	case S3CFB_WIN_POSITION:
		if (copy_from_user(&p.user_window,
				   (struct s3cfb_user_window __user *)arg,
				   sizeof(p.user_window)))
			ret = -EFAULT;
		else {
			if (p.user_window.x < 0)
				p.user_window.x = 0;

			if (p.user_window.y < 0)
				p.user_window.y = 0;

			if (p.user_window.x + var->xres > lcd->width)
				win->x = lcd->width - var->xres;
			else
				win->x = p.user_window.x;

			if (p.user_window.y + var->yres > lcd->height)
				win->y = lcd->height - var->yres;
			else
				win->y = p.user_window.y;

			s3cfb_set_window_position(fbdev, win->id);
		}
		break;

	case S3CFB_WIN_SET_PLANE_ALPHA:
		if (copy_from_user(&p.user_alpha,
				   (struct s3cfb_user_plane_alpha __user *)arg,
				   sizeof(p.user_alpha)))
			ret = -EFAULT;
		else {
			win->alpha.mode = PLANE_BLENDING;
			win->alpha.channel = p.user_alpha.channel;
			win->alpha.value =
			    S3CFB_AVALUE(p.user_alpha.red,
					 p.user_alpha.green, p.user_alpha.blue);

			s3cfb_set_alpha_blending(fbdev, win->id);
		}
		break;

	case S3CFB_WIN_SET_CHROMA:
		if (copy_from_user(&p.user_chroma,
				   (struct s3cfb_user_chroma __user *)arg,
				   sizeof(p.user_chroma)))
			ret = -EFAULT;
		else {
			win->chroma.enabled = p.user_chroma.enabled;
			win->chroma.key = S3CFB_CHROMA(p.user_chroma.red,
						       p.user_chroma.green,
						       p.user_chroma.blue);

			s3cfb_set_chroma_key(fbdev, win->id);
		}
		break;

	case S3CFB_SET_VSYNC_INT:
		if (get_user(p.vsync, (int __user *)arg))
			ret = -EFAULT;
		else {
			if (p.vsync)
				s3cfb_set_global_interrupt(fbdev, 1);

			s3cfb_set_vsync_interrupt(fbdev, p.vsync);
		}
		break;

	case S3CFB_GET_CURR_FB_INFO:
		next_fb_info.phy_start_addr = fix->smem_start;
		next_fb_info.xres = var->xres;
		next_fb_info.yres = var->yres;
		next_fb_info.xres_virtual = var->xres_virtual;
		next_fb_info.yres_virtual = var->yres_virtual;
		next_fb_info.xoffset = var->xoffset;
		next_fb_info.yoffset = var->yoffset;
		next_fb_info.lcd_offset_x = 0;
		next_fb_info.lcd_offset_y = 0;

		if (copy_to_user((void *)arg,
				 (struct s3cfb_next_info *) &next_fb_info,
				 sizeof(struct s3cfb_next_info)))
			return -EFAULT;
		break;

	/* get changing physical framebuffer address(because of double buffering) */
	case S3CFB_GET_LCD_ADDR:
		LCDControllerBase = (volatile unsigned int *)ioremap(0xf8000000,1024);
		framebuffer_addr = LCDControllerBase[0xa0/4 + (win->id)*2];
		iounmap(LCDControllerBase);

		dev_dbg(fbdev->dev, "framebuffer_addr: 0x%08x\n", framebuffer_addr);

		if (copy_to_user((void *)arg, &framebuffer_addr, sizeof(int)))
			return -EFAULT;

		break;
	}

	return ret;
}
Ejemplo n.º 8
0
int s3cfb_ioctl(struct fb_info *info, unsigned int cmd, unsigned long arg)
{
	s3cfb_info_t *fbi = container_of(info, s3cfb_info_t, fb);
	s3cfb_win_info_t win_info;
	s3cfb_color_key_info_t colkey_info;
	s3cfb_color_val_info_t colval_info;
	s3cfb_dma_info_t dma_info;
	s3cfb_next_info_t next_fb_info;
	struct fb_var_screeninfo *var= &fbi->fb.var;
	unsigned int crt, alpha_level, alpha_mode;

#if defined(CONFIG_S3C6410_PWM)
	int brightness;
#endif

#if defined(CONFIG_FB_S3C_DOUBLE_BUFFERING)
	unsigned int f_num_val;
#endif

#if defined(CONFIG_FB_S3C_VIRTUAL_SCREEN)
	s3cfb_vs_info_t vs_info;
#endif

	switch(cmd){
	case S3CFB_GET_INFO:
		dma_info.map_dma_f1 = fbi->map_dma_f1;
		dma_info.map_dma_f2 = fbi->map_dma_f2;

		if(copy_to_user((void *) arg, (const void *) &dma_info, sizeof(s3cfb_dma_info_t)))
			return -EFAULT;
		break;

	case S3CFB_OSD_SET_INFO:
		if (copy_from_user(&win_info, (s3cfb_win_info_t *) arg, sizeof(s3cfb_win_info_t)))
			return -EFAULT;

		s3cfb_init_win(fbi, win_info.bpp, win_info.left_x, win_info.top_y, win_info.width, win_info.height, OFF);
		break;

	case S3CFB_OSD_START:
		s3cfb_onoff_win(fbi, ON);
		break;

	case S3CFB_OSD_STOP:
		s3cfb_onoff_win(fbi, OFF);
		break;

	case S3CFB_OSD_ALPHA_UP:
		alpha_level = readl(S3C_VIDOSD0C + (0x10 * fbi->win_id)) & 0xf;

		if (alpha_level < S3CFB_MAX_ALPHA_LEVEL)
			alpha_level++;

		s3cfb_set_alpha_level(fbi, alpha_level, 1);
		break;

	case S3CFB_OSD_ALPHA_DOWN:
		alpha_level = readl(S3C_VIDOSD0C + (0x10 * fbi->win_id)) & 0xf;

		if (alpha_level > 0)
			alpha_level--;

		s3cfb_set_alpha_level(fbi, alpha_level, 1);
		break;

	case S3CFB_OSD_ALPHA0_SET:
		alpha_level = (unsigned int) arg;

		if (alpha_level > S3CFB_MAX_ALPHA_LEVEL)
			alpha_level = S3CFB_MAX_ALPHA_LEVEL;

		s3cfb_set_alpha_level(fbi, alpha_level, 0);
		break;

	case S3CFB_OSD_ALPHA1_SET:
		alpha_level = (unsigned int) arg;

		if (alpha_level > S3CFB_MAX_ALPHA_LEVEL)
			alpha_level = S3CFB_MAX_ALPHA_LEVEL;

		s3cfb_set_alpha_level(fbi, alpha_level, 1);
		break;

	case S3CFB_OSD_ALPHA_MODE:
		alpha_mode = (unsigned int) arg;
		s3cfb_set_alpha_mode(fbi, alpha_mode);
		break;

	case S3CFB_OSD_MOVE_LEFT:
		if (var->xoffset > 0)
			var->xoffset--;

		s3cfb_set_win_position(fbi, var->xoffset, var->yoffset, var->xres, var->yres);
		break;

	case S3CFB_OSD_MOVE_RIGHT:
		if (var->xoffset < (s3cfb_fimd.width - var->xres))
			var->xoffset++;

		s3cfb_set_win_position(fbi, var->xoffset, var->yoffset, var->xres, var->yres);
		break;

	case S3CFB_OSD_MOVE_UP:
		if (var->yoffset > 0)
			var->yoffset--;

		s3cfb_set_win_position(fbi, var->xoffset, var->yoffset, var->xres, var->yres);
		break;

	case S3CFB_OSD_MOVE_DOWN:
		if (var->yoffset < (s3cfb_fimd.height - var->yres))
			var->yoffset++;

		s3cfb_set_win_position(fbi, var->xoffset, var->yoffset, var->xres, var->yres);
		break;

	case FBIO_WAITFORVSYNC:
		if (get_user(crt, (unsigned int __user *)arg))
			return -EFAULT;

		return s3cfb_wait_for_vsync();

	case S3CFB_COLOR_KEY_START:
		s3cfb_onoff_color_key(fbi, ON);
		break;

	case S3CFB_COLOR_KEY_STOP:
		s3cfb_onoff_color_key(fbi, OFF);
		break;

	case S3CFB_COLOR_KEY_ALPHA_START:
		s3cfb_onoff_color_key_alpha(fbi, ON);
		break;

	case S3CFB_COLOR_KEY_ALPHA_STOP:
		s3cfb_onoff_color_key_alpha(fbi, OFF);
		break;

	case S3CFB_COLOR_KEY_SET_INFO:
		if (copy_from_user(&colkey_info, (s3cfb_color_key_info_t *) arg, sizeof(s3cfb_color_key_info_t)))
			return -EFAULT;

		s3cfb_set_color_key_registers(fbi, colkey_info);
		break;

	case S3CFB_COLOR_KEY_VALUE:
		if (copy_from_user(&colval_info, (s3cfb_color_val_info_t *) arg, sizeof(s3cfb_color_val_info_t)))
			return -EFAULT;

		s3cfb_set_color_value(fbi, colval_info);
		break;

	case S3CFB_SET_VSYNC_INT:
		s3cfb_fimd.vidintcon0 &= ~S3C_VIDINTCON0_FRAMESEL0_MASK;
		s3cfb_fimd.vidintcon0 |= S3C_VIDINTCON0_FRAMESEL0_VSYNC;

		if (arg)
			s3cfb_fimd.vidintcon0 |= S3C_VIDINTCON0_INTFRMEN_ENABLE;
		else
			s3cfb_fimd.vidintcon0 &= ~S3C_VIDINTCON0_INTFRMEN_ENABLE;

		writel(s3cfb_fimd.vidintcon0, S3C_VIDINTCON0);
		break;

	case S3CFB_SET_NEXT_FB_INFO:
		if (copy_from_user(&next_fb_info, (s3cfb_next_info_t *) arg, sizeof(s3cfb_next_info_t)))
			return -EFAULT;

		
		if ((next_fb_info.xres + next_fb_info.xoffset) > next_fb_info.xres_virtual ||
			(next_fb_info.yres + next_fb_info.yoffset) > next_fb_info.yres_virtual ||
			(next_fb_info.xres + next_fb_info.lcd_offset_x ) > s3cfb_fimd.width ||
			(next_fb_info.yres + next_fb_info.lcd_offset_y ) > s3cfb_fimd.height) {
			printk("Error : S3CFB_SET_NEXT_FB_INFO\n");
			return -EINVAL;
		}


		fbi->next_fb_info = next_fb_info;
		fbi->next_fb_info_change_req = 1;
		break;

	case S3CFB_GET_CURR_FB_INFO:
		next_fb_info.phy_start_addr = fbi->fb.fix.smem_start;
		next_fb_info.xres = fbi->fb.var.xres;
		next_fb_info.yres = fbi->fb.var.yres;
		next_fb_info.xres_virtual = fbi->fb.var.xres_virtual;
		next_fb_info.yres_virtual = fbi->fb.var.yres_virtual;
		next_fb_info.xoffset = fbi->fb.var.xoffset;
		next_fb_info.yoffset = fbi->fb.var.yoffset;
		next_fb_info.lcd_offset_x = fbi->lcd_offset_x;
		next_fb_info.lcd_offset_y = fbi->lcd_offset_y;

		if (copy_to_user((void *)arg, (s3cfb_next_info_t *) &next_fb_info, sizeof(s3cfb_next_info_t)))
			return -EFAULT;
		break;

	case S3CFB_GET_BRIGHTNESS:
		if (copy_to_user((void *)arg, (const void *) &s3cfb_fimd.brightness, sizeof(int)))
			return -EFAULT;
		break;

#if defined(CONFIG_S3C6410_PWM)
	case S3CFB_SET_BRIGHTNESS:
		if (copy_from_user(&brightness, (int *) arg, sizeof(int)))
			return -EFAULT;

		s3cfb_set_brightness(brightness);
		break;
#endif

#if defined(CONFIG_FB_S3C_VIRTUAL_SCREEN)
	case S3CFB_VS_START:
		s3cfb_fimd.wincon0 &= ~(S3C_WINCONx_ENWIN_F_ENABLE);
		writel(s3cfb_fimd.wincon0 | S3C_WINCONx_ENWIN_F_ENABLE, S3C_WINCON0);

		fbi->fb.var.xoffset = s3cfb_fimd.xoffset;
		fbi->fb.var.yoffset = s3cfb_fimd.yoffset;
		break;

	case S3CFB_VS_STOP:
		s3cfb_fimd.vidw00add0b0 = fbi->screen_dma_f1;
		s3cfb_fimd.vidw00add0b1 = fbi->screen_dma_f2;
		fbi->fb.var.xoffset = 0;
		fbi->fb.var.yoffset = 0;

		writel(s3cfb_fimd.vidw00add0b0, S3C_VIDW00ADD0B0);
		writel(s3cfb_fimd.vidw00add0b1, S3C_VIDW00ADD0B1);

		break;

	case S3CFB_VS_SET_INFO:
		if (copy_from_user(&vs_info, (s3cfb_vs_info_t *) arg, sizeof(s3cfb_vs_info_t)))
			return -EFAULT;

		if (s3cfb_set_vs_info(vs_info)) {
			printk("Error S3CFB_VS_SET_INFO\n");
			return -EINVAL;
		}

		s3cfb_set_vs_registers(S3CFB_VS_SET);

		fbi->fb.var.xoffset = s3cfb_fimd.xoffset;
		fbi->fb.var.yoffset = s3cfb_fimd.yoffset;
		break;

	case S3CFB_VS_MOVE:
		s3cfb_set_vs_registers(arg);

		fbi->fb.var.xoffset = s3cfb_fimd.xoffset;
		fbi->fb.var.yoffset = s3cfb_fimd.yoffset;
		break;
#endif

#if defined(CONFIG_FB_S3C_DOUBLE_BUFFERING)
	case S3CFB_GET_NUM:
		if (copy_from_user((void *)&f_num_val, (const void *)arg, sizeof(u_int)))
			return -EFAULT;

		if (copy_to_user((void *)arg, (const void *) &f_num_val, sizeof(u_int)))
			return -EFAULT;

		break;

	case S3CFB_CHANGE_REQ:
		s3cfb_change_buff(0, (int) arg);
		break;
#endif

	default:
		return -EINVAL;
	}

	return 0;
}
Ejemplo n.º 9
0
static int s3cfb_ioctl(struct fb_info *fb, unsigned int cmd,
			unsigned long arg)
{
	struct s3c_platform_fb *pdata = to_fb_plat(ctrl->dev);
	struct fb_var_screeninfo *var = &fb->var;
	struct s3cfb_window *win = fb->par, *win_temp;
	struct s3cfb_lcd *lcd = ctrl->lcd;
	int ret = 0, i;

	union {
		struct s3cfb_user_window user_window;
		struct s3cfb_user_plane_alpha user_alpha;
		struct s3cfb_user_chroma user_chroma;
		int vsync;
	} p;

	switch (cmd) {
	case FBIO_WAITFORVSYNC:
		s3cfb_wait_for_vsync();
		break;

	case S3CFB_WIN_ON:
		s3cfb_enable_window(win->id);
		break;

	case S3CFB_WIN_OFF:
		s3cfb_disable_window(win->id);
		break;

	case S3CFB_WIN_OFF_ALL:
		for (i = 0; i < pdata->nr_wins; i++) {
			win_temp = ctrl->fb[i]->par;
			s3cfb_disable_window(win_temp->id);
		}
		break;

	case S3CFB_WIN_POSITION:
		if (copy_from_user(&p.user_window,
			(struct s3cfb_user_window __user *) arg,
			sizeof(p.user_window)))
			ret = -EFAULT;
		else {
			if (p.user_window.x < 0)
				p.user_window.x = 0;

			if (p.user_window.y < 0)
				p.user_window.y = 0;

			if (p.user_window.x + var->xres > lcd->width)
				win->x = lcd->width - var->xres;
			else
				win->x = p.user_window.x;

			if (p.user_window.y + var->yres > lcd->height)
				win->y = lcd->height - var->yres;
			else
				win->y = p.user_window.y;

			s3cfb_set_window_position(ctrl, win->id);
		}
		break;

	case S3CFB_WIN_SET_PLANE_ALPHA:
		if (copy_from_user(&p.user_alpha,
			(struct s3cfb_user_plane_alpha __user *) arg,
			sizeof(p.user_alpha)))
			ret = -EFAULT;
		else {
			win->alpha.mode = PLANE_BLENDING;
			win->alpha.channel = p.user_alpha.channel;
			win->alpha.value =
				S3CFB_AVALUE(p.user_alpha.red,
					p.user_alpha.green,
					p.user_alpha.blue);

			s3cfb_set_alpha_blending(ctrl, win->id);
		}
		break;

	case S3CFB_WIN_SET_CHROMA:
		if (copy_from_user(&p.user_chroma,
			(struct s3cfb_user_chroma __user *) arg,
			sizeof(p.user_chroma)))
			ret = -EFAULT;
		else {
			win->chroma.enabled = p.user_chroma.enabled;
			win->chroma.key = S3CFB_CHROMA(p.user_chroma.red,
						p.user_chroma.green,
						p.user_chroma.blue);

			s3cfb_set_chroma_key(ctrl, win->id);
		}
		break;

	case S3CFB_SET_VSYNC_INT:
		if (get_user(p.vsync, (int __user *) arg))
			ret = -EFAULT;
		else {
			if (p.vsync)
				s3cfb_set_global_interrupt(ctrl, 1);

			s3cfb_set_vsync_interrupt(ctrl, p.vsync);
		}
		break;
	}

	return ret;
}