Changes in kernel/genarch/src/fb/fb.c [888c06e:de96d3b] in mainline
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
kernel/genarch/src/fb/fb.c
r888c06e rde96d3b 81 81 ((glyph) * (instance)->glyphbytes + (y) * (instance)->glyphscanline) 82 82 83 #define TAB_WIDTH 884 85 83 typedef void (*rgb_conv_t)(void *, uint32_t); 86 84 … … 101 99 102 100 /** Number of rows that fit on framebuffer */ 103 unsigned int screen_rows;101 unsigned int rowtrim; 104 102 105 103 unsigned int scanline; … … 123 121 /** Current backbuffer position */ 124 122 unsigned int position; 125 126 /** Partial character between writes */127 mbstate_t mbstate;128 129 unsigned int row;130 unsigned int column;131 123 } fb_instance_t; 132 124 133 static void fb_ write(outdev_t *, const char *, size_t);125 static void fb_putuchar(outdev_t *, char32_t); 134 126 static void fb_redraw(outdev_t *); 135 127 static void fb_scroll_up(outdev_t *); … … 137 129 138 130 static outdev_operations_t fbdev_ops = { 139 .write = fb_ write,131 .write = fb_putuchar, 140 132 .redraw = fb_redraw, 141 133 .scroll_up = fb_scroll_up, … … 255 247 256 248 unsigned int rel_row = row - instance->offset_row; 257 if (rel_row >= instance-> screen_rows)249 if (rel_row >= instance->rowtrim) 258 250 return; 259 251 … … 267 259 } 268 260 261 /** Scroll screen down by one row 262 * 263 */ 264 static void screen_scroll(fb_instance_t *instance) 265 { 266 if ((!instance->parea.mapped) || (console_override)) { 267 for (unsigned int rel_row = 0; rel_row < instance->rowtrim; rel_row++) { 268 unsigned int y = ROW2Y(rel_row); 269 unsigned int row = rel_row + instance->offset_row; 270 271 for (unsigned int yd = 0; yd < FONT_SCANLINES; yd++) { 272 unsigned int x; 273 unsigned int col; 274 size_t bb_pos = BB_POS(instance, 0, row); 275 size_t bb_pos1 = BB_POS(instance, 0, row + 1); 276 277 for (col = 0, x = 0; col < instance->cols; 278 col++, x += FONT_WIDTH) { 279 uint16_t glyph; 280 281 if (row < instance->rows - 1) { 282 if (instance->backbuf[bb_pos] == 283 instance->backbuf[bb_pos1]) 284 goto skip; 285 286 glyph = instance->backbuf[bb_pos1]; 287 } else 288 glyph = 0; 289 290 memcpy(&instance->addr[FB_POS(instance, x, y + yd)], 291 &instance->glyphs[GLYPH_POS(instance, glyph, yd)], 292 instance->glyphscanline); 293 skip: 294 BB_NEXT_COL(bb_pos); 295 BB_NEXT_COL(bb_pos1); 296 } 297 } 298 } 299 } 300 301 /* 302 * Implement backbuffer scrolling by wrapping around 303 * the cyclic buffer. 304 */ 305 306 instance->start_row++; 307 if (instance->start_row == instance->rows) 308 instance->start_row = 0; 309 310 memsetw(&instance->backbuf[BB_POS(instance, 0, instance->rows - 1)], 311 instance->cols, 0); 312 } 313 269 314 static void cursor_put(fb_instance_t *instance) 270 315 { 271 unsigned int col = instance-> column;272 unsigned int row = instance-> row;316 unsigned int col = instance->position % instance->cols; 317 unsigned int row = instance->position / instance->cols; 273 318 274 319 glyph_draw(instance, fb_font_glyph(U_CURSOR), col, row, true); … … 277 322 static void cursor_remove(fb_instance_t *instance) 278 323 { 279 unsigned int col = instance-> column;280 unsigned int row = instance-> row;324 unsigned int col = instance->position % instance->cols; 325 unsigned int row = instance->position / instance->cols; 281 326 282 327 glyph_draw(instance, instance->backbuf[BB_POS(instance, col, row)], … … 328 373 static void fb_redraw_internal(fb_instance_t *instance) 329 374 { 330 for (unsigned int rel_row = 0; rel_row < instance-> screen_rows; rel_row++) {375 for (unsigned int rel_row = 0; rel_row < instance->rowtrim; rel_row++) { 331 376 unsigned int y = ROW2Y(rel_row); 332 377 unsigned int row = rel_row + instance->offset_row; … … 359 404 } 360 405 361 if (ROW2Y(instance-> screen_rows) < instance->yres) {406 if (ROW2Y(instance->rowtrim) < instance->yres) { 362 407 unsigned int y; 363 408 364 for (y = ROW2Y(instance-> screen_rows); y < instance->yres; y++)409 for (y = ROW2Y(instance->rowtrim); y < instance->yres; y++) 365 410 memcpy(&instance->addr[FB_POS(instance, 0, y)], 366 411 instance->bgscan, instance->bgscanbytes); … … 368 413 } 369 414 370 /** Scroll screen down by one row371 *372 */373 static void screen_scroll(fb_instance_t *instance)374 {375 /*376 * Implement backbuffer scrolling by wrapping around377 * the cyclic buffer.378 */379 380 instance->start_row++;381 if (instance->start_row == instance->rows)382 instance->start_row = 0;383 384 if ((!instance->parea.mapped) || (console_override)) {385 fb_redraw_internal(instance);386 }387 }388 389 static void _advance_row(fb_instance_t *instance)390 {391 instance->column = 0;392 instance->row++;393 }394 395 static void _advance_column(fb_instance_t *instance)396 {397 instance->column++;398 if (instance->column == instance->cols)399 _advance_row(instance);400 }401 402 415 /** Print character to screen 403 416 * … … 405 418 * 406 419 */ 407 static void _putuchar(fb_instance_t *instance, char32_t ch) 408 { 420 static void fb_putuchar(outdev_t *dev, char32_t ch) 421 { 422 fb_instance_t *instance = (fb_instance_t *) dev->data; 423 spinlock_lock(&instance->lock); 424 409 425 switch (ch) { 410 426 case '\n': 411 _advance_row(instance); 427 cursor_remove(instance); 428 instance->position += instance->cols; 429 instance->position -= instance->position % instance->cols; 412 430 break; 413 431 case '\r': 414 instance->column = 0; 432 cursor_remove(instance); 433 instance->position -= instance->position % instance->cols; 415 434 break; 416 435 case '\b': 417 if (instance->column > 0) 418 instance->column--; 436 cursor_remove(instance); 437 if (instance->position % instance->cols) 438 instance->position--; 419 439 break; 420 440 case '\t': 441 cursor_remove(instance); 421 442 do { 422 443 glyph_draw(instance, fb_font_glyph(' '), 423 instance->column, 424 instance->row, false); 425 _advance_column(instance); 426 } while (instance->column % TAB_WIDTH != 0); 444 instance->position % instance->cols, 445 instance->position / instance->cols, false); 446 instance->position++; 447 } while (((instance->position % instance->cols) % 8 != 0) && 448 (instance->position < instance->cols * instance->rows)); 427 449 break; 428 450 default: 429 451 glyph_draw(instance, fb_font_glyph(ch), 430 instance-> column,431 instance-> row, false);432 _advance_column(instance);433 } 434 435 while (instance->row >=instance->rows) {436 instance-> row--;452 instance->position % instance->cols, 453 instance->position / instance->cols, false); 454 instance->position++; 455 } 456 457 if (instance->position >= instance->cols * instance->rows) { 458 instance->position -= instance->cols; 437 459 screen_scroll(instance); 438 460 } 439 }440 441 static void fb_write(outdev_t *dev, const char *s, size_t n)442 {443 fb_instance_t *instance = (fb_instance_t *) dev->data;444 445 spinlock_lock(&instance->lock);446 cursor_remove(instance);447 448 size_t offset = 0;449 char32_t ch;450 451 while ((ch = str_decode_r(s, &offset, n, U_SPECIAL, &instance->mbstate)))452 _putuchar(instance, ch);453 461 454 462 cursor_put(instance); 463 455 464 spinlock_unlock(&instance->lock); 456 465 } … … 464 473 spinlock_lock(&instance->lock); 465 474 466 if (instance->offset_row >= instance-> screen_rows/ 2)467 instance->offset_row -= instance-> screen_rows/ 2;475 if (instance->offset_row >= instance->rowtrim / 2) 476 instance->offset_row -= instance->rowtrim / 2; 468 477 else 469 478 instance->offset_row = 0; … … 483 492 spinlock_lock(&instance->lock); 484 493 485 if (instance->offset_row + instance-> screen_rows/ 2 <=486 instance->rows - instance-> screen_rows)487 instance->offset_row += instance-> screen_rows/ 2;494 if (instance->offset_row + instance->rowtrim / 2 <= 495 instance->rows - instance->rowtrim) 496 instance->offset_row += instance->rowtrim / 2; 488 497 else 489 instance->offset_row = instance->rows - instance-> screen_rows;498 instance->offset_row = instance->rows - instance->rowtrim; 490 499 491 500 fb_redraw_internal(instance); … … 606 615 instance->scanline = props->scan; 607 616 608 instance-> screen_rows= Y2ROW(instance->yres);617 instance->rowtrim = Y2ROW(instance->yres); 609 618 610 619 instance->cols = X2COL(instance->xres); 611 instance->rows = FB_PAGES * instance-> screen_rows;612 613 instance->start_row = instance->rows - instance-> screen_rows;620 instance->rows = FB_PAGES * instance->rowtrim; 621 622 instance->start_row = instance->rows - instance->rowtrim; 614 623 instance->offset_row = instance->start_row; 615 instance->row = instance->start_row; 616 instance->column = 0; 624 instance->position = instance->start_row * instance->cols; 617 625 618 626 instance->glyphscanline = FONT_WIDTH * instance->pixelbytes;
Note:
See TracChangeset
for help on using the changeset viewer.