This source file includes following definitions.
- CURSOR_UNDRAWN
- fbcon_startup
- fbcon_init
- fbcon_deinit
- fbcon_changevar
- fbcon_setup
- mymemclear_small
- mymemclear
- mymemset
- mymemmove
- fast_memmove
- memclear_4p_col
- memset_even_4p
- memmove_4p_col
- expand4l
- expand4dl
- dup4l
- memclear_8p_col
- memset_even_8p
- memmove_8p_col
- expand8dl
- memclear_2p_col
- memset_even_2p
- memmove_2p_col
- expand2w
- expand2l
- dup2w
- real_y
- fbcon_clear
- fbcon_putc
- fbcon_putcs
- fbcon_cursor
- fbcon_vbl_handler
- fbcon_scroll
- fbcon_bmove
- fbcon_bmove_rec
- fbcon_switch
- fbcon_blank
- fbcon_get_font
- fbcon_set_font
- bmove_mono
- clear_mono
- putc_mono
- putcs_mono
- rev_char_mono
- bmove_ilbm
- clear_ilbm
- putc_ilbm
- putcs_ilbm
- rev_char_ilbm
- bmove_plan
- clear_plan
- putc_plan
- putcs_plan
- rev_char_plan
- bmove_2_plane
- clear_2_plane
- putc_2_plane
- putcs_2_plane
- rev_char_2_plane
- bmove_4_plane
- clear_4_plane
- putc_4_plane
- putcs_4_plane
- rev_char_4_plane
- bmove_8_plane
- clear_8_plane
- putc_8_plane
- putcs_8_plane
- rev_char_8_plane
- bmove_8_packed
- clear_8_packed
- putc_8_packed
- putcs_8_packed
- rev_char_8_packed
- bmove_16_packed
- clear_16_packed
- putc_16_packed
- putcs_16_packed
- rev_char_16_packed
- bmove_cyber
- clear_cyber
- putc_cyber
- putcs_cyber
- rev_char_cyber
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42 #include <linux/types.h>
43 #include <linux/fs.h>
44 #include <linux/kernel.h>
45 #include <linux/tty.h>
46 #include <linux/console.h>
47 #include <linux/string.h>
48 #include <linux/config.h>
49 #include <linux/kd.h>
50 #include <linux/malloc.h>
51
52 #include <asm/bootinfo.h>
53 #include <asm/irq.h>
54 #ifdef CONFIG_AMIGA
55 #include <asm/amigahw.h>
56 #include <asm/amigaints.h>
57 #endif
58 #ifdef CONFIG_ATARI
59 #include <asm/atariints.h>
60 #endif
61 #ifdef CONFIG_FB_CYBER
62 #include "../amiga/s3blit.h"
63 #endif
64 #include <linux/fb.h>
65 #include <asm/font.h>
66 #include <asm/machdep.h>
67
68 #include <asm/system.h>
69
70 #include "../../../drivers/char/vt_kern.h"
71
72
73
74
75 extern int console_blanked;
76
77
78
79
80
81
82
83
84
85 #undef CONFIG_FBCON_MONO
86 #undef CONFIG_FBCON_ILBM
87 #undef CONFIG_FBCON_PLANES
88 #undef CONFIG_FBCON_2PLANE
89 #undef CONFIG_FBCON_4PLANE
90 #undef CONFIG_FBCON_8PLANE
91 #undef CONFIG_FBCON_8PACKED
92 #undef CONFIG_FBCON_16PACKED
93 #undef CONFIG_FBCON_24PACKED
94 #undef CONFIG_FBCON_32PACKED
95 #undef CONFIG_FBCON_CYBER
96
97
98
99
100 #define CONFIG_FBCON_MONO
101
102
103
104 #ifdef CONFIG_AMIGA
105 #ifndef CONFIG_FBCON_ILBM
106 #define CONFIG_FBCON_ILBM
107 #endif
108 #ifndef CONFIG_FBCON_PLANES
109 #define CONFIG_FBCON_PLANES
110 #endif
111
112
113
114 #ifdef CONFIG_FB_CYBER
115 #ifndef CONFIG_FBCON_CYBER
116 #define CONFIG_FBCON_CYBER
117 #endif
118 #endif
119
120 #endif
121
122
123
124 #ifdef CONFIG_ATARI
125 #ifndef CONFIG_FBCON_2PLANE
126 #define CONFIG_FBCON_2PLANE
127 #endif
128 #ifndef CONFIG_FBCON_4PLANE
129 #define CONFIG_FBCON_4PLANE
130 #endif
131 #ifndef CONFIG_FBCON_8PLANE
132 #define CONFIG_FBCON_8PLANE
133 #endif
134 #ifndef CONFIG_FBCON_8PACKED
135 #define CONFIG_FBCON_8PACKED
136 #endif
137 #ifndef CONFIG_FBCON_16PACKED
138 #define CONFIG_FBCON_16PACKED
139 #endif
140 #endif
141
142
143
144
145 #if defined(CONFIG_FBCON_2PLANE) || defined(CONFIG_FBCON_4PLANE) || \
146 defined(CONFIG_FBCON_8PLANE)
147 #define CONFIG_FBCON_IPLAN2
148 #else
149 #undef CONFIG_FBCON_IPLAN2
150 #endif
151
152 #if defined(CONFIG_FBCON_CYBER) || defined(CONFIG_FBCON_8PACKED) || \
153 defined(CONFIG_FBCON_16PACKED) || defined(CONFIG_FBCON_24PACKED) || \
154 defined(CONFIG_FBCON_32PACKED)
155 #define CONFIG_FBCON_PACKED
156 #else
157 #undef CONFIG_FBCON_PACKED
158 #endif
159
160
161 struct fb_info *fb_info;
162 struct display *disp;
163
164
165
166
167
168 static int cursor_drawn = 0;
169
170 #define CURSOR_DRAW_DELAY (2)
171
172
173 #define AMIGA_CURSOR_BLINK_RATE (20)
174 #define ATARI_CURSOR_BLINK_RATE (42)
175
176 static int vbl_cursor_cnt = 0;
177 static int cursor_on = 0;
178 static int cursor_blink_rate;
179
180 static __inline__ int CURSOR_UNDRAWN(void)
181 {
182 int cursor_was_drawn;
183 vbl_cursor_cnt = 0;
184 cursor_was_drawn = cursor_drawn;
185 cursor_drawn = 0;
186 return(cursor_was_drawn);
187 }
188
189
190
191
192
193
194 #define attr_fgcol(p,conp) \
195 (((conp)->vc_attr >> ((p)->inverse ? 4 : 0)) & 0x0f)
196 #define attr_bgcol(p,conp) \
197 (((conp)->vc_attr >> ((p)->inverse ? 0 : 4)) & 0x0f)
198 #define attr_bgcol_ec(p,conp) \
199 (((conp)->vc_video_erase_char >> ((p)->inverse ? 8 : 12)) & 0x0f)
200
201
202 #define attr_bold(p,conp) \
203 (((conp)->vc_attr & 3) == 2)
204 #define attr_reverse(p,conp) \
205 (((conp)->vc_attr & 8) ^ ((p)->inverse ? 8 : 0))
206 #define attr_underline(p,conp) \
207 (((conp)->vc_attr) & 4)
208
209
210
211
212
213
214 #define SCROLL_YWRAP (0)
215 #define SCROLL_YPAN (1)
216 #define SCROLL_YMOVE (2)
217
218 #define divides(a, b) ((!(a) || (b)%(a)) ? 0 : 1)
219
220
221
222
223
224
225 static u_long fbcon_startup(u_long kmem_start, char **display_desc);
226 static void fbcon_init(struct vc_data *conp);
227 static int fbcon_deinit(struct vc_data *conp);
228 static int fbcon_changevar(int con);
229 static int fbcon_clear(struct vc_data *conp, int sy, int sx, int height,
230 int width);
231 static int fbcon_putc(struct vc_data *conp, int c, int y, int x);
232 static int fbcon_putcs(struct vc_data *conp, const char *s, int count, int y,
233 int x);
234 static int fbcon_cursor(struct vc_data *conp, int mode);
235 static int fbcon_scroll(struct vc_data *conp, int t, int b, int dir, int count);
236 static int fbcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
237 int height, int width);
238 static int fbcon_switch(struct vc_data *conp);
239 static int fbcon_blank(int blank);
240
241
242
243
244
245
246 static void fbcon_setup(int con, int setcol, int cls);
247 static __inline__ void *mymemclear_small(void *s, size_t count);
248 static __inline__ void *mymemclear(void *s, size_t count);
249 static __inline__ void *mymemset(void *s, size_t count);
250 static __inline__ void *mymemmove(void *d, void *s, size_t count);
251 static __inline__ void fast_memmove(char *dst, char *src, size_t size);
252 static __inline__ void memclear_4p_col(void *d, size_t h, u_long val, int bpr);
253 static __inline__ void memset_even_4p(void *d, size_t count, u_long val1,
254 u_long val2);
255 static __inline__ void memmove_4p_col(void *d, void *s, int h, int bpr);
256 static __inline__ u_long expand4l(u_char c);
257 static __inline__ void expand4dl(u_char c, u_long *ret1, u_long *ret2);
258 static __inline__ u_long dup4l(u_char c);
259 static __inline__ void memclear_8p_col(void *d, size_t h, u_long val1,
260 u_long val2, int bpr);
261 static __inline__ void memset_even_8p(void *d, size_t count, u_long val1,
262 u_long val2, u_long val3, u_long val4);
263 static __inline__ void memmove_8p_col(void *d, void *s, int h, int bpr);
264 static __inline__ void expand8dl(u_char c, u_long *ret1, u_long *ret2);
265 static __inline__ void memclear_2p_col(void *d, size_t h, u_short val, int bpr);
266 static __inline__ void memset_even_2p(void *d, size_t count, u_long val);
267 static __inline__ void memmove_2p_col(void *d, void *s, int h, int bpr);
268 static __inline__ u_short expand2w(u_char c);
269 static __inline__ u_long expand2l(u_char c);
270 static __inline__ u_short dup2w(u_char c);
271 static __inline__ int real_y(struct display *p, int y);
272 static void fbcon_vbl_handler(int irq, struct pt_regs *fp, void *dummy);
273 static void fbcon_bmove_rec(struct display *p, int sy, int sx, int dy, int dx,
274 int height, int width, u_int y_break);
275
276
277
278
279
280
281 #ifdef CONFIG_FBCON_MONO
282 static void bmove_mono(struct display *p, int sy, int sx, int dy, int dx,
283 int height, int width);
284 static void clear_mono(struct vc_data *conp, struct display *p, int sy, int sx,
285 int height, int width);
286 static void putc_mono(struct vc_data *conp, struct display *p, int c, int y,
287 int x);
288 static void putcs_mono(struct vc_data *conp, struct display *p, const char *s,
289 int count, int y, int x);
290 static void rev_char_mono(struct display *p, int x, int y);
291 #endif
292
293
294
295
296
297
298 #ifdef CONFIG_FBCON_ILBM
299 static void bmove_ilbm(struct display *p, int sy, int sx, int dy, int dx,
300 int height, int width);
301 static void clear_ilbm(struct vc_data *conp, struct display *p, int sy, int sx,
302 int height, int width);
303 static void putc_ilbm(struct vc_data *conp, struct display *p, int c, int y,
304 int x);
305 static void putcs_ilbm(struct vc_data *conp, struct display *p, const char *s,
306 int count, int y, int x);
307 static void rev_char_ilbm(struct display *p, int x, int y);
308 #endif
309
310
311
312
313
314
315 #ifdef CONFIG_FBCON_PLANES
316 static void bmove_plan(struct display *p, int sy, int sx, int dy, int dx,
317 int height, int width);
318 static void clear_plan(struct vc_data *conp, struct display *p, int sy, int sx,
319 int height, int width);
320 static void putc_plan(struct vc_data *conp, struct display *p, int c, int y,
321 int x);
322 static void putcs_plan(struct vc_data *conp, struct display *p, const char *s,
323 int count, int y, int x);
324 static void rev_char_plan(struct display *p, int x, int y);
325 #endif
326
327
328
329
330
331
332 #ifdef CONFIG_FBCON_2PLANE
333 static void bmove_2_plane(struct display *p, int sy, int sx, int dy, int dx,
334 int height, int width);
335 static void clear_2_plane(struct vc_data *conp, struct display *p, int sy,
336 int sx, int height, int width);
337 static void putc_2_plane(struct vc_data *conp, struct display *p, int c, int y,
338 int x);
339 static void putcs_2_plane(struct vc_data *conp, struct display *p,
340 const char *s, int count, int y, int x);
341 static void rev_char_2_plane(struct display *display, int x, int y);
342 #endif
343
344
345
346
347
348
349 #ifdef CONFIG_FBCON_4PLANE
350 static void bmove_4_plane(struct display *p, int sy, int sx, int dy, int dx,
351 int height, int width);
352 static void clear_4_plane(struct vc_data *conp, struct display *p, int sy,
353 int sx, int height, int width);
354 static void putc_4_plane(struct vc_data *conp, struct display *p, int c, int y,
355 int x);
356 static void putcs_4_plane(struct vc_data *conp, struct display *p,
357 const char *s, int count, int y, int x);
358 static void rev_char_4_plane(struct display *p, int x, int y);
359 #endif
360
361
362
363
364
365
366 #ifdef CONFIG_FBCON_8PLANE
367 static void bmove_8_plane(struct display *p, int sy, int sx, int dy, int dx,
368 int height, int width);
369 static void clear_8_plane(struct vc_data *conp, struct display *p, int sy,
370 int sx, int height, int width);
371 static void putc_8_plane(struct vc_data *conp, struct display *p, int c, int y,
372 int x);
373 static void putcs_8_plane(struct vc_data *conp, struct display *p,
374 const char *s, int count, int y, int x);
375 static void rev_char_8_plane(struct display *display, int x, int y);
376 #endif
377
378
379
380
381
382
383 #ifdef CONFIG_FBCON_8PACKED
384 static void bmove_8_packed(struct display *p, int sy, int sx, int dy, int dx,
385 int height, int width);
386 static void clear_8_packed(struct vc_data *conp, struct display *p, int sy,
387 int sx, int height, int width);
388 static void putc_8_packed(struct vc_data *conp, struct display *p, int c, int y,
389 int x);
390 static void putcs_8_packed(struct vc_data *conp, struct display *p,
391 const char *s, int count, int y, int x);
392 static void rev_char_8_packed(struct display *p, int x, int y);
393 #endif
394
395
396
397
398
399
400 #ifdef CONFIG_FBCON_16PACKED
401 static void bmove_16_packed(struct display *p, int sy, int sx, int dy, int dx,
402 int height, int width);
403 static void clear_16_packed(struct vc_data *conp, struct display *p, int sy,
404 int sx, int height, int width);
405 static void putc_16_packed(struct vc_data *conp, struct display *p, int c,
406 int y, int x);
407 static void putcs_16_packed(struct vc_data *conp, struct display *p,
408 const char *s, int count, int y, int x);
409 static void rev_char_16_packed(struct display *p, int x, int y);
410 #endif */ CONFIG_FBCON_8PACKED */
411
412
413
414
415
416
417 #ifdef CONFIG_FBCON_CYBER
418 static void bmove_cyber(struct display *p, int sy, int sx, int dy, int dx,
419 int height, int width);
420 static void clear_cyber(struct vc_data *conp, struct display *p, int sy, int sx,
421 int height, int width);
422 static void putc_cyber(struct vc_data *conp, struct display *p, int c, int y,
423 int x);
424 static void putcs_cyber(struct vc_data *conp, struct display *p, const char *s,
425 int count, int y, int x);
426 static void rev_char_cyber(struct display *p, int x, int y);
427
428 extern void Cyber_WaitQueue(u_short fifo);
429 extern void Cyber_WaitBlit(void);
430 extern void Cyber_BitBLT(u_short curx, u_short cury, u_short destx,
431 u_short desty, u_short width, u_short height,
432 u_short mode);
433 extern void Cyber_RectFill(u_short x, u_short y, u_short width, u_short height,
434 u_short mode, u_short color);
435 extern void Cyber_MoveCursor(u_short x, u_short y);
436 #endif
437
438
439
440
441
442
443 struct display_switch {
444 void (*bmove)(struct display *p, int sy, int sx, int dy, int dx, int height,
445 int width);
446 void (*clear)(struct vc_data *conp, struct display *p, int sy, int sx,
447 int height, int width);
448 void (*putc)(struct vc_data *conp, struct display *p, int c, int y, int x);
449 void (*putcs)(struct vc_data *conp, struct display *p, const char *s,
450 int count, int y, int x);
451 void (*rev_char)(struct display *p, int x, int y);
452 };
453
454
455 #ifdef CONFIG_FBCON_MONO
456 struct display_switch dispsw_mono = {
457 bmove_mono, clear_mono, putc_mono, putcs_mono, rev_char_mono
458 };
459 #endif
460
461 #ifdef CONFIG_FBCON_ILBM
462 struct display_switch dispsw_ilbm = {
463 bmove_ilbm, clear_ilbm, putc_ilbm, putcs_ilbm, rev_char_ilbm
464 };
465 #endif
466
467 #ifdef CONFIG_FBCON_PLANES
468 struct display_switch dispsw_plan = {
469 bmove_plan, clear_plan, putc_plan, putcs_plan, rev_char_plan
470 };
471 #endif
472
473 #ifdef CONFIG_FBCON_2PLANE
474 struct display_switch dispsw_2_plane = {
475 bmove_2_plane, clear_2_plane, putc_2_plane, putcs_2_plane, rev_char_2_plane
476 };
477 #endif
478
479 #ifdef CONFIG_FBCON_4PLANE
480 struct display_switch dispsw_4_plane = {
481 bmove_4_plane, clear_4_plane, putc_4_plane, putcs_4_plane, rev_char_4_plane
482 };
483 #endif
484
485 #ifdef CONFIG_FBCON_8PLANE
486 struct display_switch dispsw_8_plane = {
487 bmove_8_plane, clear_8_plane, putc_8_plane, putcs_8_plane, rev_char_8_plane
488 };
489 #endif
490
491 #ifdef CONFIG_FBCON_8PACKED
492 struct display_switch dispsw_8_packed = {
493 bmove_8_packed, clear_8_packed, putc_8_packed, putcs_8_packed, rev_char_8_packed
494 };
495 #endif
496
497 #ifdef CONFIG_FBCON_16PACKED
498 struct display_switch dispsw_16_packed = {
499 bmove_16_packed, clear_16_packed, putc_16_packed, putcs_16_packed,
500 rev_char_16_packed
501 };
502 #endif
503
504 #ifdef CONFIG_FBCON_CYBER
505 struct display_switch dispsw_cyber = {
506 bmove_cyber, clear_cyber, putc_cyber, putcs_cyber, rev_char_cyber
507 };
508 #endif
509
510
511 static u_long fbcon_startup(u_long kmem_start, char **display_desc)
512 {
513 int irqres = 0;
514
515 fb_info = mach_fb_init(&kmem_start);
516 disp = fb_info->disp;
517 *display_desc = fb_info->modename;
518 fb_info->changevar = &fbcon_changevar;
519
520 #ifdef CONFIG_AMIGA
521 if (MACH_IS_AMIGA) {
522 cursor_blink_rate = AMIGA_CURSOR_BLINK_RATE;
523 irqres = add_isr(IRQ_AMIGA_VERTB, fbcon_vbl_handler, 0, NULL,
524 "console/cursor");
525 }
526 #endif
527 #ifdef CONFIG_ATARI
528 if (MACH_IS_ATARI) {
529 cursor_blink_rate = ATARI_CURSOR_BLINK_RATE;
530 irqres = add_isr(IRQ_AUTO_4, fbcon_vbl_handler, IRQ_TYPE_PRIO, NULL,
531 "console/cursor");
532 }
533 #endif
534
535 if (!irqres)
536 panic("fbcon_startup: Couldn't add vblank interrupt");
537
538 return(kmem_start);
539 }
540
541
542 static void fbcon_init(struct vc_data *conp)
543 {
544 int unit = conp->vc_num;
545
546 if (unit)
547 disp[unit] = disp[0];
548 disp[unit].conp = conp;
549 fbcon_setup(unit, 1, 0);
550 }
551
552
553 static int fbcon_deinit(struct vc_data *conp)
554 {
555 disp[conp->vc_num].conp = 0;
556 return(0);
557 }
558
559
560 static int fbcon_changevar(int con)
561 {
562 fbcon_setup(con, 1, 1);
563 return(0);
564 }
565
566
567 static void fbcon_setup(int con, int setcol, int cls)
568 {
569 struct display *p = &disp[con];
570 struct vc_data *conp = p->conp;
571
572 p->var.xoffset = p->var.yoffset = p->yscroll = 0;
573
574 if (!fb_info->fontname[0] ||
575 !findsoftfont(fb_info->fontname, &p->fontwidth, &p->fontheight,
576 &p->fontdata) || p->fontwidth != 8)
577 getdefaultfont(p->var.xres, p->var.yres, NULL, &p->fontwidth,
578 &p->fontheight, &p->fontdata);
579 if (p->fontwidth != 8)
580 panic("fbcon_setup: No support for fontwidth != 8");
581
582 if (divides(p->ywrapstep, p->fontheight) && divides(p->fontheight, p->var.yres_virtual))
583 p->scrollmode = SCROLL_YWRAP;
584 else if (divides(p->ypanstep, p->fontheight) &&
585 p->var.yres_virtual >= p->var.yres+p->fontheight)
586 p->scrollmode = SCROLL_YPAN;
587 else
588 p->scrollmode = SCROLL_YMOVE;
589
590 conp->vc_cols = p->var.xres/p->fontwidth;
591 conp->vc_rows = p->var.yres/p->fontheight;
592 p->vrows = p->var.yres_virtual/p->fontheight;
593 conp->vc_can_do_color = p->var.bits_per_pixel != 1;
594
595 #ifdef CONFIG_FBCON_MONO
596 if (p->var.bits_per_pixel == 1) {
597 if (p->line_length)
598 p->next_line = p->line_length;
599 else
600 p->next_line = p->var.xres_virtual>>3;
601 p->next_plane = 0;
602 p->dispsw = &dispsw_mono;
603 } else
604 #endif
605 #ifdef CONFIG_FBCON_IPLAN2
606 if (p->type == FB_TYPE_INTERLEAVED_PLANES && p->type_aux == 2) {
607 p->next_line = p->var.xres_virtual*p->var.bits_per_pixel>>3;
608 p->next_plane = 0;
609 #ifdef CONFIG_FBCON_2PLANE
610 if (p->var.bits_per_pixel == 2)
611 p->dispsw = &dispsw_2_plane;
612 else
613 #endif
614 #ifdef CONFIG_FBCON_4PLANE
615 if (p->var.bits_per_pixel == 4)
616 p->dispsw = &dispsw_4_plane;
617 else
618 #endif
619 #ifdef CONFIG_FBCON_8PLANE
620 if (p->var.bits_per_pixel == 8)
621 p->dispsw = &dispsw_8_plane;
622 else
623 #endif
624 goto fail;
625 } else
626 #endif
627 #ifdef CONFIG_FBCON_ILBM
628 if (p->type == FB_TYPE_INTERLEAVED_PLANES && p->type_aux != 2) {
629 if (p->line_length) {
630 p->next_line = p->line_length*p->var.bits_per_pixel;
631 p->next_plane = p->line_length;
632 } else {
633 p->next_line = p->type_aux;
634 p->next_plane = p->type_aux/p->var.bits_per_pixel;
635 }
636 p->dispsw = &dispsw_ilbm;
637 } else
638 #endif
639 #ifdef CONFIG_FBCON_PLANES
640 if (p->type == FB_TYPE_PLANES) {
641 if (p->line_length)
642 p->next_line = p->line_length;
643 else
644 p->next_line = p->var.xres_virtual>>3;
645 p->next_plane = p->var.yres_virtual*p->next_line;
646 p->dispsw = &dispsw_plan;
647 } else
648 #endif
649 #ifdef CONFIG_FBCON_PACKED
650 if (p->type == FB_TYPE_PACKED_PIXELS) {
651 p->next_line = p->var.xres_virtual*p->var.bits_per_pixel>>3;
652 p->next_plane = 0;
653 #ifdef CONFIG_FBCON_CYBER
654 if (p->var.accel == FB_ACCEL_CYBERVISION)
655 p->dispsw = &dispsw_cyber;
656 else
657 #endif
658 #ifdef CONFIG_FBCON_8PACKED
659 if (p->var.bits_per_pixel == 8)
660 p->dispsw = &dispsw_8_packed;
661 else
662 #endif
663 #ifdef CONFIG_FBCON_16PACKED
664 if (p->var.bits_per_pixel == 16)
665 p->dispsw = &dispsw_16_packed;
666 else
667 #endif
668 #ifdef CONFIG_FBCON_24PACKED
669 if (p->var.bits_per_pixel == 24)
670 p->dispsw = &dispsw_24_packed;
671 else
672 #endif
673 #ifdef CONFIG_FBCON_32PACKED
674 if (p->var.bits_per_pixel == 32)
675 p->dispsw = &dispsw_32_packed;
676 else
677 #endif
678 goto fail;
679 } else
680 #endif
681 {
682 fail:
683 #ifdef CONFIG_FBCON_MONO
684 printk("fbcon_setup: type %d (aux %d) not supported, trying mono\n",
685 p->type, p->type_aux);
686 if (p->line_length)
687 p->next_line = p->line_length;
688 else
689 p->next_line = p->var.xres_virtual>>3;
690 p->next_plane = 0;
691 p->var.bits_per_pixel = 1;
692 p->dispsw = &dispsw_mono;
693 #else
694 panic("fbcon_setup: no default driver");
695 #endif
696 }
697
698 if (setcol) {
699 p->fgcol = p->var.bits_per_pixel > 2 ? 7 : (1<<p->var.bits_per_pixel)-1;
700 p->bgcol = 0;
701 }
702
703 if (cls)
704 vc_resize_con(conp->vc_rows, conp->vc_cols, con);
705 }
706
707
708
709
710
711
712
713
714
715
716
717
718
719
720
721
722
723
724
725
726
727
728
729
730
731
732
733
734
735
736
737
738
739
740
741
742
743
744
745
746
747
748
749
750
751
752
753 static __inline__ void *mymemclear_small(void *s, size_t count)
754 {
755 if (!count)
756 return(0);
757
758 __asm__ __volatile__(
759 "lsrl #1,%1 ; jcc 1f ; moveb %2,%0@-\n\t"
760 "1: lsrl #1,%1 ; jcc 1f ; movew %2,%0@-\n\t"
761 "1: lsrl #1,%1 ; jcc 1f ; movel %2,%0@-\n\t"
762 "1: lsrl #1,%1 ; jcc 1f ; movel %2,%0@- ; movel %2,%0@-\n\t"
763 "1: subql #1,%1 ; jcs 3f\n\t"
764 "2: moveml %2/%3/%4/%5,%0@-\n\t"
765 "dbra %1,2b\n\t"
766 "3:"
767 : "=a" (s), "=d" (count)
768 : "d" (0), "d" (0), "d" (0), "d" (0),
769 "0" ((char *)s+count), "1" (count)
770 );
771
772 return(0);
773 }
774
775
776 static __inline__ void *mymemclear(void *s, size_t count)
777 {
778 if (!count)
779 return(0);
780
781 if (count < 16) {
782 __asm__ __volatile__(
783 "lsrl #1,%1 ; jcc 1f ; clrb %0@+\n\t"
784 "1: lsrl #1,%1 ; jcc 1f ; clrw %0@+\n\t"
785 "1: lsrl #1,%1 ; jcc 1f ; clrl %0@+\n\t"
786 "1: lsrl #1,%1 ; jcc 1f ; clrl %0@+ ; clrl %0@+\n\t"
787 "1:"
788 : "=a" (s), "=d" (count)
789 : "0" (s), "1" (count)
790 );
791 } else {
792 long tmp;
793 __asm__ __volatile__(
794 "movel %1,%2\n\t"
795 "lsrl #1,%2 ; jcc 1f ; clrb %0@+ ; subqw #1,%1\n\t"
796 "lsrl #1,%2 ; jcs 2f\n\t"
797 "clrw %0@+ ; subqw #2,%1 ; jra 2f\n\t"
798 "1: lsrl #1,%2 ; jcc 2f\n\t"
799 "clrw %0@+ ; subqw #2,%1\n\t"
800 "2: movew %1,%2; lsrl #2,%1 ; jeq 6f\n\t"
801 "lsrl #1,%1 ; jcc 3f ; clrl %0@+\n\t"
802 "3: lsrl #1,%1 ; jcc 4f ; clrl %0@+ ; clrl %0@+\n\t"
803 "4: subql #1,%1 ; jcs 6f\n\t"
804 "5: clrl %0@+; clrl %0@+ ; clrl %0@+ ; clrl %0@+\n\t"
805 "dbra %1,5b ; clrw %1; subql #1,%1; jcc 5b\n\t"
806 "6: movew %2,%1; btst #1,%1 ; jeq 7f ; clrw %0@+\n\t"
807 "7: ; btst #0,%1 ; jeq 8f ; clrb %0@+\n\t"
808 "8:"
809 : "=a" (s), "=d" (count), "=d" (tmp)
810 : "0" (s), "1" (count)
811 );
812 }
813
814 return(0);
815 }
816
817
818 static __inline__ void *mymemset(void *s, size_t count)
819 {
820 if (!count)
821 return(0);
822
823 __asm__ __volatile__(
824 "lsrl #1,%1 ; jcc 1f ; moveb %2,%0@-\n\t"
825 "1: lsrl #1,%1 ; jcc 1f ; movew %2,%0@-\n\t"
826 "1: lsrl #1,%1 ; jcc 1f ; movel %2,%0@-\n\t"
827 "1: lsrl #1,%1 ; jcc 1f ; movel %2,%0@- ; movel %2,%0@-\n\t"
828 "1: subql #1,%1 ; jcs 3f\n\t"
829 "2: moveml %2/%3/%4/%5,%0@-\n\t"
830 "dbra %1,2b\n\t"
831 "3:"
832 : "=a" (s), "=d" (count)
833 : "d" (-1), "d" (-1), "d" (-1), "d" (-1),
834 "0" ((char *) s + count), "1" (count)
835 );
836
837 return(0);
838 }
839
840
841 static __inline__ void *mymemmove(void *d, void *s, size_t count)
842 {
843 if (d < s) {
844 if (count < 16) {
845 __asm__ __volatile__(
846 "lsrl #1,%2 ; jcc 1f ; moveb %1@+,%0@+\n\t"
847 "1: lsrl #1,%2 ; jcc 1f ; movew %1@+,%0@+\n\t"
848 "1: lsrl #1,%2 ; jcc 1f ; movel %1@+,%0@+\n\t"
849 "1: lsrl #1,%2 ; jcc 1f ; movel %1@+,%0@+ ; movel %1@+,%0@+\n\t"
850 "1:"
851 : "=a" (d), "=a" (s), "=d" (count)
852 : "0" (d), "1" (s), "2" (count)
853 );
854 } else {
855 long tmp;
856 __asm__ __volatile__(
857 "movel %0,%3\n\t"
858 "lsrl #1,%3 ; jcc 1f ; moveb %1@+,%0@+ ; subqw #1,%2\n\t"
859 "lsrl #1,%3 ; jcs 2f\n\t"
860 "movew %1@+,%0@+ ; subqw #2,%2 ; jra 2f\n\t"
861 "1: lsrl #1,%3 ; jcc 2f\n\t"
862 "movew %1@+,%0@+ ; subqw #2,%2\n\t"
863 "2: movew %2,%-; lsrl #2,%2 ; jeq 6f\n\t"
864 "lsrl #1,%2 ; jcc 3f ; movel %1@+,%0@+\n\t"
865 "3: lsrl #1,%2 ; jcc 4f ; movel %1@+,%0@+ ; movel %1@+,%0@+\n\t"
866 "4: subql #1,%2 ; jcs 6f\n\t"
867 "5: movel %1@+,%0@+;movel %1@+,%0@+\n\t"
868 "movel %1@+,%0@+;movel %1@+,%0@+\n\t"
869 "dbra %2,5b ; clrw %2; subql #1,%2; jcc 5b\n\t"
870 "6: movew %+,%2; btst #1,%2 ; jeq 7f ; movew %1@+,%0@+\n\t"
871 "7: ; btst #0,%2 ; jeq 8f ; moveb %1@+,%0@+\n\t"
872 "8:"
873 : "=a" (d), "=a" (s), "=d" (count), "=d" (tmp)
874 : "0" (d), "1" (s), "2" (count)
875 );
876 }
877 } else {
878 if (count < 16) {
879 __asm__ __volatile__(
880 "lsrl #1,%2 ; jcc 1f ; moveb %1@-,%0@-\n\t"
881 "1: lsrl #1,%2 ; jcc 1f ; movew %1@-,%0@-\n\t"
882 "1: lsrl #1,%2 ; jcc 1f ; movel %1@-,%0@-\n\t"
883 "1: lsrl #1,%2 ; jcc 1f ; movel %1@-,%0@- ; movel %1@-,%0@-\n\t"
884 "1:"
885 : "=a" (d), "=a" (s), "=d" (count)
886 : "0" ((char *) d + count), "1" ((char *) s + count), "2" (count)
887 );
888 } else {
889 long tmp;
890 __asm__ __volatile__(
891 "movel %0,%3\n\t"
892 "lsrl #1,%3 ; jcc 1f ; moveb %1@-,%0@- ; subqw #1,%2\n\t"
893 "lsrl #1,%3 ; jcs 2f\n\t"
894 "movew %1@-,%0@- ; subqw #2,%2 ; jra 2f\n\t"
895 "1: lsrl #1,%3 ; jcc 2f\n\t"
896 "movew %1@-,%0@- ; subqw #2,%2\n\t"
897 "2: movew %2,%-; lsrl #2,%2 ; jeq 6f\n\t"
898 "lsrl #1,%2 ; jcc 3f ; movel %1@-,%0@-\n\t"
899 "3: lsrl #1,%2 ; jcc 4f ; movel %1@-,%0@- ; movel %1@-,%0@-\n\t"
900 "4: subql #1,%2 ; jcs 6f\n\t"
901 "5: movel %1@-,%0@-;movel %1@-,%0@-\n\t"
902 "movel %1@-,%0@-;movel %1@-,%0@-\n\t"
903 "dbra %2,5b ; clrw %2; subql #1,%2; jcc 5b\n\t"
904 "6: movew %+,%2; btst #1,%2 ; jeq 7f ; movew %1@-,%0@-\n\t"
905 "7: ; btst #0,%2 ; jeq 8f ; moveb %1@-,%0@-\n\t"
906 "8:"
907 : "=a" (d), "=a" (s), "=d" (count), "=d" (tmp)
908 : "0" ((char *) d + count), "1" ((char *) s + count), "2" (count)
909 );
910 }
911 }
912
913 return(0);
914 }
915
916
917
918
919 static __inline__ void fast_memmove(char *dst, char *src, size_t size)
920 {
921 if (!size)
922 return;
923 if (dst < src)
924 __asm__ __volatile__
925 ("1:"
926 " moveml %0@+,%/d0/%/d1/%/a0/%/a1\n"
927 " moveml %/d0/%/d1/%/a0/%/a1,%1@\n"
928 " addql #8,%1; addql #8,%1\n"
929 " dbra %2,1b\n"
930 " clrw %2; subql #1,%2\n"
931 " jcc 1b"
932 : "=a" (src), "=a" (dst), "=d" (size)
933 : "0" (src), "1" (dst), "2" (size / 16 - 1)
934 : "d0", "d1", "a0", "a1", "memory");
935 else
936 __asm__ __volatile__
937 ("1:"
938 " subql #8,%0; subql #8,%0\n"
939 " moveml %0@,%/d0/%/d1/%/a0/%/a1\n"
940 " moveml %/d0/%/d1/%/a0/%/a1,%1@-\n"
941 " dbra %2,1b\n"
942 " clrw %2; subql #1,%2\n"
943 " jcc 1b"
944 : "=a" (src), "=a" (dst), "=d" (size)
945 : "0" (src + size), "1" (dst + size), "2" (size / 16 - 1)
946 : "d0", "d1", "a0", "a1", "memory");
947 }
948
949
950
951
952
953
954
955
956
957
958
959
960
961 static __inline__ void memclear_4p_col(void *d, size_t h, u_long val, int bpr)
962 {
963 __asm__ __volatile__
964 ("1: movepl %4,%0@(0)\n\t"
965 "addal %5,%0\n\t"
966 "dbra %1,1b"
967 : "=a" (d), "=d" (h)
968 : "0" (d), "1" (h - 1), "d" (val), "r" (bpr)
969 );
970 }
971
972
973
974
975
976
977
978
979
980
981
982
983 static __inline__ void memset_even_4p(void *d, size_t count, u_long val1,
984 u_long val2)
985 {
986 u_long *dd = d;
987
988 count /= 8;
989 while (count--)
990 {
991 *dd++ = val1;
992 *dd++ = val2;
993 }
994 }
995
996
997
998 static __inline__ void memmove_4p_col (void *d, void *s, int h, int bpr)
999 {
1000 u_char *dd = d, *ss = s;
1001
1002 while (h--)
1003 {
1004 dd[0] = ss[0];
1005 dd[2] = ss[2];
1006 dd[4] = ss[4];
1007 dd[6] = ss[6];
1008 dd += bpr;
1009 ss += bpr;
1010 }
1011 }
1012
1013
1014
1015
1016 static __inline__ u_long expand4l(u_char c)
1017 {
1018 u_long rv;
1019
1020 __asm__ __volatile__
1021 ("lsrb #1,%2\n\t"
1022 "scs %0\n\t"
1023 "lsll #8,%0\n\t"
1024 "lsrb #1,%2\n\t"
1025 "scs %0\n\t"
1026 "lsll #8,%0\n\t"
1027 "lsrb #1,%2\n\t"
1028 "scs %0\n\t"
1029 "lsll #8,%0\n\t"
1030 "lsrb #1,%2\n\t"
1031 "scs %0\n\t"
1032 : "=&d" (rv), "=d" (c)
1033 : "1" (c)
1034 );
1035 return(rv);
1036 }
1037
1038
1039
1040
1041
1042 static __inline__ void expand4dl(u_char c, u_long *ret1, u_long *ret2)
1043 {
1044 u_long rv1, rv2;
1045
1046 __asm__ __volatile__
1047 ("lsrb #1,%3\n\t"
1048 "scs %0\n\t"
1049 "extw %0\n\t"
1050 "swap %0\n\t"
1051 "lsrb #1,%3\n\t"
1052 "scs %0\n\t"
1053 "extw %0\n\t"
1054 "lsrb #1,%3\n\t"
1055 "scs %1\n\t"
1056 "extw %1\n\t"
1057 "swap %1\n\t"
1058 "lsrb #1,%3\n\t"
1059 "scs %1\n\t"
1060 "extw %1"
1061 : "=&d" (rv1), "=&d" (rv2), "=d" (c)
1062 : "2" (c)
1063 );
1064 *ret1 = rv1;
1065 *ret2 = rv2;
1066 }
1067
1068
1069
1070
1071 static __inline__ u_long dup4l(u_char c)
1072 {
1073 ushort tmp;
1074 ulong rv;
1075
1076 __asm__ __volatile__
1077 ("moveb %2,%0\n\t"
1078 "lslw #8,%0\n\t"
1079 "moveb %2,%0\n\t"
1080 "movew %0,%1\n\t"
1081 "swap %0\n\t"
1082 "movew %1,%0"
1083 : "=&d" (rv), "=d" (tmp)
1084 : "d" (c)
1085 );
1086
1087 return(rv);
1088 }
1089
1090
1091
1092
1093
1094
1095
1096
1097
1098
1099
1100
1101
1102
1103
1104
1105
1106 static __inline__ void memclear_8p_col(void *d, size_t h, u_long val1,
1107 u_long val2, int bpr)
1108 {
1109 __asm__ __volatile__
1110 ("1: movepl %4,%0@(0)\n\t"
1111 "movepl %5,%0@(8)\n\t"
1112 "addal %6,%0\n\t"
1113 "dbra %1,1b"
1114 : "=a" (d), "=d" (h)
1115 : "0" (d), "1" (h - 1), "d" (val1), "d" (val2), "r" (bpr)
1116 );
1117 }
1118
1119
1120
1121
1122
1123
1124
1125
1126
1127
1128
1129
1130
1131
1132
1133
1134 static __inline__ void memset_even_8p(void *d, size_t count, u_long val1,
1135 u_long val2, u_long val3, u_long val4)
1136 {
1137 u_long *dd = d;
1138
1139 count /= 16;
1140 while (count--)
1141 {
1142 *dd++ = val1;
1143 *dd++ = val2;
1144 *dd++ = val3;
1145 *dd++ = val4;
1146 }
1147 }
1148
1149
1150
1151 static __inline__ void memmove_8p_col (void *d, void *s, int h, int bpr)
1152 {
1153 u_char *dd = d, *ss = s;
1154
1155 while (h--)
1156 {
1157 dd[0] = ss[0];
1158 dd[2] = ss[2];
1159 dd[4] = ss[4];
1160 dd[6] = ss[6];
1161 dd[8] = ss[8];
1162 dd[10] = ss[10];
1163 dd[12] = ss[12];
1164 dd[14] = ss[14];
1165 dd += bpr;
1166 ss += bpr;
1167 }
1168 }
1169
1170
1171
1172
1173
1174
1175 static __inline__ void expand8dl(u_char c, u_long *ret1, u_long *ret2)
1176 {
1177 u_long rv1, rv2;
1178
1179 __asm__ __volatile__
1180 ("lsrb #1,%3\n\t"
1181 "scs %0\n\t"
1182 "lsll #8,%0\n\t"
1183 "lsrb #1,%3\n\t"
1184 "scs %0\n\t"
1185 "lsll #8,%0\n\t"
1186 "lsrb #1,%3\n\t"
1187 "scs %0\n\t"
1188 "lsll #8,%0\n\t"
1189 "lsrb #1,%3\n\t"
1190 "scs %0\n\t"
1191 "lsrb #1,%3\n\t"
1192 "scs %1\n\t"
1193 "lsll #8,%1\n\t"
1194 "lsrb #1,%3\n\t"
1195 "scs %1\n\t"
1196 "lsll #8,%1\n\t"
1197 "lsrb #1,%3\n\t"
1198 "scs %1\n\t"
1199 "lsll #8,%1\n\t"
1200 "lsrb #1,%3\n\t"
1201 "scs %1"
1202 : "=&d" (rv1), "=&d" (rv2),"=d" (c)
1203 : "2" (c)
1204 );
1205
1206 *ret1 = rv1;
1207 *ret2 = rv2;
1208 }
1209
1210
1211
1212
1213
1214
1215 #define expand8ql(c, rv1, rv2, rv3, rv4) \
1216 do { u_char tmp = c; \
1217 __asm__ __volatile__ \
1218 ("lsrb #1,%5\n\t" \
1219 "scs %0\n\t" \
1220 "extw %0\n\t" \
1221 "swap %0\n\t" \
1222 "lsrb #1,%5\n\t" \
1223 "scs %0\n\t" \
1224 "extw %0\n\t" \
1225 "lsrb #1,%5\n\t" \
1226 "scs %1\n\t" \
1227 "extw %1\n\t" \
1228 "swap %1\n\t" \
1229 "lsrb #1,%5\n\t" \
1230 "scs %1\n\t" \
1231 "extw %1\n\t" \
1232 "lsrb #1,%5\n\t" \
1233 "scs %2\n\t" \
1234 "extw %2\n\t" \
1235 "swap %2\n\t" \
1236 "lsrb #1,%5\n\t" \
1237 "scs %2\n\t" \
1238 "extw %2\n\t" \
1239 "lsrb #1,%5\n\t" \
1240 "scs %3\n\t" \
1241 "extw %3\n\t" \
1242 "swap %3\n\t" \
1243 "lsrb #1,%5\n\t" \
1244 "scs %3\n\t" \
1245 "extw %3" \
1246 : "=&d" (rv1), "=&d" (rv2), "=&d" (rv3), \
1247 "=&d" (rv4), "=d" (tmp) \
1248 : "4" (tmp) \
1249 ); \
1250 } while (0)
1251
1252
1253
1254
1255
1256
1257
1258
1259
1260
1261
1262 static __inline__ void memclear_2p_col(void *d, size_t h, u_short val, int bpr)
1263 {
1264 __asm__ __volatile__
1265 ("1: movepw %4,%0@(0)\n\t"
1266 "addal %5,%0\n\t"
1267 "dbra %1,1b"
1268 : "=a" (d), "=d" (h)
1269 : "0" (d), "1" (h - 1), "d" (val), "r" (bpr)
1270 );
1271 }
1272
1273
1274
1275
1276
1277
1278
1279
1280
1281
1282 static __inline__ void memset_even_2p(void *d, size_t count, u_long val)
1283 {
1284 u_long *dd = d;
1285
1286 count /= 4;
1287 while (count--)
1288 *dd++ = val;
1289 }
1290
1291
1292
1293 static __inline__ void memmove_2p_col (void *d, void *s, int h, int bpr)
1294 {
1295 u_char *dd = d, *ss = s;
1296
1297 while (h--)
1298 {
1299 dd[0] = ss[0];
1300 dd[2] = ss[2];
1301 dd += bpr;
1302 ss += bpr;
1303 }
1304 }
1305
1306
1307
1308
1309 static __inline__ u_short expand2w(u_char c)
1310 {
1311 u_short rv;
1312
1313 __asm__ __volatile__
1314 ("lsrb #1,%2\n\t"
1315 "scs %0\n\t"
1316 "lsll #8,%0\n\t"
1317 "lsrb #1,%2\n\t"
1318 "scs %0\n\t"
1319 : "=&d" (rv), "=d" (c)
1320 : "1" (c)
1321 );
1322 return(rv);
1323 }
1324
1325
1326
1327
1328
1329 static __inline__ u_long expand2l(u_char c)
1330 {
1331 u_long rv;
1332
1333 __asm__ __volatile__
1334 ("lsrb #1,%2\n\t"
1335 "scs %0\n\t"
1336 "extw %0\n\t"
1337 "swap %0\n\t"
1338 "lsrb #1,%2\n\t"
1339 "scs %0\n\t"
1340 "extw %0\n\t"
1341 : "=&d" (rv), "=d" (c)
1342 : "1" (c)
1343 );
1344
1345 return rv;
1346 }
1347
1348
1349
1350
1351 static __inline__ u_short dup2w(u_char c)
1352 {
1353 ushort rv;
1354
1355 __asm__ __volatile__
1356 ( "moveb %1,%0\n\t"
1357 "lslw #8,%0\n\t"
1358 "moveb %1,%0\n\t"
1359 : "=&d" (rv)
1360 : "d" (c)
1361 );
1362
1363 return( rv );
1364 }
1365
1366
1367
1368
1369
1370
1371
1372
1373
1374
1375
1376
1377
1378
1379
1380
1381
1382
1383
1384
1385
1386
1387
1388
1389
1390
1391
1392 static __inline__ int real_y(struct display *p, int y)
1393 {
1394 int rows = p->vrows;
1395
1396 y += p->yscroll;
1397 return(y < rows ? y : y-rows);
1398 }
1399
1400
1401 static int fbcon_clear(struct vc_data *conp, int sy, int sx, int height,
1402 int width)
1403 {
1404 int unit = conp->vc_num;
1405 struct display *p = &disp[unit];
1406 u_int y_break;
1407
1408 if (!p->can_soft_blank && console_blanked)
1409 return(0);
1410
1411 if ((sy <= p->cursor_y) && (p->cursor_y < sy+height) &&
1412 (sx <= p->cursor_x) && (p->cursor_x < sx+width))
1413 CURSOR_UNDRAWN();
1414
1415
1416
1417 y_break = p->vrows-p->yscroll;
1418 if (sy < y_break && sy+height-1 >= y_break) {
1419 u_int b = y_break-sy;
1420 p->dispsw->clear(conp, p, real_y(p, sy), sx, b, width);
1421 p->dispsw->clear(conp, p, real_y(p, sy+b), sx, height-b, width);
1422 } else
1423 p->dispsw->clear(conp, p, real_y(p, sy), sx, height, width);
1424
1425 return(0);
1426 }
1427
1428
1429 static int fbcon_putc(struct vc_data *conp, int c, int y, int x)
1430 {
1431 int unit = conp->vc_num;
1432 struct display *p = &disp[unit];
1433
1434 if (!p->can_soft_blank && console_blanked)
1435 return(0);
1436
1437 if ((p->cursor_x == x) && (p->cursor_y == y))
1438 CURSOR_UNDRAWN();
1439
1440 p->dispsw->putc(conp, p, c, real_y(p, y), x);
1441
1442 return(0);
1443 }
1444
1445
1446 static int fbcon_putcs(struct vc_data *conp, const char *s, int count, int y,
1447 int x)
1448 {
1449 int unit = conp->vc_num;
1450 struct display *p = &disp[unit];
1451
1452 if (!p->can_soft_blank && console_blanked)
1453 return(0);
1454
1455 if ((p->cursor_y == y) && (x <= p->cursor_x) && (p->cursor_x < x+count))
1456 CURSOR_UNDRAWN();
1457
1458 p->dispsw->putcs(conp, p, s, count, real_y(p, y), x);
1459
1460 return(0);
1461 }
1462
1463
1464 static int fbcon_cursor(struct vc_data *conp, int mode)
1465 {
1466 int unit = conp->vc_num;
1467 struct display *p = &disp[unit];
1468
1469 if (CURSOR_UNDRAWN ())
1470 p->dispsw->rev_char(p, p->cursor_x, real_y(p, p->cursor_y));
1471 p->cursor_x = conp->vc_x;
1472 p->cursor_y = conp->vc_y;
1473
1474 switch (mode) {
1475 case CM_ERASE:
1476 cursor_on = 0;
1477 break;
1478
1479 case CM_MOVE:
1480 case CM_DRAW:
1481 vbl_cursor_cnt = CURSOR_DRAW_DELAY;
1482 cursor_on = 1;
1483 break;
1484 }
1485
1486 return(0);
1487 }
1488
1489
1490 static void fbcon_vbl_handler(int irq, struct pt_regs *fp, void *dummy)
1491 {
1492 struct display *p;
1493
1494 if (!cursor_on)
1495 return;
1496
1497 if (vbl_cursor_cnt && --vbl_cursor_cnt == 0) {
1498
1499
1500
1501 p = &disp[fg_console];
1502 p->dispsw->rev_char(p, p->cursor_x, real_y(p, p->cursor_y));
1503 cursor_drawn ^= 1;
1504 vbl_cursor_cnt = cursor_blink_rate;
1505 }
1506 }
1507
1508
1509 static int fbcon_scroll(struct vc_data *conp, int t, int b, int dir, int count)
1510 {
1511 int unit = conp->vc_num;
1512 struct display *p = &disp[unit];
1513
1514 if (!p->can_soft_blank && console_blanked)
1515 return(0);
1516
1517 fbcon_cursor(conp, CM_ERASE);
1518
1519
1520
1521
1522
1523 switch (dir) {
1524 case SM_UP:
1525 if (t == 0 && b == conp->vc_rows &&
1526 vt_cons[unit]->vc_mode == KD_TEXT) {
1527 if (count > conp->vc_rows)
1528 count = conp->vc_rows;
1529 switch (p->scrollmode) {
1530 case SCROLL_YWRAP:
1531 p->yscroll += count;
1532 if (p->yscroll >= p->vrows)
1533 p->yscroll -= p->vrows;
1534 p->var.xoffset = 0;
1535 p->var.yoffset = p->yscroll*p->fontheight;
1536 p->var.vmode |= FB_VMODE_YWRAP;
1537 fb_info->updatevar(unit);
1538 break;
1539
1540 case SCROLL_YPAN:
1541 p->yscroll += count;
1542 if (p->yscroll+conp->vc_rows > p->vrows) {
1543 p->dispsw->bmove(p, p->yscroll, 0, 0, 0, b-count,
1544 conp->vc_cols);
1545 p->yscroll = 0;
1546 }
1547 p->var.xoffset = 0;
1548 p->var.yoffset = p->yscroll*p->fontheight;
1549 p->var.vmode &= ~FB_VMODE_YWRAP;
1550 fb_info->updatevar(unit);
1551 break;
1552
1553 case SCROLL_YMOVE:
1554 p->dispsw->bmove(p, count, 0, 0, 0, b-count, conp->vc_cols);
1555 break;
1556 }
1557 } else
1558 fbcon_bmove(conp, t+count, 0, t, 0, b-t-count, conp->vc_cols);
1559 fbcon_clear(conp, b-count, 0, count, conp->vc_cols);
1560 break;
1561
1562 case SM_DOWN:
1563 if (t == 0 && b == conp->vc_rows &&
1564 vt_cons[unit]->vc_mode == KD_TEXT) {
1565 if (count > conp->vc_rows)
1566 count = conp->vc_rows;
1567 switch (p->scrollmode) {
1568 case SCROLL_YWRAP:
1569 p->yscroll -= count;
1570 if (p->yscroll < 0)
1571 p->yscroll += p->vrows;
1572 p->var.xoffset = 0;
1573 p->var.yoffset = p->yscroll*p->fontheight;
1574 p->var.vmode |= FB_VMODE_YWRAP;
1575 fb_info->updatevar(unit);
1576 break;
1577
1578 case SCROLL_YPAN:
1579 p->yscroll -= count;
1580 if (p->yscroll < 0) {
1581 p->yscroll = p->vrows-conp->vc_rows;
1582 p->dispsw->bmove(p, 0, 0, p->yscroll+count, 0, b-count,
1583 conp->vc_cols);
1584 }
1585 p->var.xoffset = 0;
1586 p->var.yoffset = p->yscroll*p->fontheight;
1587 p->var.vmode &= ~FB_VMODE_YWRAP;
1588 fb_info->updatevar(unit);
1589 break;
1590
1591 case SCROLL_YMOVE:
1592 p->dispsw->bmove(p, 0, 0, count, 0, b-count, conp->vc_cols);
1593 break;
1594 }
1595 } else
1596 fbcon_bmove(conp, t, 0, t+count, 0, b-t-count, conp->vc_cols);
1597
1598
1599
1600
1601
1602 fbcon_clear(conp, t, 0, count, conp->vc_cols);
1603 break;
1604
1605 case SM_LEFT:
1606 fbcon_bmove(conp, 0, t+count, 0, t, conp->vc_rows, b-t-count);
1607 fbcon_clear(conp, 0, b-count, conp->vc_rows, count);
1608 break;
1609
1610 case SM_RIGHT:
1611 fbcon_bmove(conp, 0, t, 0, t+count, conp->vc_rows, b-t-count);
1612 fbcon_clear(conp, 0, t, conp->vc_rows, count);
1613 break;
1614 }
1615
1616 return(0);
1617 }
1618
1619
1620 static int fbcon_bmove(struct vc_data *conp, int sy, int sx, int dy, int dx,
1621 int height, int width)
1622 {
1623 int unit = conp->vc_num;
1624 struct display *p = &disp[unit];
1625
1626 if (!p->can_soft_blank && console_blanked)
1627 return(0);
1628
1629 if (((sy <= p->cursor_y) && (p->cursor_y < sy+height) &&
1630 (sx <= p->cursor_x) && (p->cursor_x < sx+width)) ||
1631 ((dy <= p->cursor_y) && (p->cursor_y < dy+height) &&
1632 (dx <= p->cursor_x) && (p->cursor_x < dx+width)))
1633 fbcon_cursor(conp, CM_ERASE);
1634
1635
1636
1637
1638
1639
1640
1641
1642 fbcon_bmove_rec(p, sy, sx, dy, dx, height, width, p->vrows-p->yscroll);
1643
1644 return(0);
1645 }
1646
1647
1648 static void fbcon_bmove_rec(struct display *p, int sy, int sx, int dy, int dx,
1649 int height, int width, u_int y_break)
1650 {
1651 u_int b;
1652
1653 if (sy < y_break && sy+height > y_break) {
1654 b = y_break-sy;
1655 if (dy < sy) {
1656 fbcon_bmove_rec(p, sy, sx, dy, dx, b, width, y_break);
1657 fbcon_bmove_rec(p, sy+b, sx, dy+b, dx, height-b, width, y_break);
1658 } else {
1659 fbcon_bmove_rec(p, sy+b, sx, dy+b, dx, height-b, width, y_break);
1660 fbcon_bmove_rec(p, sy, sx, dy, dx, b, width, y_break);
1661 }
1662 return;
1663 }
1664
1665 if (dy < y_break && dy+height > y_break) {
1666 b = y_break-dy;
1667 if (dy < sy) {
1668 fbcon_bmove_rec(p, sy, sx, dy, dx, b, width, y_break);
1669 fbcon_bmove_rec(p, sy+b, sx, dy+b, dx, height-b, width, y_break);
1670 } else {
1671 fbcon_bmove_rec(p, sy+b, sx, dy+b, dx, height-b, width, y_break);
1672 fbcon_bmove_rec(p, sy, sx, dy, dx, b, width, y_break);
1673 }
1674 return;
1675 }
1676 p->dispsw->bmove(p, real_y(p, sy), sx, real_y(p, dy), dx, height, width);
1677 }
1678
1679
1680 static int fbcon_switch(struct vc_data *conp)
1681 {
1682 if (fb_info && fb_info->switch_con)
1683 (*fb_info->switch_con)(conp->vc_num);
1684 return(0);
1685 }
1686
1687
1688 static int fbcon_blank(int blank)
1689 {
1690 struct display *p = &disp[fg_console];
1691
1692 fbcon_cursor(p->conp, blank ? CM_ERASE : CM_DRAW);
1693
1694 if (!p->can_soft_blank)
1695 if (blank) {
1696 if (p->visual == FB_VISUAL_MONO01)
1697 mymemset(p->screen_base, p->var.xres_virtual*p->var.yres_virtual*
1698 p->var.bits_per_pixel>>3);
1699 else
1700 mymemclear(p->screen_base, p->var.xres_virtual*p->var.yres_virtual*
1701 p->var.bits_per_pixel>>3);
1702 return(0);
1703 } else {
1704
1705 return(1);
1706 }
1707 (*fb_info->blank)(blank);
1708 return(0);
1709 }
1710
1711
1712 static int fbcon_get_font(struct vc_data *conp, int *w, int *h, char *data)
1713 {
1714 int unit = conp->vc_num;
1715 struct display *p = &disp[unit];
1716 int i, size, alloc;
1717
1718 size = (p->fontwidth+7)/8 * p->fontheight * 256;
1719 alloc = (*w+7)/8 * *h * 256;
1720 *w = p->fontwidth;
1721 *h = p->fontheight;
1722
1723 if (alloc < size)
1724
1725 return( -ENAMETOOLONG );
1726
1727 if ((i = verify_area( VERIFY_WRITE, (void *)data, size )))
1728 return i;
1729
1730 memcpy_tofs( data, p->fontdata, size );
1731 return( 0 );
1732 }
1733
1734
1735 #define REFCOUNT(fd) (((int *)(fd))[-1])
1736
1737 static int fbcon_set_font(struct vc_data *conp, int w, int h, char *data)
1738 {
1739 int unit = conp->vc_num;
1740 struct display *p = &disp[unit];
1741 int i, size, userspace = 1, resize;
1742 char *old_data = NULL, *new_data;
1743
1744 if (w < 0)
1745 w = p->fontwidth;
1746 if (h < 0)
1747 h = p->fontheight;
1748
1749 if (w == 0) {
1750
1751 char name[MAX_FONT_NAME+1];
1752
1753 if ((i = verify_area( VERIFY_READ, (void *)data, MAX_FONT_NAME )))
1754 return i;
1755 memcpy_fromfs( name, data, MAX_FONT_NAME );
1756 name[sizeof(name)-1] = 0;
1757
1758 if (!findsoftfont( name, &w, &h, (u_char **)&data ))
1759 return( -ENOENT );
1760 userspace = 0;
1761 }
1762 else if (w == 1) {
1763
1764 struct display *op;
1765
1766 if (h < 0 || !vc_cons_allocated( h ))
1767 return( -ENOTTY );
1768 if (h == unit)
1769 return( 0 );
1770 op = &disp[h];
1771 if (op->fontdata == p->fontdata)
1772 return( 0 );
1773
1774 resize = (op->fontwidth != p->fontwidth) ||
1775 (op->fontheight != p->fontheight);
1776 if (p->userfont)
1777 old_data = p->fontdata;
1778 p->fontdata = op->fontdata;
1779 w = p->fontwidth = op->fontwidth;
1780 h = p->fontheight = op->fontheight;
1781 if ((p->userfont = op->userfont))
1782 REFCOUNT(p->fontdata)++;
1783 goto activate;
1784 }
1785
1786 if (w != 8)
1787
1788 return( -ENXIO );
1789
1790 resize = (w != p->fontwidth) || (h != p->fontheight);
1791 size = (w+7)/8 * h * 256;
1792
1793 if (p->userfont)
1794 old_data = p->fontdata;
1795
1796 if (userspace) {
1797 if ((i = verify_area( VERIFY_READ, (void *)data, size )))
1798 return i;
1799 if (!(new_data = kmalloc( sizeof(int)+size, GFP_USER )))
1800 return( -ENOMEM );
1801 new_data += sizeof(int);
1802 REFCOUNT(new_data) = 1;
1803 memcpy_fromfs( new_data, data, size );
1804 p->fontdata = new_data;
1805 p->userfont = 1;
1806 }
1807 else {
1808 p->fontdata = data;
1809 p->userfont = 0;
1810 }
1811 p->fontwidth = w;
1812 p->fontheight = h;
1813
1814 activate:
1815 if (resize) {
1816 p->var.xoffset = p->var.yoffset = p->yscroll = 0;
1817 if (divides(p->ywrapstep, p->fontheight))
1818 p->scrollmode = SCROLL_YWRAP;
1819 else if (divides(p->ypanstep, p->fontheight) &&
1820 p->var.yres_virtual >= p->var.yres+p->fontheight)
1821 p->scrollmode = SCROLL_YPAN;
1822 else
1823 p->scrollmode = SCROLL_YMOVE;
1824
1825 vc_resize_con( p->var.yres/h, p->var.xres/w, unit );
1826 }
1827 else if (unit == fg_console)
1828 update_screen( unit );
1829
1830 if (old_data) {
1831 if (--REFCOUNT(old_data) == 0) {
1832 kfree( old_data - sizeof(int) );
1833 }
1834 }
1835
1836 return( 0 );
1837 }
1838
1839
1840
1841
1842
1843
1844
1845
1846
1847
1848
1849
1850
1851
1852
1853
1854
1855 #ifdef CONFIG_FBCON_MONO
1856
1857
1858
1859
1860
1861 static void bmove_mono(struct display *p, int sy, int sx, int dy, int dx,
1862 int height, int width)
1863 {
1864 u_char *src, *dest;
1865 u_int rows;
1866
1867 if (sx == 0 && sy == 0 && width == p->next_line) {
1868 src = p->screen_base;
1869 dest = p->screen_base+dy*p->fontheight*width;
1870 mymemmove(dest, src, height*p->fontheight*width);
1871 } else if (dy <= sy) {
1872 src = p->screen_base+sy*p->fontheight*p->next_line+sx;
1873 dest = p->screen_base+dy*p->fontheight*p->next_line+dx;
1874 for (rows = height*p->fontheight; rows--;) {
1875 mymemmove(dest, src, width);
1876 src += p->next_line;
1877 dest += p->next_line;
1878 }
1879 } else {
1880 src = p->screen_base+((sy+height)*p->fontheight-1)*p->next_line+sx;
1881 dest = p->screen_base+((dy+height)*p->fontheight-1)*p->next_line+dx;
1882 for (rows = height*p->fontheight; rows--;) {
1883 mymemmove(dest, src, width);
1884 src -= p->next_line;
1885 dest -= p->next_line;
1886 }
1887 }
1888 }
1889
1890
1891 static void clear_mono(struct vc_data *conp, struct display *p, int sy, int sx,
1892 int height, int width)
1893 {
1894 u_char *dest;
1895 u_int rows;
1896
1897 dest = p->screen_base+sy*p->fontheight*p->next_line+sx;
1898
1899 if (sx == 0 && width == p->next_line)
1900 if (attr_reverse(p,conp))
1901 mymemset(dest, height*p->fontheight*width);
1902 else
1903 mymemclear(dest, height*p->fontheight*width);
1904 else
1905 for (rows = height*p->fontheight; rows--; dest += p->next_line)
1906 if (attr_reverse(p,conp))
1907 mymemset(dest, width);
1908 else
1909 mymemclear_small(dest, width);
1910 }
1911
1912
1913 static void putc_mono(struct vc_data *conp, struct display *p, int c, int y,
1914 int x)
1915 {
1916 u_char *dest, *cdat;
1917 u_int rows, bold, reverse, underline;
1918 u_char d;
1919
1920 c &= 0xff;
1921
1922 dest = p->screen_base+y*p->fontheight*p->next_line+x;
1923 cdat = p->fontdata+c*p->fontheight;
1924 bold = attr_bold(p,conp);
1925 reverse = attr_reverse(p,conp);
1926 underline = attr_underline(p,conp);
1927
1928 for (rows = p->fontheight; rows--; dest += p->next_line) {
1929 d = *cdat++;
1930 if (underline && !rows)
1931 d = 0xff;
1932 else if (bold)
1933 d |= d>>1;
1934 if (reverse)
1935 d = ~d;
1936 *dest = d;
1937 }
1938 }
1939
1940
1941 static void putcs_mono(struct vc_data *conp, struct display *p, const char *s,
1942 int count, int y, int x)
1943 {
1944 u_char *dest, *dest0, *cdat;
1945 u_int rows, bold, reverse, underline;
1946 u_char c, d;
1947
1948 dest0 = p->screen_base+y*p->fontheight*p->next_line+x;
1949 bold = attr_bold(p,conp);
1950 reverse = attr_reverse(p,conp);
1951 underline = attr_underline(p,conp);
1952
1953 while (count--) {
1954 c = *s++;
1955 dest = dest0++;
1956 cdat = p->fontdata+c*p->fontheight;
1957 for (rows = p->fontheight; rows--; dest += p->next_line) {
1958 d = *cdat++;
1959 if (underline && !rows)
1960 d = 0xff;
1961 else if (bold)
1962 d |= d>>1;
1963 if (reverse)
1964 d = ~d;
1965 *dest = d;
1966 }
1967 }
1968 }
1969
1970
1971 static void rev_char_mono(struct display *p, int x, int y)
1972 {
1973 u_char *dest;
1974 u_int rows;
1975
1976 dest = p->screen_base+y*p->fontheight*p->next_line+x;
1977 for (rows = p->fontheight; rows--; dest += p->next_line)
1978 *dest = ~*dest;
1979 }
1980
1981 #endif
1982
1983
1984
1985
1986 #ifdef CONFIG_FBCON_ILBM
1987
1988
1989
1990
1991
1992
1993
1994
1995
1996
1997
1998
1999 static void bmove_ilbm(struct display *p, int sy, int sx, int dy, int dx,
2000 int height, int width)
2001 {
2002 if (sx == 0 && sy == 0 && width == p->next_plane)
2003 mymemmove(p->screen_base+dy*p->fontheight*p->next_line, p->screen_base,
2004 height*p->fontheight*p->next_line);
2005 else {
2006 u_char *src, *dest;
2007 u_int i;
2008
2009 if (dy <= sy) {
2010 src = p->screen_base+sy*p->fontheight*p->next_line+sx;
2011 dest = p->screen_base+dy*p->fontheight*p->next_line+dx;
2012 for (i = p->var.bits_per_pixel*height*p->fontheight; i--;) {
2013 mymemmove(dest, src, width);
2014 src += p->next_plane;
2015 dest += p->next_plane;
2016 }
2017 } else {
2018 src = p->screen_base+(sy+height)*p->fontheight*p->next_line+sx;
2019 dest = p->screen_base+(dy+height)*p->fontheight*p->next_line+dx;
2020 for (i = p->var.bits_per_pixel*height*p->fontheight; i--;) {
2021 src -= p->next_plane;
2022 dest -= p->next_plane;
2023 mymemmove(dest, src, width);
2024 }
2025 }
2026 }
2027 }
2028
2029
2030 static void clear_ilbm(struct vc_data *conp, struct display *p, int sy, int sx,
2031 int height, int width)
2032 {
2033 u_char *dest;
2034 u_int i, rows;
2035 int bg, bg0;
2036
2037 dest = p->screen_base+sy*p->fontheight*p->next_line+sx;
2038
2039 bg0 = attr_bgcol_ec(p,conp);
2040 for (rows = height*p->fontheight; rows--;) {
2041 bg = bg0;
2042 for (i = p->var.bits_per_pixel; i--; dest += p->next_plane) {
2043 if (bg & 1)
2044 mymemset(dest, width);
2045 else
2046 mymemclear(dest, width);
2047 bg >>= 1;
2048 }
2049 }
2050 }
2051
2052
2053 static void putc_ilbm(struct vc_data *conp, struct display *p, int c, int y,
2054 int x)
2055 {
2056 u_char *dest, *cdat;
2057 u_int rows, i;
2058 u_char d;
2059 int fg0, bg0, fg, bg;
2060
2061 c &= 0xff;
2062
2063 dest = p->screen_base+y*p->fontheight*p->next_line+x;
2064 cdat = p->fontdata+c*p->fontheight;
2065 fg0 = attr_fgcol(p,conp);
2066 bg0 = attr_bgcol(p,conp);
2067
2068 for (rows = p->fontheight; rows--;) {
2069 d = *cdat++;
2070 fg = fg0;
2071 bg = bg0;
2072 for (i = p->var.bits_per_pixel; i--; dest += p->next_plane) {
2073 if (bg & 1)
2074 if (fg & 1)
2075 *dest = 0xff;
2076 else
2077 *dest = ~d;
2078 else
2079 if (fg & 1)
2080 *dest = d;
2081 else
2082 *dest = 0x00;
2083 bg >>= 1;
2084 fg >>= 1;
2085 }
2086 }
2087 }
2088
2089
2090
2091
2092
2093
2094
2095
2096
2097
2098
2099
2100
2101
2102
2103
2104
2105 static void putcs_ilbm(struct vc_data *conp, struct display *p, const char *s,
2106 int count, int y, int x)
2107 {
2108 u_char *dest0, *dest, *cdat1, *cdat2, *cdat3, *cdat4;
2109 u_int rows, i;
2110 u_char c1, c2, c3, c4;
2111 u_long d;
2112 int fg0, bg0, fg, bg;
2113
2114 dest0 = p->screen_base+y*p->fontheight*p->next_line+x;
2115 fg0 = attr_fgcol(p,conp);
2116 bg0 = attr_bgcol(p,conp);
2117
2118 while (count--)
2119 if (x&3 || count < 3) {
2120 c1 = *s++;
2121 dest = dest0++;
2122 x++;
2123
2124 cdat1 = p->fontdata+c1*p->fontheight;
2125 for (rows = p->fontheight; rows--;) {
2126 d = *cdat1++;
2127 fg = fg0;
2128 bg = bg0;
2129 for (i = p->var.bits_per_pixel; i--; dest += p->next_plane) {
2130 if (bg & 1)
2131 if (fg & 1)
2132 *dest = 0xff;
2133 else
2134 *dest = ~d;
2135 else
2136 if (fg & 1)
2137 *dest = d;
2138 else
2139 *dest = 0x00;
2140 bg >>= 1;
2141 fg >>= 1;
2142 }
2143 }
2144 } else {
2145 c1 = s[0];
2146 c2 = s[1];
2147 c3 = s[2];
2148 c4 = s[3];
2149
2150 dest = dest0;
2151 cdat1 = p->fontdata+c1*p->fontheight;
2152 cdat2 = p->fontdata+c2*p->fontheight;
2153 cdat3 = p->fontdata+c3*p->fontheight;
2154 cdat4 = p->fontdata+c4*p->fontheight;
2155 for (rows = p->fontheight; rows--;) {
2156 d = *cdat1++<<24 | *cdat2++<<16 | *cdat3++<<8 | *cdat4++;
2157 fg = fg0;
2158 bg = bg0;
2159 for (i = p->var.bits_per_pixel; i--; dest += p->next_plane) {
2160 if (bg & 1)
2161 if (fg & 1)
2162 *(u_long *)dest = 0xffffffff;
2163 else
2164 *(u_long *)dest = ~d;
2165 else
2166 if (fg & 1)
2167 *(u_long *)dest = d;
2168 else
2169 *(u_long *)dest = 0x00000000;
2170 bg >>= 1;
2171 fg >>= 1;
2172 }
2173 }
2174 s += 4;
2175 dest0 += 4;
2176 x += 4;
2177 count -= 3;
2178 }
2179 }
2180
2181
2182 static void rev_char_ilbm(struct display *p, int x, int y)
2183 {
2184 u_char *dest, *dest0;
2185 u_int rows, i;
2186 int mask;
2187
2188 dest0 = p->screen_base+y*p->fontheight*p->next_line+x;
2189 mask = p->fgcol ^ p->bgcol;
2190
2191
2192
2193
2194
2195
2196
2197 for (i = p->var.bits_per_pixel; i--; dest0 += p->next_plane) {
2198 if (mask & 1) {
2199 dest = dest0;
2200 for (rows = p->fontheight; rows--; dest += p->next_line)
2201 *dest = ~*dest;
2202 }
2203 mask >>= 1;
2204 }
2205 }
2206
2207 #endif
2208
2209
2210
2211
2212 #ifdef CONFIG_FBCON_PLANES
2213
2214
2215
2216
2217
2218 static void bmove_plan(struct display *p, int sy, int sx, int dy, int dx,
2219 int height, int width)
2220 {
2221 u_char *src, *dest, *src0, *dest0;
2222 u_int i, rows;
2223
2224 if (sx == 0 && sy == 0 && width == p->next_line) {
2225 src = p->screen_base;
2226 dest = p->screen_base+dy*p->fontheight*width;
2227 for (i = p->var.bits_per_pixel; i--;) {
2228 mymemmove(dest, src, height*p->fontheight*width);
2229 src += p->next_plane;
2230 dest += p->next_plane;
2231 }
2232 } else if (dy <= sy) {
2233 src0 = p->screen_base+sy*p->fontheight*p->next_line+sx;
2234 dest0 = p->screen_base+dy*p->fontheight*p->next_line+dx;
2235 for (i = p->var.bits_per_pixel; i--;) {
2236 src = src0;
2237 dest = dest0;
2238 for (rows = height*p->fontheight; rows--;) {
2239 mymemmove(dest, src, width);
2240 src += p->next_line;
2241 dest += p->next_line;
2242 }
2243 src0 += p->next_plane;
2244 dest0 += p->next_plane;
2245 }
2246 } else {
2247 src0 = p->screen_base+(sy+height)*p->fontheight*p->next_line+sx;
2248 dest0 = p->screen_base+(dy+height)*p->fontheight*p->next_line+dx;
2249 for (i = p->var.bits_per_pixel; i--;) {
2250 src = src0;
2251 dest = dest0;
2252 for (rows = height*p->fontheight; rows--;) {
2253 src -= p->next_line;
2254 dest -= p->next_line;
2255 mymemmove(dest, src, width);
2256 }
2257 src0 += p->next_plane;
2258 dest0 += p->next_plane;
2259 }
2260 }
2261 }
2262
2263
2264 static void clear_plan(struct vc_data *conp, struct display *p, int sy, int sx,
2265 int height, int width)
2266 {
2267 u_char *dest, *dest0;
2268 u_int i, rows;
2269 int bg;
2270
2271 dest0 = p->screen_base+sy*p->fontheight*p->next_line+sx;
2272
2273 bg = attr_bgcol_ec(p,conp);
2274 for (i = p->var.bits_per_pixel; i--; dest0 += p->next_plane) {
2275 dest = dest0;
2276 for (rows = height*p->fontheight; rows--; dest += p->next_line)
2277 if (bg & 1)
2278 mymemset(dest, width);
2279 else
2280 mymemclear(dest, width);
2281 bg >>= 1;
2282 }
2283 }
2284
2285
2286 static void putc_plan(struct vc_data *conp, struct display *p, int c, int y,
2287 int x)
2288 {
2289 u_char *dest, *dest0, *cdat, *cdat0;
2290 u_int rows, i;
2291 u_char d;
2292 int fg, bg;
2293
2294 c &= 0xff;
2295
2296 dest0 = p->screen_base+y*p->fontheight*p->next_line+x;
2297 cdat0 = p->fontdata+c*p->fontheight;
2298 fg = attr_fgcol(p,conp);
2299 bg = attr_bgcol(p,conp);
2300
2301 for (i = p->var.bits_per_pixel; i--; dest0 += p->next_plane) {
2302 dest = dest0;
2303 cdat = cdat0;
2304 for (rows = p->fontheight; rows--; dest += p->next_line) {
2305 d = *cdat++;
2306 if (bg & 1)
2307 if (fg & 1)
2308 *dest = 0xff;
2309 else
2310 *dest = ~d;
2311 else
2312 if (fg & 1)
2313 *dest = d;
2314 else
2315 *dest = 0x00;
2316 }
2317 bg >>= 1;
2318 fg >>= 1;
2319 }
2320 }
2321
2322
2323
2324
2325
2326
2327
2328 static void putcs_plan(struct vc_data *conp, struct display *p, const char *s,
2329 int count, int y, int x)
2330 {
2331 u_char *dest, *dest0, *dest1;
2332 u_char *cdat1, *cdat2, *cdat3, *cdat4, *cdat10, *cdat20, *cdat30, *cdat40;
2333 u_int rows, i;
2334 u_char c1, c2, c3, c4;
2335 u_long d;
2336 int fg0, bg0, fg, bg;
2337
2338 dest0 = p->screen_base+y*p->fontheight*p->next_line+x;
2339 fg0 = attr_fgcol(p,conp);
2340 bg0 = attr_bgcol(p,conp);
2341
2342 while (count--)
2343 if (x&3 || count < 3) {
2344 c1 = *s++;
2345 dest1 = dest0++;
2346 x++;
2347
2348 cdat10 = p->fontdata+c1*p->fontheight;
2349 fg = fg0;
2350 bg = bg0;
2351
2352 for (i = p->var.bits_per_pixel; i--; dest1 += p->next_plane) {
2353 dest = dest1;
2354 cdat1 = cdat10;
2355 for (rows = p->fontheight; rows--; dest += p->next_line) {
2356 d = *cdat1++;
2357 if (bg & 1)
2358 if (fg & 1)
2359 *dest = 0xff;
2360 else
2361 *dest = ~d;
2362 else
2363 if (fg & 1)
2364 *dest = d;
2365 else
2366 *dest = 0x00;
2367 }
2368 bg >>= 1;
2369 fg >>= 1;
2370 }
2371 } else {
2372 c1 = s[0];
2373 c2 = s[1];
2374 c3 = s[2];
2375 c4 = s[3];
2376
2377 dest1 = dest0;
2378 cdat10 = p->fontdata+c1*p->fontheight;
2379 cdat20 = p->fontdata+c2*p->fontheight;
2380 cdat30 = p->fontdata+c3*p->fontheight;
2381 cdat40 = p->fontdata+c4*p->fontheight;
2382 fg = fg0;
2383 bg = bg0;
2384
2385 for (i = p->var.bits_per_pixel; i--; dest1 += p->next_plane) {
2386 dest = dest1;
2387 cdat1 = cdat10;
2388 cdat2 = cdat20;
2389 cdat3 = cdat30;
2390 cdat4 = cdat40;
2391 for (rows = p->fontheight; rows--; dest += p->next_line) {
2392 d = *cdat1++<<24 | *cdat2++<<16 | *cdat3++<<8 | *cdat4++;
2393 if (bg & 1)
2394 if (fg & 1)
2395 *(u_long *)dest = 0xffffffff;
2396 else
2397 *(u_long *)dest = ~d;
2398 else
2399 if (fg & 1)
2400 *(u_long *)dest = d;
2401 else
2402 *(u_long *)dest = 0x00000000;
2403 }
2404 bg >>= 1;
2405 fg >>= 1;
2406 }
2407 s += 4;
2408 dest0 += 4;
2409 x += 4;
2410 count -= 3;
2411 }
2412 }
2413
2414
2415 static void rev_char_plan(struct display *p, int x, int y)
2416 {
2417 u_char *dest, *dest0;
2418 u_int rows, i;
2419 int mask;
2420
2421 dest0 = p->screen_base+y*p->fontheight*p->next_line+x;
2422 mask = p->fgcol ^ p->bgcol;
2423
2424
2425
2426
2427
2428
2429
2430 for (i = p->var.bits_per_pixel; i--; dest0 += p->next_plane) {
2431 if (mask & 1) {
2432 dest = dest0;
2433 for (rows = p->fontheight; rows--; dest += p->next_line)
2434 *dest = ~*dest;
2435 }
2436 mask >>= 1;
2437 }
2438 }
2439
2440 #endif
2441
2442
2443
2444
2445 #ifdef CONFIG_FBCON_2PLANE
2446
2447
2448
2449
2450
2451
2452
2453 #define INC_2P(p) do { if (!((long)(++(p)) & 1)) (p) += 2; } while(0)
2454 #define DEC_2P(p) do { if ((long)(--(p)) & 1) (p) -= 2; } while(0)
2455
2456
2457
2458
2459
2460
2461 #define COLOR_2P(c) (((c & 7) >= 3 && (c & 7) != 4) | (c & 8) >> 2)
2462
2463
2464 static void bmove_2_plane(struct display *p, int sy, int sx, int dy, int dx,
2465 int height, int width)
2466 {
2467
2468
2469
2470
2471
2472
2473
2474
2475
2476
2477
2478
2479 if (sx == 0 && dx == 0 && width == p->next_line/2) {
2480
2481
2482
2483 mymemmove(p->screen_base + dy * p->next_line * p->fontheight,
2484 p->screen_base + sy * p->next_line * p->fontheight,
2485 p->next_line * height * p->fontheight);
2486 } else {
2487 int rows, cols;
2488 u_char *src;
2489 u_char *dst;
2490 int bytes = p->next_line;
2491 int linesize = bytes * p->fontheight;
2492 u_int colsize = height * p->fontheight;
2493 u_int upwards = (dy < sy) || (dy == sy && dx < sx);
2494
2495 if ((sx & 1) == (dx & 1)) {
2496
2497
2498 if (upwards) {
2499
2500 src = p->screen_base + sy * linesize + (sx>>1)*4 + (sx & 1);
2501 dst = p->screen_base + dy * linesize + (dx>>1)*4 + (dx & 1);
2502
2503 if (sx & 1) {
2504 memmove_2p_col(dst, src, colsize, bytes);
2505 src += 3;
2506 dst += 3;
2507 --width;
2508 }
2509
2510 if (width > 1) {
2511 for(rows = colsize; rows > 0; --rows) {
2512 mymemmove(dst, src, (width>>1)*4);
2513 src += bytes;
2514 dst += bytes;
2515 }
2516 }
2517
2518 if (width & 1) {
2519 src -= colsize * bytes;
2520 dst -= colsize * bytes;
2521 memmove_2p_col(dst + (width>>1)*4, src + (width>>1)*4,
2522 colsize, bytes);
2523 }
2524 }
2525 else {
2526
2527 if (!((sx+width-1) & 1)) {
2528 src = p->screen_base + sy * linesize + ((sx+width-1)>>1)*4;
2529 dst = p->screen_base + dy * linesize + ((dx+width-1)>>1)*4;
2530 memmove_2p_col(dst, src, colsize, bytes);
2531 --width;
2532 }
2533
2534 src = p->screen_base + sy * linesize + (sx>>1)*4 + (sx & 1);
2535 dst = p->screen_base + dy * linesize + (dx>>1)*4 + (dx & 1);
2536
2537 if (width > 1) {
2538 src += colsize * bytes + (sx & 1)*3;
2539 dst += colsize * bytes + (sx & 1)*3;
2540 for(rows = colsize; rows > 0; --rows) {
2541 src -= bytes;
2542 dst -= bytes;
2543 mymemmove(dst, src, (width>>1)*4);
2544 }
2545 }
2546
2547 if (width & 1) {
2548 memmove_2p_col(dst-3, src-3, colsize, bytes);
2549 }
2550
2551 }
2552 }
2553 else {
2554
2555
2556 if (upwards) {
2557 src = p->screen_base + sy * linesize + (sx>>1)*4 + (sx & 1);
2558 dst = p->screen_base + dy * linesize + (dx>>1)*4 + (dx & 1);
2559 for(cols = width; cols > 0; --cols) {
2560 memmove_2p_col(dst, src, colsize, bytes);
2561 INC_2P(src);
2562 INC_2P(dst);
2563 }
2564 }
2565 else {
2566 sx += width-1;
2567 dx += width-1;
2568 src = p->screen_base + sy * linesize + (sx>>1)*4 + (sx & 1);
2569 dst = p->screen_base + dy * linesize + (dx>>1)*4 + (dx & 1);
2570 for(cols = width; cols > 0; --cols) {
2571 memmove_2p_col(dst, src, colsize, bytes);
2572 DEC_2P(src);
2573 DEC_2P(dst);
2574 }
2575 }
2576 }
2577
2578
2579 }
2580 }
2581
2582
2583 static void clear_2_plane(struct vc_data *conp, struct display *p, int sy,
2584 int sx, int height, int width)
2585 {
2586 ulong offset;
2587 u_char *start;
2588 int rows;
2589 int bytes = p->next_line;
2590 int lines = height * p->fontheight;
2591 ulong size;
2592 u_long cval;
2593 u_short pcval;
2594
2595 cval = expand2l (COLOR_2P (attr_bgcol_ec(p,conp)));
2596
2597 if (sx == 0 && width == bytes/2) {
2598
2599 offset = sy * bytes * p->fontheight;
2600 size = lines * bytes;
2601 memset_even_2p(p->screen_base+offset, size, cval);
2602
2603 } else {
2604
2605 offset = (sy * bytes * p->fontheight) + (sx>>1)*4 + (sx & 1);
2606 start = p->screen_base + offset;
2607 pcval = expand2w(COLOR_2P(attr_bgcol_ec(p,conp)));
2608
2609
2610
2611
2612
2613
2614
2615
2616 if (sx & 1) {
2617 memclear_2p_col(start, lines, pcval, bytes);
2618 start += 3;
2619 width--;
2620 }
2621
2622 if (width & 1) {
2623 memclear_2p_col(start + (width>>1)*4, lines, pcval, bytes);
2624 width--;
2625 }
2626
2627 if (width) {
2628 for(rows = lines; rows-- ; start += bytes)
2629 memset_even_2p(start, width*2, cval);
2630 }
2631 }
2632 }
2633
2634
2635 static void putc_2_plane(struct vc_data *conp, struct display *p, int c, int y,
2636 int x)
2637 {
2638 u_char *dest;
2639 u_char *cdat;
2640 int rows;
2641 int bytes = p->next_line;
2642 ulong eorx, fgx, bgx, fdx;
2643
2644 c &= 0xff;
2645
2646 dest = p->screen_base + y * p->fontheight * bytes + (x>>1)*4 + (x & 1);
2647 cdat = p->fontdata + (c * p->fontheight);
2648
2649 fgx = expand2w(COLOR_2P(attr_fgcol(p,conp)));
2650 bgx = expand2w(COLOR_2P(attr_bgcol(p,conp)));
2651 eorx = fgx ^ bgx;
2652
2653 for(rows = p->fontheight ; rows-- ; dest += bytes) {
2654 fdx = dup2w(*cdat++);
2655 __asm__ __volatile__ ("movepw %1,%0@(0)" :
2656 : "a" (dest), "d" ((fdx & eorx) ^ bgx));
2657 }
2658 }
2659
2660
2661 static void putcs_2_plane(struct vc_data *conp, struct display *p,
2662 const char *s, int count, int y, int x)
2663 {
2664 u_char *dest, *dest0;
2665 u_char *cdat, c;
2666 int rows;
2667 int bytes;
2668 ulong eorx, fgx, bgx, fdx;
2669
2670 bytes = p->next_line;
2671 dest0 = p->screen_base + y * p->fontheight * bytes + (x>>1)*4 + (x & 1);
2672 fgx = expand2w(COLOR_2P(attr_fgcol(p,conp)));
2673 bgx = expand2w(COLOR_2P(attr_bgcol(p,conp)));
2674 eorx = fgx ^ bgx;
2675
2676 while (count--) {
2677
2678 c = *s++;
2679 cdat = p->fontdata + (c * p->fontheight);
2680
2681 for(rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
2682 fdx = dup2w(*cdat++);
2683 __asm__ __volatile__ ("movepw %1,%0@(0)" :
2684 : "a" (dest), "d" ((fdx & eorx) ^ bgx));
2685 }
2686 INC_2P(dest0);
2687 }
2688 }
2689
2690
2691 static void rev_char_2_plane(struct display *p, int x, int y)
2692 {
2693 u_char *dest;
2694 int j;
2695 int bytes;
2696
2697 dest = p->screen_base + y * p->fontheight * p->next_line + (x>>1)*4 + (x & 1);
2698 j = p->fontheight;
2699 bytes = p->next_line;
2700 while (j--)
2701 {
2702
2703
2704
2705
2706 dest[0] = ~dest[0];
2707 dest[2] = ~dest[2];
2708 dest += bytes;
2709 }
2710 }
2711 #endif
2712
2713
2714
2715
2716 #ifdef CONFIG_FBCON_4PLANE
2717
2718
2719
2720
2721
2722
2723
2724 #define INC_4P(p) do { if (!((long)(++(p)) & 1)) (p) += 6; } while(0)
2725 #define DEC_4P(p) do { if ((long)(--(p)) & 1) (p) -= 6; } while(0)
2726
2727
2728 static void bmove_4_plane(struct display *p, int sy, int sx, int dy, int dx,
2729 int height, int width)
2730 {
2731
2732
2733
2734
2735
2736
2737
2738
2739
2740
2741
2742
2743 if (sx == 0 && dx == 0 && width == p->next_line/4) {
2744
2745
2746
2747 mymemmove(p->screen_base + dy * p->next_line * p->fontheight,
2748 p->screen_base + sy * p->next_line * p->fontheight,
2749 p->next_line * height * p->fontheight);
2750 } else {
2751 int rows, cols;
2752 u_char *src;
2753 u_char *dst;
2754 int bytes = p->next_line;
2755 int linesize = bytes * p->fontheight;
2756 u_int colsize = height * p->fontheight;
2757 u_int upwards = (dy < sy) || (dy == sy && dx < sx);
2758
2759 if ((sx & 1) == (dx & 1)) {
2760
2761
2762 if (upwards) {
2763
2764 src = p->screen_base + sy * linesize + (sx>>1)*8 + (sx & 1);
2765 dst = p->screen_base + dy * linesize + (dx>>1)*8 + (dx & 1);
2766
2767 if (sx & 1) {
2768 memmove_4p_col(dst, src, colsize, bytes);
2769 src += 7;
2770 dst += 7;
2771 --width;
2772 }
2773
2774 if (width > 1) {
2775 for(rows = colsize; rows > 0; --rows) {
2776 mymemmove(dst, src, (width>>1)*8);
2777 src += bytes;
2778 dst += bytes;
2779 }
2780 }
2781
2782 if (width & 1) {
2783 src -= colsize * bytes;
2784 dst -= colsize * bytes;
2785 memmove_4p_col(dst + (width>>1)*8, src + (width>>1)*8,
2786 colsize, bytes);
2787 }
2788 }
2789 else {
2790
2791 if (!((sx+width-1) & 1)) {
2792 src = p->screen_base + sy * linesize + ((sx+width-1)>>1)*8;
2793 dst = p->screen_base + dy * linesize + ((dx+width-1)>>1)*8;
2794 memmove_4p_col(dst, src, colsize, bytes);
2795 --width;
2796 }
2797
2798 src = p->screen_base + sy * linesize + (sx>>1)*8 + (sx & 1);
2799 dst = p->screen_base + dy * linesize + (dx>>1)*8 + (dx & 1);
2800
2801 if (width > 1) {
2802 src += colsize * bytes + (sx & 1)*7;
2803 dst += colsize * bytes + (sx & 1)*7;
2804 for(rows = colsize; rows > 0; --rows) {
2805 src -= bytes;
2806 dst -= bytes;
2807 mymemmove(dst, src, (width>>1)*8);
2808 }
2809 }
2810
2811 if (width & 1) {
2812 memmove_4p_col(dst-7, src-7, colsize, bytes);
2813 }
2814
2815 }
2816 }
2817 else {
2818
2819
2820 if (upwards) {
2821 src = p->screen_base + sy * linesize + (sx>>1)*8 + (sx & 1);
2822 dst = p->screen_base + dy * linesize + (dx>>1)*8 + (dx & 1);
2823 for(cols = width; cols > 0; --cols) {
2824 memmove_4p_col(dst, src, colsize, bytes);
2825 INC_4P(src);
2826 INC_4P(dst);
2827 }
2828 }
2829 else {
2830 sx += width-1;
2831 dx += width-1;
2832 src = p->screen_base + sy * linesize + (sx>>1)*8 + (sx & 1);
2833 dst = p->screen_base + dy * linesize + (dx>>1)*8 + (dx & 1);
2834 for(cols = width; cols > 0; --cols) {
2835 memmove_4p_col(dst, src, colsize, bytes);
2836 DEC_4P(src);
2837 DEC_4P(dst);
2838 }
2839 }
2840 }
2841
2842
2843 }
2844 }
2845
2846
2847 static void clear_4_plane(struct vc_data *conp, struct display *p, int sy,
2848 int sx, int height, int width)
2849 {
2850 ulong offset;
2851 u_char *start;
2852 int rows;
2853 int bytes = p->next_line;
2854 int lines = height * p->fontheight;
2855 ulong size;
2856 u_long cval1, cval2, pcval;
2857
2858 expand4dl(attr_bgcol_ec(p,conp), &cval1, &cval2);
2859
2860 if (sx == 0 && width == bytes/4) {
2861
2862 offset = sy * bytes * p->fontheight;
2863 size = lines * bytes;
2864 memset_even_4p(p->screen_base+offset, size, cval1, cval2);
2865
2866 } else {
2867
2868 offset = (sy * bytes * p->fontheight) + (sx>>1)*8 + (sx & 1);
2869 start = p->screen_base + offset;
2870 pcval = expand4l(attr_bgcol_ec(p,conp));
2871
2872
2873
2874
2875
2876
2877
2878
2879 if (sx & 1) {
2880 memclear_4p_col(start, lines, pcval, bytes);
2881 start += 7;
2882 width--;
2883 }
2884
2885 if (width & 1) {
2886 memclear_4p_col(start + (width>>1)*8, lines, pcval, bytes);
2887 width--;
2888 }
2889
2890 if (width) {
2891 for(rows = lines; rows-- ; start += bytes)
2892 memset_even_4p(start, width*4, cval1, cval2);
2893 }
2894 }
2895 }
2896
2897
2898 static void putc_4_plane(struct vc_data *conp, struct display *p, int c, int y,
2899 int x)
2900 {
2901 u_char *dest;
2902 u_char *cdat;
2903 int rows;
2904 int bytes = p->next_line;
2905 ulong eorx, fgx, bgx, fdx;
2906
2907 c &= 0xff;
2908
2909 dest = p->screen_base + y * p->fontheight * bytes + (x>>1)*8 + (x & 1);
2910 cdat = p->fontdata + (c * p->fontheight);
2911
2912 fgx = expand4l(attr_fgcol(p,conp));
2913 bgx = expand4l(attr_bgcol(p,conp));
2914 eorx = fgx ^ bgx;
2915
2916 for(rows = p->fontheight ; rows-- ; dest += bytes) {
2917 fdx = dup4l(*cdat++);
2918 __asm__ __volatile__ ("movepl %1,%0@(0)" :
2919 : "a" (dest), "d" ((fdx & eorx) ^ bgx));
2920 }
2921 }
2922
2923
2924 static void putcs_4_plane(struct vc_data *conp, struct display *p,
2925 const char *s, int count, int y, int x)
2926 {
2927 u_char *dest, *dest0;
2928 u_char *cdat, c;
2929 int rows;
2930 int bytes;
2931 ulong eorx, fgx, bgx, fdx;
2932
2933 bytes = p->next_line;
2934 dest0 = p->screen_base + y * p->fontheight * bytes + (x>>1)*8 + (x & 1);
2935 fgx = expand4l(attr_fgcol(p,conp));
2936 bgx = expand4l(attr_bgcol(p,conp));
2937 eorx = fgx ^ bgx;
2938
2939 while (count--) {
2940
2941
2942
2943
2944
2945
2946
2947
2948 c = *s++;
2949 cdat = p->fontdata + (c * p->fontheight);
2950
2951 for(rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
2952 fdx = dup4l(*cdat++);
2953 __asm__ __volatile__ ("movepl %1,%0@(0)" :
2954 : "a" (dest), "d" ((fdx & eorx) ^ bgx));
2955 }
2956 INC_4P(dest0);
2957 }
2958 }
2959
2960
2961 static void rev_char_4_plane(struct display *p, int x, int y)
2962 {
2963 u_char *dest;
2964 int j;
2965 int bytes;
2966
2967 dest = p->screen_base + y * p->fontheight * p->next_line + (x>>1)*8 + (x & 1);
2968 j = p->fontheight;
2969 bytes = p->next_line;
2970
2971 while (j--)
2972 {
2973
2974
2975
2976
2977 dest[0] = ~dest[0];
2978 dest[2] = ~dest[2];
2979 dest[4] = ~dest[4];
2980 dest[6] = ~dest[6];
2981 dest += bytes;
2982 }
2983 }
2984 #endif
2985
2986
2987
2988
2989 #ifdef CONFIG_FBCON_8PLANE
2990
2991
2992
2993
2994
2995
2996
2997
2998
2999
3000
3001
3002
3003 #define INC_8P(p) do { if (!((long)(++(p)) & 1)) (p) += 14; } while(0)
3004 #define DEC_8P(p) do { if ((long)(--(p)) & 1) (p) -= 14; } while(0)
3005
3006
3007 static void bmove_8_plane(struct display *p, int sy, int sx, int dy, int dx,
3008 int height, int width)
3009 {
3010
3011
3012
3013
3014
3015
3016
3017
3018
3019
3020
3021
3022 if (sx == 0 && dx == 0 && width == p->next_line/8) {
3023
3024
3025
3026 fast_memmove (p->screen_base + dy * p->next_line * p->fontheight,
3027 p->screen_base + sy * p->next_line * p->fontheight,
3028 p->next_line * height * p->fontheight);
3029 } else {
3030 int rows, cols;
3031 u_char *src;
3032 u_char *dst;
3033 int bytes = p->next_line;
3034 int linesize = bytes * p->fontheight;
3035 u_int colsize = height * p->fontheight;
3036 u_int upwards = (dy < sy) || (dy == sy && dx < sx);
3037
3038 if ((sx & 1) == (dx & 1)) {
3039
3040
3041 if (upwards) {
3042
3043 src = p->screen_base + sy * linesize + (sx>>1)*16 + (sx & 1);
3044 dst = p->screen_base + dy * linesize + (dx>>1)*16 + (dx & 1);
3045
3046 if (sx & 1) {
3047 memmove_8p_col(dst, src, colsize, bytes);
3048 src += 15;
3049 dst += 15;
3050 --width;
3051 }
3052
3053 if (width > 1) {
3054 for(rows = colsize; rows > 0; --rows) {
3055 fast_memmove (dst, src, (width >> 1) * 16);
3056 src += bytes;
3057 dst += bytes;
3058 }
3059 }
3060
3061 if (width & 1) {
3062 src -= colsize * bytes;
3063 dst -= colsize * bytes;
3064 memmove_8p_col(dst + (width>>1)*16, src + (width>>1)*16,
3065 colsize, bytes);
3066 }
3067 }
3068 else {
3069
3070 if (!((sx+width-1) & 1)) {
3071 src = p->screen_base + sy * linesize + ((sx+width-1)>>1)*16;
3072 dst = p->screen_base + dy * linesize + ((dx+width-1)>>1)*16;
3073 memmove_8p_col(dst, src, colsize, bytes);
3074 --width;
3075 }
3076
3077 src = p->screen_base + sy * linesize + (sx>>1)*16 + (sx & 1);
3078 dst = p->screen_base + dy * linesize + (dx>>1)*16 + (dx & 1);
3079
3080 if (width > 1) {
3081 src += colsize * bytes + (sx & 1)*15;
3082 dst += colsize * bytes + (sx & 1)*15;
3083 for(rows = colsize; rows > 0; --rows) {
3084 src -= bytes;
3085 dst -= bytes;
3086 fast_memmove (dst, src, (width>>1)*16);
3087 }
3088 }
3089
3090 if (width & 1) {
3091 memmove_8p_col(dst-15, src-15, colsize, bytes);
3092 }
3093
3094 }
3095 }
3096 else {
3097
3098
3099 if (upwards) {
3100 src = p->screen_base + sy * linesize + (sx>>1)*16 + (sx & 1);
3101 dst = p->screen_base + dy * linesize + (dx>>1)*16 + (dx & 1);
3102 for(cols = width; cols > 0; --cols) {
3103 memmove_8p_col(dst, src, colsize, bytes);
3104 INC_8P(src);
3105 INC_8P(dst);
3106 }
3107 }
3108 else {
3109 sx += width-1;
3110 dx += width-1;
3111 src = p->screen_base + sy * linesize + (sx>>1)*16 + (sx & 1);
3112 dst = p->screen_base + dy * linesize + (dx>>1)*16 + (dx & 1);
3113 for(cols = width; cols > 0; --cols) {
3114 memmove_8p_col(dst, src, colsize, bytes);
3115 DEC_8P(src);
3116 DEC_8P(dst);
3117 }
3118 }
3119 }
3120
3121
3122 }
3123 }
3124
3125
3126 static void clear_8_plane(struct vc_data *conp, struct display *p, int sy,
3127 int sx, int height, int width)
3128 {
3129 ulong offset;
3130 u_char *start;
3131 int rows;
3132 int bytes = p->next_line;
3133 int lines = height * p->fontheight;
3134 ulong size;
3135 u_long cval1, cval2, cval3, cval4, pcval1, pcval2;
3136
3137 expand8ql(attr_bgcol_ec(p,conp), cval1, cval2, cval3, cval4);
3138
3139 if (sx == 0 && width == bytes/8) {
3140
3141 offset = sy * bytes * p->fontheight;
3142 size = lines * bytes;
3143 memset_even_8p(p->screen_base+offset, size, cval1, cval2, cval3, cval4);
3144
3145 } else {
3146
3147 offset = (sy * bytes * p->fontheight) + (sx>>1)*16 + (sx & 1);
3148 start = p->screen_base + offset;
3149 expand8dl(attr_bgcol_ec(p,conp), &pcval1, &pcval2);
3150
3151
3152
3153
3154
3155
3156
3157
3158 if (sx & 1) {
3159 memclear_8p_col(start, lines, pcval1, pcval2, bytes);
3160 start += 7;
3161 width--;
3162 }
3163
3164 if (width & 1) {
3165 memclear_8p_col(start + (width>>1)*16, lines, pcval1,
3166 pcval2, bytes);
3167 width--;
3168 }
3169
3170 if (width) {
3171 for(rows = lines; rows-- ; start += bytes)
3172 memset_even_8p(start, width*8, cval1, cval2, cval3, cval4);
3173 }
3174 }
3175 }
3176
3177
3178 static void putc_8_plane(struct vc_data *conp, struct display *p, int c, int y,
3179 int x)
3180 {
3181 u_char *dest;
3182 u_char *cdat;
3183 int rows;
3184 int bytes = p->next_line;
3185 ulong eorx1, eorx2, fgx1, fgx2, bgx1, bgx2, fdx;
3186
3187 c &= 0xff;
3188
3189 dest = p->screen_base + y * p->fontheight * bytes + (x>>1)*16 + (x & 1);
3190 cdat = p->fontdata + (c * p->fontheight);
3191
3192 expand8dl(attr_fgcol(p,conp), &fgx1, &fgx2);
3193 expand8dl(attr_bgcol(p,conp), &bgx1, &bgx2);
3194 eorx1 = fgx1 ^ bgx1; eorx2 = fgx2 ^ bgx2;
3195
3196 for(rows = p->fontheight ; rows-- ; dest += bytes) {
3197 fdx = dup4l(*cdat++);
3198 __asm__ __volatile__
3199 ("movepl %1,%0@(0)\n\t"
3200 "movepl %2,%0@(8)"
3201 :
3202 : "a" (dest), "d" ((fdx & eorx1) ^ bgx1),
3203 "d" ((fdx & eorx2) ^ bgx2)
3204 );
3205 }
3206 }
3207
3208
3209 static void putcs_8_plane(struct vc_data *conp, struct display *p,
3210 const char *s, int count, int y, int x)
3211 {
3212 u_char *dest, *dest0;
3213 u_char *cdat, c;
3214 int rows;
3215 int bytes;
3216 ulong eorx1, eorx2, fgx1, fgx2, bgx1, bgx2, fdx;
3217
3218 bytes = p->next_line;
3219 dest0 = p->screen_base + y * p->fontheight * bytes + (x>>1)*16 + (x & 1);
3220
3221 expand8dl(attr_fgcol(p,conp), &fgx1, &fgx2);
3222 expand8dl(attr_bgcol(p,conp), &bgx1, &bgx2);
3223 eorx1 = fgx1 ^ bgx1; eorx2 = fgx2 ^ bgx2;
3224
3225 while (count--) {
3226
3227
3228
3229
3230
3231
3232
3233
3234 c = *s++;
3235 cdat = p->fontdata + (c * p->fontheight);
3236
3237 for(rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
3238 fdx = dup4l(*cdat++);
3239 __asm__ __volatile__
3240 ("movepl %1,%0@(0)\n\t"
3241 "movepl %2,%0@(8)"
3242 :
3243 : "a" (dest), "d" ((fdx & eorx1) ^ bgx1),
3244 "d" ((fdx & eorx2) ^ bgx2)
3245 );
3246 }
3247 INC_8P(dest0);
3248 }
3249 }
3250
3251
3252 static void rev_char_8_plane(struct display *p, int x, int y)
3253 {
3254 u_char *dest;
3255 int j;
3256 int bytes;
3257
3258 dest = p->screen_base + y * p->fontheight * p->next_line + (x>>1)*16 + (x & 1);
3259 j = p->fontheight;
3260 bytes = p->next_line;
3261
3262 while (j--)
3263 {
3264
3265
3266
3267
3268
3269
3270 dest[0] = ~dest[0];
3271 dest[2] = ~dest[2];
3272 dest[4] = ~dest[4];
3273 dest[6] = ~dest[6];
3274 dest += bytes;
3275 }
3276 }
3277 #endif
3278
3279
3280
3281
3282 #ifdef CONFIG_FBCON_8PACKED
3283
3284
3285
3286
3287
3288 static u_long nibbletab_8_packed[]={
3289 0x00000000,0x000000ff,0x0000ff00,0x0000ffff,
3290 0x00ff0000,0x00ff00ff,0x00ffff00,0x00ffffff,
3291 0xff000000,0xff0000ff,0xff00ff00,0xff00ffff,
3292 0xffff0000,0xffff00ff,0xffffff00,0xffffffff};
3293
3294 static void bmove_8_packed(struct display *p, int sy, int sx, int dy, int dx,
3295 int height, int width)
3296 {
3297 int bytes = p->next_line, linesize = bytes * p->fontheight, rows;
3298 u_char *src,*dst;
3299
3300 if (sx == 0 && dx == 0 && width * 8 == bytes) {
3301 mymemmove(p->screen_base + dy * linesize,
3302 p->screen_base + sy * linesize,
3303 height * linesize);
3304 }
3305 else {
3306 if (dy < sy || (dy == sy && dx < sx)) {
3307 src = p->screen_base + sy * linesize + sx * 8;
3308 dst = p->screen_base + dy * linesize + dx * 8;
3309 for (rows = height * p->fontheight ; rows-- ;) {
3310 mymemmove(dst, src, width * 8);
3311 src += bytes;
3312 dst += bytes;
3313 }
3314 }
3315 else {
3316 src = p->screen_base + (sy+height) * linesize + sx * 8
3317 - bytes;
3318 dst = p->screen_base + (dy+height) * linesize + dx * 8
3319 - bytes;
3320 for (rows = height * p->fontheight ; rows-- ;) {
3321 mymemmove(dst, src, width * 8);
3322 src -= bytes;
3323 dst -= bytes;
3324 }
3325 }
3326 }
3327 }
3328
3329
3330 static void clear_8_packed(struct vc_data *conp, struct display *p, int sy,
3331 int sx, int height, int width)
3332 {
3333 u_char *dest0,*dest;
3334 int bytes=p->next_line,lines=height * p->fontheight, rows, i;
3335 u_long bgx;
3336
3337 dest = p->screen_base + sy * p->fontheight * bytes + sx * 8;
3338
3339 bgx=attr_bgcol_ec(p,conp);
3340 bgx |= (bgx << 8);
3341 bgx |= (bgx << 16);
3342
3343 if (sx == 0 && width * 8 == bytes) {
3344 for (i = 0 ; i < lines * width ; i++) {
3345 ((u_long *)dest)[0]=bgx;
3346 ((u_long *)dest)[1]=bgx;
3347 dest+=8;
3348 }
3349 } else {
3350 dest0=dest;
3351 for (rows = lines; rows-- ; dest0 += bytes) {
3352 dest=dest0;
3353 for (i = 0 ; i < width ; i++) {
3354 ((u_long *)dest)[0]=bgx;
3355 ((u_long *)dest)[1]=bgx;
3356 dest+=8;
3357 }
3358 }
3359 }
3360 }
3361
3362
3363 static void putc_8_packed(struct vc_data *conp, struct display *p, int c, int y,
3364 int x)
3365 {
3366 u_char *dest,*cdat;
3367 int bytes=p->next_line,rows;
3368 ulong eorx,fgx,bgx;
3369
3370 c &= 0xff;
3371
3372 dest = p->screen_base + y * p->fontheight * bytes + x * 8;
3373 cdat = p->fontdata + c * p->fontheight;
3374
3375 fgx=attr_fgcol(p,conp);
3376 bgx=attr_bgcol(p,conp);
3377 fgx |= (fgx << 8);
3378 fgx |= (fgx << 16);
3379 bgx |= (bgx << 8);
3380 bgx |= (bgx << 16);
3381 eorx = fgx ^ bgx;
3382
3383 for (rows = p->fontheight ; rows-- ; dest += bytes) {
3384 ((u_long *)dest)[0]=
3385 (nibbletab_8_packed[*cdat >> 4] & eorx) ^ bgx;
3386 ((u_long *)dest)[1]=
3387 (nibbletab_8_packed[*cdat++ & 0xf] & eorx) ^ bgx;
3388 }
3389 }
3390
3391
3392 static void putcs_8_packed(struct vc_data *conp, struct display *p,
3393 const char *s, int count, int y, int x)
3394 {
3395 u_char *cdat, c, *dest, *dest0;
3396 int rows,bytes=p->next_line;
3397 u_long eorx, fgx, bgx;
3398
3399 dest0 = p->screen_base + y * p->fontheight * bytes + x * 8;
3400 fgx=attr_fgcol(p,conp);
3401 bgx=attr_bgcol(p,conp);
3402 fgx |= (fgx << 8);
3403 fgx |= (fgx << 16);
3404 bgx |= (bgx << 8);
3405 bgx |= (bgx << 16);
3406 eorx = fgx ^ bgx;
3407 while (count--) {
3408 c = *s++;
3409 cdat = p->fontdata + c * p->fontheight;
3410
3411 for (rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
3412 ((u_long *)dest)[0]=
3413 (nibbletab_8_packed[*cdat >> 4] & eorx) ^ bgx;
3414 ((u_long *)dest)[1]=
3415 (nibbletab_8_packed[*cdat++ & 0xf] & eorx) ^ bgx;
3416 }
3417 dest0+=8;
3418 }
3419 }
3420
3421
3422 static void rev_char_8_packed(struct display *p, int x, int y)
3423 {
3424 u_char *dest;
3425 int bytes=p->next_line, rows;
3426
3427 dest = p->screen_base + y * p->fontheight * bytes + x * 8;
3428 for (rows = p->fontheight ; rows-- ; dest += bytes) {
3429 ((u_long *)dest)[0] ^= 0x0f0f0f0f;
3430 ((u_long *)dest)[1] ^= 0x0f0f0f0f;
3431 }
3432 }
3433
3434 #endif
3435
3436
3437
3438
3439 #ifdef CONFIG_FBCON_16PACKED
3440
3441
3442
3443
3444
3445 u_short packed16_cmap[16];
3446
3447 static u_long tab_16_packed[]={
3448 0x00000000,0x0000ffff,0xffff0000,0xffffffff};
3449
3450 static void bmove_16_packed(struct display *p, int sy, int sx, int dy, int dx,
3451 int height, int width)
3452 {
3453 int bytes = p->next_line, linesize = bytes * p->fontheight, rows;
3454 u_char *src,*dst;
3455
3456 if (sx == 0 && dx == 0 && width * 16 == bytes) {
3457 mymemmove(p->screen_base + dy * linesize,
3458 p->screen_base + sy * linesize,
3459 height * linesize);
3460 }
3461 else {
3462 if (dy < sy || (dy == sy && dx < sx)) {
3463 src = p->screen_base + sy * linesize + sx * 16;
3464 dst = p->screen_base + dy * linesize + dx * 16;
3465 for (rows = height * p->fontheight ; rows-- ;) {
3466 mymemmove(dst, src, width * 16);
3467 src += bytes;
3468 dst += bytes;
3469 }
3470 }
3471 else {
3472 src = p->screen_base + (sy+height) * linesize + sx * 16
3473 - bytes;
3474 dst = p->screen_base + (dy+height) * linesize + dx * 16
3475 - bytes;
3476 for (rows = height * p->fontheight ; rows-- ;) {
3477 mymemmove(dst, src, width * 16);
3478 src -= bytes;
3479 dst -= bytes;
3480 }
3481 }
3482 }
3483 }
3484
3485
3486 static void clear_16_packed(struct vc_data *conp, struct display *p, int sy,
3487 int sx, int height, int width)
3488 {
3489 u_char *dest0,*dest;
3490 int bytes=p->next_line,lines=height * p->fontheight, rows, i;
3491 u_long bgx;
3492
3493 dest = p->screen_base + sy * p->fontheight * bytes + sx * 16;
3494
3495 bgx = attr_bgcol_ec(p,conp);
3496 bgx = packed16_cmap[bgx];
3497 bgx |= (bgx << 16);
3498
3499 if (sx == 0 && width * 16 == bytes) {
3500 for (i = 0 ; i < lines * width ; i++) {
3501 ((u_long *)dest)[0]=bgx;
3502 ((u_long *)dest)[1]=bgx;
3503 ((u_long *)dest)[2]=bgx;
3504 ((u_long *)dest)[3]=bgx;
3505 dest+=16;
3506 }
3507 } else {
3508 dest0=dest;
3509 for (rows = lines; rows-- ; dest0 += bytes) {
3510 dest=dest0;
3511 for (i = 0 ; i < width ; i++) {
3512 ((u_long *)dest)[0]=bgx;
3513 ((u_long *)dest)[1]=bgx;
3514 ((u_long *)dest)[2]=bgx;
3515 ((u_long *)dest)[3]=bgx;
3516 dest+=16;
3517 }
3518 }
3519 }
3520 }
3521
3522
3523 static void putc_16_packed(struct vc_data *conp, struct display *p, int c,
3524 int y, int x)
3525 {
3526 u_char *dest,*cdat;
3527 int bytes=p->next_line,rows;
3528 ulong eorx,fgx,bgx;
3529
3530 c &= 0xff;
3531
3532 dest = p->screen_base + y * p->fontheight * bytes + x * 16;
3533 cdat = p->fontdata + c * p->fontheight;
3534
3535 fgx = attr_fgcol(p,conp);
3536 fgx = packed16_cmap[fgx];
3537 bgx = attr_bgcol(p,conp);
3538 bgx = packed16_cmap[bgx];
3539 fgx |= (fgx << 16);
3540 bgx |= (bgx << 16);
3541 eorx = fgx ^ bgx;
3542
3543 for (rows = p->fontheight ; rows-- ; dest += bytes) {
3544 ((u_long *)dest)[0]=
3545 (tab_16_packed[*cdat >> 6] & eorx) ^ bgx;
3546 ((u_long *)dest)[1]=
3547 (tab_16_packed[*cdat >> 4 & 0x3] & eorx) ^ bgx;
3548 ((u_long *)dest)[2]=
3549 (tab_16_packed[*cdat >> 2 & 0x3] & eorx) ^ bgx;
3550 ((u_long *)dest)[3]=
3551 (tab_16_packed[*cdat++ & 0x3] & eorx) ^ bgx;
3552 }
3553 }
3554
3555
3556
3557 static void putcs_16_packed(struct vc_data *conp, struct display *p,
3558 const char *s, int count, int y, int x)
3559 {
3560 u_char *cdat, c, *dest, *dest0;
3561 int rows,bytes=p->next_line;
3562 u_long eorx, fgx, bgx;
3563
3564 dest0 = p->screen_base + y * p->fontheight * bytes + x * 16;
3565 fgx = attr_fgcol(p,conp);
3566 fgx = packed16_cmap[fgx];
3567 bgx = attr_bgcol(p,conp);
3568 bgx = packed16_cmap[bgx];
3569 fgx |= (fgx << 16);
3570 bgx |= (bgx << 16);
3571 eorx = fgx ^ bgx;
3572 while (count--) {
3573 c = *s++;
3574 cdat = p->fontdata + c * p->fontheight;
3575
3576 for (rows = p->fontheight, dest = dest0; rows-- ; dest += bytes) {
3577 ((u_long *)dest)[0]=
3578 (tab_16_packed[*cdat >> 6] & eorx) ^ bgx;
3579 ((u_long *)dest)[1]=
3580 (tab_16_packed[*cdat >> 4 & 0x3] & eorx) ^ bgx;
3581 ((u_long *)dest)[2]=
3582 (tab_16_packed[*cdat >> 2 & 0x3] & eorx) ^ bgx;
3583 ((u_long *)dest)[3]=
3584 (tab_16_packed[*cdat++ & 0x3] & eorx) ^ bgx;
3585 }
3586 dest0+=16;
3587 }
3588 }
3589
3590
3591 static void rev_char_16_packed(struct display *p, int x, int y)
3592 {
3593 u_char *dest;
3594 int bytes=p->next_line, rows;
3595
3596 dest = p->screen_base + y * p->fontheight * bytes + x * 16;
3597 for (rows = p->fontheight ; rows-- ; dest += bytes) {
3598 ((u_long *)dest)[0] ^= 0xffffffff;
3599 ((u_long *)dest)[1] ^= 0xffffffff;
3600 ((u_long *)dest)[2] ^= 0xffffffff;
3601 ((u_long *)dest)[3] ^= 0xffffffff;
3602 }
3603 }
3604
3605 #endif
3606
3607
3608
3609
3610 #ifdef CONFIG_FBCON_CYBER
3611
3612
3613
3614
3615
3616 static void bmove_cyber(struct display *p, int sy, int sx, int dy, int dx,
3617 int height, int width)
3618 {
3619 sx *= 8; dx *= 8; width *= 8;
3620 Cyber_BitBLT((u_short)sx, (u_short)(sy*p->fontheight), (u_short)dx,
3621 (u_short)(dy*p->fontheight), (u_short)width,
3622 (u_short)(height*p->fontheight), (u_short)S3_NEW);
3623 }
3624
3625
3626 static void clear_cyber(struct vc_data *conp, struct display *p, int sy, int sx,
3627 int height, int width)
3628 {
3629 u_char bg;
3630
3631 sx *= 8; width *= 8;
3632 bg = attr_bgcol_ec(p,conp);
3633 Cyber_RectFill((u_short)sx, (u_short)(sy*p->fontheight), (u_short)width,
3634 (u_short)(height*p->fontheight), (u_short)S3_NEW,
3635 (u_short)bg);
3636 }
3637
3638
3639 static void putc_cyber(struct vc_data *conp, struct display *p, int c, int y,
3640 int x)
3641 {
3642 u_char *dest, *cdat;
3643 u_long tmp;
3644 u_int rows, reverse, underline;
3645 u_char d;
3646 u_char fg, bg;
3647
3648 c &= 0xff;
3649
3650 dest = p->screen_base+y*p->fontheight*p->next_line+8*x;
3651 cdat = p->fontdata+(c*p->fontheight);
3652 fg = disp->fgcol;
3653 bg = disp->bgcol;
3654 reverse = conp->vc_reverse;
3655 underline = conp->vc_underline;
3656
3657 Cyber_WaitBlit();
3658 for (rows = p->fontheight; rows--; dest += p->next_line) {
3659 d = *cdat++;
3660
3661 if (underline && !rows)
3662 d = 0xff;
3663 if (reverse)
3664 d = ~d;
3665
3666 tmp = ((d & 0x80) ? fg : bg) << 24;
3667 tmp |= ((d & 0x40) ? fg : bg) << 16;
3668 tmp |= ((d & 0x20) ? fg : bg) << 8;
3669 tmp |= ((d & 0x10) ? fg : bg);
3670 *((u_long*) dest) = tmp;
3671 tmp = ((d & 0x8) ? fg : bg) << 24;
3672 tmp |= ((d & 0x4) ? fg : bg) << 16;
3673 tmp |= ((d & 0x2) ? fg : bg) << 8;
3674 tmp |= ((d & 0x1) ? fg : bg);
3675 *((u_long*) dest + 1) = tmp;
3676 }
3677 }
3678
3679
3680 static void putcs_cyber(struct vc_data *conp, struct display *p, const char *s,
3681 int count, int y, int x)
3682 {
3683 u_char *dest, *dest0, *cdat;
3684 u_long tmp;
3685 u_int rows, reverse, underline;
3686 u_char c, d;
3687 u_char fg, bg;
3688
3689 dest0 = p->screen_base+y*p->fontheight*p->next_line+8*x;
3690 fg = disp->fgcol;
3691 bg = disp->bgcol;
3692 reverse = conp->vc_reverse;
3693 underline = conp->vc_underline;
3694
3695 Cyber_WaitBlit();
3696 while (count--) {
3697 c = *s++;
3698 dest = dest0;
3699 dest0 += 8;
3700 cdat = p->fontdata+(c*p->fontheight);
3701 for (rows = p->fontheight; rows--; dest += p->next_line) {
3702 d = *cdat++;
3703
3704 if (underline && !rows)
3705 d = 0xff;
3706 if (reverse)
3707 d = ~d;
3708
3709 tmp = ((d & 0x80) ? fg : bg) << 24;
3710 tmp |= ((d & 0x40) ? fg : bg) << 16;
3711 tmp |= ((d & 0x20) ? fg : bg) << 8;
3712 tmp |= ((d & 0x10) ? fg : bg);
3713 *((u_long*) dest) = tmp;
3714 tmp = ((d & 0x8) ? fg : bg) << 24;
3715 tmp |= ((d & 0x4) ? fg : bg) << 16;
3716 tmp |= ((d & 0x2) ? fg : bg) << 8;
3717 tmp |= ((d & 0x1) ? fg : bg);
3718 *((u_long*) dest + 1) = tmp;
3719 }
3720 }
3721 }
3722
3723
3724 static void rev_char_cyber(struct display *p, int x, int y)
3725 {
3726 u_char *dest;
3727 u_int rows;
3728 u_char fg, bg;
3729
3730 fg = disp->fgcol;
3731 bg = disp->bgcol;
3732
3733 dest = p->screen_base+y*p->fontheight*p->next_line+8*x;
3734 Cyber_WaitBlit();
3735 for (rows = p->fontheight; rows--; dest += p->next_line) {
3736 *dest = (*dest == fg) ? bg : fg;
3737 *(dest+1) = (*(dest + 1) == fg) ? bg : fg;
3738 *(dest+2) = (*(dest + 2) == fg) ? bg : fg;
3739 *(dest+3) = (*(dest + 3) == fg) ? bg : fg;
3740 *(dest+4) = (*(dest + 4) == fg) ? bg : fg;
3741 *(dest+5) = (*(dest + 5) == fg) ? bg : fg;
3742 *(dest+6) = (*(dest + 6) == fg) ? bg : fg;
3743 *(dest+7) = (*(dest + 7) == fg) ? bg : fg;
3744 }
3745 }
3746
3747 #endif
3748
3749
3750
3751
3752
3753
3754
3755
3756 struct consw fb_con = {
3757 fbcon_startup, fbcon_init, fbcon_deinit, fbcon_clear, fbcon_putc,
3758 fbcon_putcs, fbcon_cursor, fbcon_scroll, fbcon_bmove, fbcon_switch,
3759 fbcon_blank, fbcon_get_font, fbcon_set_font
3760 };