Subversion Repositories HelenOS-historic

Rev

Rev 1547 | Rev 1555 | Go to most recent revision | Show entire file | Ignore whitespace | Details | Blame | Last modification | View Log | RSS feed

Rev 1547 Rev 1552
Line 81... Line 81...
81
    /* Auto-cursor position */
81
    /* Auto-cursor position */
82
    int cursor_active, cur_col, cur_row;
82
    int cursor_active, cur_col, cur_row;
83
    int cursor_shown;
83
    int cursor_shown;
84
} viewport_t;
84
} viewport_t;
85
 
85
 
-
 
86
/** Maximum number of saved pixmaps
-
 
87
 * Pixmap is a saved rectangle
-
 
88
 */
-
 
89
#define MAX_PIXMAPS        256
-
 
90
typedef struct {
-
 
91
    unsigned int width;
-
 
92
    unsigned int height;
-
 
93
    void *data;
-
 
94
} pixmap_t;
-
 
95
static pixmap_t pixmaps[MAX_PIXMAPS];
-
 
96
 
-
 
97
/* Viewport is a rectangular area on the screen */
86
#define MAX_VIEWPORTS 128
98
#define MAX_VIEWPORTS 128
87
static viewport_t viewports[128];
99
static viewport_t viewports[128];
88
 
100
 
89
/* Allow only 1 connection */
101
/* Allow only 1 connection */
90
static int client_connected = 0;
102
static int client_connected = 0;
Line 284... Line 296...
284
    for (x = 0; x < COL_WIDTH; x++)
296
    for (x = 0; x < COL_WIDTH; x++)
285
        for (y = 0; y < FONT_SCANLINES; y++)
297
        for (y = 0; y < FONT_SCANLINES; y++)
286
            invert_pixel(vp, col * COL_WIDTH + x, row * FONT_SCANLINES + y);
298
            invert_pixel(vp, col * COL_WIDTH + x, row * FONT_SCANLINES + y);
287
}
299
}
288
 
300
 
289
static void draw_logo(int vp,unsigned int startx, unsigned int starty)
-
 
290
{
-
 
291
    unsigned int x;
-
 
292
    unsigned int y;
-
 
293
    unsigned int byte;
-
 
294
    unsigned int rowbytes;
-
 
295
 
-
 
296
    rowbytes = (helenos_width - 1) / 8 + 1;
-
 
297
 
-
 
298
    for (y = 0; y < helenos_height; y++)
-
 
299
        for (x = 0; x < helenos_width; x++) {
-
 
300
            byte = helenos_bits[rowbytes * y + x / 8];
-
 
301
            byte >>= x % 8;
-
 
302
            if (byte & 1)
-
 
303
                putpixel(vp ,startx + x, starty + y, viewports[vp].style.fg_color);
-
 
304
        }
-
 
305
}
-
 
306
 
-
 
307
/***************************************************************/
301
/***************************************************************/
308
/* Stdout specific functions */
302
/* Stdout specific functions */
309
 
303
 
310
 
304
 
311
/** Create new viewport
305
/** Create new viewport
Line 393... Line 387...
393
   
387
   
394
    /* Create first viewport */
388
    /* Create first viewport */
395
    viewport_create(0,0,xres,yres);
389
    viewport_create(0,0,xres,yres);
396
}
390
}
397
 
391
 
-
 
392
/** Hide cursor if it is shown */
398
static void cursor_hide(int vp)
393
static void cursor_hide(int vp)
399
{
394
{
400
    viewport_t *vport = &viewports[vp];
395
    viewport_t *vport = &viewports[vp];
401
 
396
 
402
    if (vport->cursor_active && vport->cursor_shown) {
397
    if (vport->cursor_active && vport->cursor_shown) {
403
        invert_char(vp, vport->cur_row, vport->cur_col);
398
        invert_char(vp, vport->cur_row, vport->cur_col);
404
        vport->cursor_shown = 0;
399
        vport->cursor_shown = 0;
405
    }
400
    }
406
}
401
}
407
 
402
 
-
 
403
/** Show cursor if cursor showing is enabled */
408
static void cursor_print(int vp)
404
static void cursor_print(int vp)
409
{
405
{
410
    viewport_t *vport = &viewports[vp];
406
    viewport_t *vport = &viewports[vp];
411
 
407
 
412
    /* Do not check for cursor_shown */
408
    /* Do not check for cursor_shown */
Line 414... Line 410...
414
        invert_char(vp, vport->cur_row, vport->cur_col);
410
        invert_char(vp, vport->cur_row, vport->cur_col);
415
        vport->cursor_shown = 1;
411
        vport->cursor_shown = 1;
416
    }
412
    }
417
}
413
}
418
 
414
 
-
 
415
/** Invert cursor, if it is enabled */
419
static void cursor_blink(int vp)
416
static void cursor_blink(int vp)
420
{
417
{
421
    viewport_t *vport = &viewports[vp];
418
    viewport_t *vport = &viewports[vp];
422
 
419
 
423
    if (vport->cursor_shown)
420
    if (vport->cursor_shown)
Line 455... Line 452...
455
            vport->cur_row--;
452
            vport->cur_row--;
456
    }
453
    }
457
    cursor_print(vp);
454
    cursor_print(vp);
458
}
455
}
459
 
456
 
-
 
457
/** Draw text data to viewport
-
 
458
 *
-
 
459
 * @param vp Viewport id
-
 
460
 * @param data Text data fitting exactly into viewport
-
 
461
 */
460
static void draw_text_data(int vp, keyfield_t *data)
462
static void draw_text_data(int vp, keyfield_t *data)
461
{
463
{
462
    viewport_t *vport = &viewports[vp];
464
    viewport_t *vport = &viewports[vp];
463
    int i;
465
    int i;
464
    char c;
466
    char c;
Line 473... Line 475...
473
        draw_glyph(vp, data[i].character, col * COL_WIDTH, row * FONT_SCANLINES, data[i].style);
475
        draw_glyph(vp, data[i].character, col * COL_WIDTH, row * FONT_SCANLINES, data[i].style);
474
    }
476
    }
475
    cursor_print(vp);
477
    cursor_print(vp);
476
}
478
}
477
 
479
 
-
 
480
/** Handle shared memory communication calls
-
 
481
 *
-
 
482
 * Protocol for drawing pixmaps:
-
 
483
 * - FB_PREPARE_SHM(client shm identification)
-
 
484
 * - IPC_M_SEND_AS_AREA
-
 
485
 * - FB_DRAW_PPM(startx,starty)
-
 
486
 * - FB_DROP_SHM
-
 
487
 *
-
 
488
 * Protocol for text drawing
-
 
489
 * - IPC_M_SEND_AS_AREA
-
 
490
 * - FB_DRAW_TEXT_DATA
-
 
491
 *
-
 
492
 * @param callid Callid of the current call
-
 
493
 * @param call Current call data
-
 
494
 * @param vp Active viewport
-
 
495
 * @return 0 if the call was not handled byt this function, 1 otherwise
-
 
496
 *
-
 
497
 * note: this function is not threads safe, you would have
-
 
498
 * to redefine static variables with __thread
-
 
499
 */
478
static int shm_handle(ipc_callid_t callid, ipc_call_t *call, int vp)
500
static int shm_handle(ipc_callid_t callid, ipc_call_t *call, int vp)
479
{
501
{
480
    static keyfield_t *interbuffer = NULL;
502
    static keyfield_t *interbuffer = NULL;
481
    static size_t intersize = 0;
503
    static size_t intersize = 0;
482
 
504
 
Line 556... Line 578...
556
    if (handled)
578
    if (handled)
557
        ipc_answer_fast(callid, retval, 0, 0);
579
        ipc_answer_fast(callid, retval, 0, 0);
558
    return handled;
580
    return handled;
559
}
581
}
560
 
582
 
-
 
583
/** Return first free pixmap */
-
 
584
static int find_free_pixmap(void)
-
 
585
{
-
 
586
    int i;
-
 
587
   
-
 
588
    for (i=0;i < MAX_PIXMAPS;i++)
-
 
589
        if (!pixmaps[i].data)
-
 
590
            return i;
-
 
591
    return -1;
-
 
592
}
-
 
593
 
-
 
594
/** Save viewport to pixmap */
-
 
595
static int save_vp_to_pixmap(int vp)
-
 
596
{
-
 
597
    int pm;
-
 
598
    pixmap_t *pmap;
-
 
599
    viewport_t *vport = &viewports[vp];
-
 
600
    int x,y;
-
 
601
    int rowsize;
-
 
602
    int tmp;
-
 
603
 
-
 
604
    pm = find_free_pixmap();
-
 
605
    if (pm == -1)
-
 
606
        return ELIMIT;
-
 
607
   
-
 
608
    pmap = &pixmaps[pm];
-
 
609
    pmap->data = malloc(screen.pixelbytes * vport->width * vport->height);
-
 
610
    if (!pmap->data)
-
 
611
        return ENOMEM;
-
 
612
 
-
 
613
    pmap->width = vport->width;
-
 
614
    pmap->height = vport->height;
-
 
615
   
-
 
616
    rowsize = vport->width * screen.pixelbytes;
-
 
617
    for (y=0;y < vport->height; y++) {
-
 
618
        tmp = (vport->y + y) * screen.scanline + vport->x * screen.pixelbytes;
-
 
619
        memcpy(pmap->data + rowsize*y, screen.fbaddress + tmp, rowsize);
-
 
620
    }
-
 
621
    return pm;
-
 
622
}
-
 
623
 
-
 
624
/** Draw pixmap on screen
-
 
625
 *
-
 
626
 * @param vp Viewport to draw on
-
 
627
 * @param pm Pixmap identifier
-
 
628
 */
-
 
629
static int draw_pixmap(int vp, int pm)
-
 
630
{
-
 
631
    pixmap_t *pmap = &pixmaps[pm];
-
 
632
    viewport_t *vport = &viewports[vp];
-
 
633
    int x,y;
-
 
634
    int tmp, srcrowsize;
-
 
635
    int realwidth, realheight, realrowsize;
-
 
636
 
-
 
637
    if (!pmap->data)
-
 
638
        return EINVAL;
-
 
639
 
-
 
640
    realwidth = pmap->width <= vport->width ? pmap->width : vport->width;
-
 
641
    realheight = pmap->height <= vport->height ? pmap->height : vport->height;
-
 
642
 
-
 
643
    srcrowsize = vport->width * screen.pixelbytes;
-
 
644
    realrowsize = realwidth * screen.pixelbytes;
-
 
645
 
-
 
646
    for (y=0; y < realheight; y++) {
-
 
647
        tmp = (vport->y + y) * screen.scanline + vport->x * screen.pixelbytes;
-
 
648
        memcpy(screen.fbaddress + tmp, pmap->data + y * srcrowsize, realrowsize);
-
 
649
    }
-
 
650
}
-
 
651
 
-
 
652
/** Handler for messages concerning pixmap handling */
-
 
653
static int pixmap_handle(ipc_callid_t callid, ipc_call_t *call, int vp)
-
 
654
{
-
 
655
    int handled = 1;
-
 
656
    int retval = 0;
-
 
657
    int i,nvp;
-
 
658
 
-
 
659
    switch (IPC_GET_METHOD(*call)) {
-
 
660
    case FB_VP_DRAW_PIXMAP:
-
 
661
        nvp = IPC_GET_ARG1(*call);
-
 
662
        if (nvp == -1)
-
 
663
            nvp = vp;
-
 
664
        if (nvp < 0 || nvp >= MAX_VIEWPORTS || !viewports[nvp].initialized) {
-
 
665
            retval = EINVAL;
-
 
666
            break;
-
 
667
        }
-
 
668
        i = IPC_GET_ARG2(*call);
-
 
669
        retval = draw_pixmap(nvp, i);
-
 
670
        break;
-
 
671
    case FB_VP2PIXMAP:
-
 
672
        nvp = IPC_GET_ARG1(*call);
-
 
673
        if (nvp == -1)
-
 
674
            nvp = vp;
-
 
675
        if (nvp < 0 || nvp >= MAX_VIEWPORTS || !viewports[nvp].initialized)
-
 
676
            retval = EINVAL;
-
 
677
        else
-
 
678
            retval = save_vp_to_pixmap(nvp);
-
 
679
        break;
-
 
680
    case FB_DROP_PIXMAP:
-
 
681
        i = IPC_GET_ARG1(*call);
-
 
682
        if (i >= MAX_PIXMAPS) {
-
 
683
            retval = EINVAL;
-
 
684
            break;
-
 
685
        }
-
 
686
        if (pixmaps[i].data) {
-
 
687
            free(pixmaps[i].data);
-
 
688
            pixmaps[i].data = NULL;
-
 
689
        }
-
 
690
        break;
-
 
691
    default:
-
 
692
        handled = 0;
-
 
693
    }
-
 
694
 
-
 
695
    if (handled)
-
 
696
        ipc_answer_fast(callid, retval, 0, 0);
-
 
697
    return handled;
-
 
698
   
-
 
699
}
-
 
700
 
561
/** Function for handling connections to FB
701
/** Function for handling connections to FB
562
 *
702
 *
563
 */
703
 */
564
static void fb_client_connection(ipc_callid_t iid, ipc_call_t *icall)
704
static void fb_client_connection(ipc_callid_t iid, ipc_call_t *icall)
565
{
705
{
Line 586... Line 726...
586
            cursor_blink(vp);
726
            cursor_blink(vp);
587
            continue;
727
            continue;
588
        }
728
        }
589
        if (shm_handle(callid, &call, vp))
729
        if (shm_handle(callid, &call, vp))
590
            continue;
730
            continue;
-
 
731
        if (pixmap_handle(callid, &call, vp))
-
 
732
            continue;
591
 
733
 
592
        switch (IPC_GET_METHOD(call)) {
734
        switch (IPC_GET_METHOD(call)) {
593
        case IPC_M_PHONE_HUNGUP:
735
        case IPC_M_PHONE_HUNGUP:
594
            client_connected = 0;
736
            client_connected = 0;
595
            /* cleanup other viewports */
737
            /* cleanup other viewports */