1 /* 2 * linux/drivers/video/console/tileblit.c -- Tile Blitting Operation 3 * 4 * Copyright (C) 2004 Antonino Daplas <adaplas @pol.net> 5 * 6 * This file is subject to the terms and conditions of the GNU General Public 7 * License. See the file COPYING in the main directory of this archive for 8 * more details. 9 */ 10 11 #include <linux/module.h> 12 #include <linux/string.h> 13 #include <linux/fb.h> 14 #include <linux/vt_kern.h> 15 #include <linux/console.h> 16 #include <asm/types.h> 17 #include "fbcon.h" 18 19 static void tile_clear(struct vc_data *vc, struct fb_info *info, int sy, 20 int sx, int height, int width) 21 { 22 struct fb_tilerect rect; 23 int bgshift = (vc->vc_hi_font_mask) ? 13 : 12; 24 int fgshift = (vc->vc_hi_font_mask) ? 9 : 8; 25 26 rect.index = vc->vc_video_erase_char & 27 ((vc->vc_hi_font_mask) ? 0x1ff : 0xff); 28 rect.fg = attr_fgcol_ec(fgshift, vc, info); 29 rect.bg = attr_bgcol_ec(bgshift, vc, info); 30 rect.sx = sx; 31 rect.sy = sy; 32 rect.width = width; 33 rect.height = height; 34 rect.rop = ROP_COPY; 35 36 info->tileops->fb_tilefill(info, &rect); 37 } 38 39 static void tile_putcs(struct vc_data *vc, struct fb_info *info, 40 const unsigned short *s, int count, int yy, int xx, 41 int fg, int bg) 42 { 43 struct fb_tileblit blit; 44 unsigned short charmask = vc->vc_hi_font_mask ? 0x1ff : 0xff; 45 int size = sizeof(u32) * count, i; 46 47 blit.sx = xx; 48 blit.sy = yy; 49 blit.width = count; 50 blit.height = 1; 51 blit.fg = fg; 52 blit.bg = bg; 53 blit.length = count; 54 blit.indices = (u32 *) fb_get_buffer_offset(info, &info->pixmap, size); 55 for (i = 0; i < count; i++) 56 blit.indices[i] = (u32)(scr_readw(s++) & charmask); 57 58 info->tileops->fb_tileblit(info, &blit); 59 } 60 61 static void tile_clear_margins(struct vc_data *vc, struct fb_info *info, 62 int color, int bottom_only) 63 { 64 return; 65 } 66 67 static void tile_cursor(struct vc_data *vc, struct fb_info *info, int mode, 68 int fg, int bg) 69 { 70 struct fb_tilecursor cursor; 71 int use_sw = vc->vc_cursor_type & CUR_SW; 72 73 cursor.sx = vc->state.x; 74 cursor.sy = vc->state.y; 75 cursor.mode = (mode == CM_ERASE || use_sw) ? 0 : 1; 76 cursor.fg = fg; 77 cursor.bg = bg; 78 79 switch (vc->vc_cursor_type & 0x0f) { 80 case CUR_NONE: 81 cursor.shape = FB_TILE_CURSOR_NONE; 82 break; 83 case CUR_UNDERLINE: 84 cursor.shape = FB_TILE_CURSOR_UNDERLINE; 85 break; 86 case CUR_LOWER_THIRD: 87 cursor.shape = FB_TILE_CURSOR_LOWER_THIRD; 88 break; 89 case CUR_LOWER_HALF: 90 cursor.shape = FB_TILE_CURSOR_LOWER_HALF; 91 break; 92 case CUR_TWO_THIRDS: 93 cursor.shape = FB_TILE_CURSOR_TWO_THIRDS; 94 break; 95 case CUR_BLOCK: 96 default: 97 cursor.shape = FB_TILE_CURSOR_BLOCK; 98 break; 99 } 100 101 info->tileops->fb_tilecursor(info, &cursor); 102 } 103 104 static int tile_update_start(struct fb_info *info) 105 { 106 struct fbcon_ops *ops = info->fbcon_par; 107 int err; 108 109 err = fb_pan_display(info, &ops->var); 110 ops->var.xoffset = info->var.xoffset; 111 ops->var.yoffset = info->var.yoffset; 112 ops->var.vmode = info->var.vmode; 113 return err; 114 } 115 116 void fbcon_set_tileops(struct vc_data *vc, struct fb_info *info) 117 { 118 struct fb_tilemap map; 119 struct fbcon_ops *ops = info->fbcon_par; 120 121 ops->clear = tile_clear; 122 ops->putcs = tile_putcs; 123 ops->clear_margins = tile_clear_margins; 124 ops->cursor = tile_cursor; 125 ops->update_start = tile_update_start; 126 127 if (ops->p) { 128 map.width = vc->vc_font.width; 129 map.height = vc->vc_font.height; 130 map.depth = 1; 131 map.length = vc->vc_font.charcount; 132 map.data = ops->p->fontdata; 133 info->tileops->fb_settile(info, &map); 134 } 135 } 136