Changeset bb4fd0c in buchla-emu for emu


Ignore:
Timestamp:
07/23/2017 10:17:42 AM (7 years ago)
Author:
Thomas Lopatic <thomas@…>
Branches:
master
Children:
a23f3d9
Parents:
a1fd5d5
Message:

Started serial console.

Location:
emu
Files:
4 edited

Legend:

Unmodified
Added
Removed
  • emu/all.h

    ra1fd5d5 rbb4fd0c  
    2020#include <stdint.h>
    2121#include <stdio.h>
     22#include <string.h>
    2223#include <unistd.h>
    2324
     
    4546#define ARRAY_COUNT(_a) (int32_t)(sizeof (_a) / sizeof (_a)[0])
    4647
     48#define WIN_W (1520 * 2 / 3)
     49#define WIN_H (950 * 2 / 3)
     50
    4751extern int32_t sdl_verbose;
    4852extern int32_t cpu_verbose;
     
    5761extern int32_t led_verbose;
    5862extern int32_t kbd_verbose;
     63
     64extern SDL_Window *sdl_win;
     65extern SDL_Renderer *sdl_ren;
    5966
    6067extern void sdl_init(void);
     
    93100extern void ser_write(uint32_t off, int32_t sz, uint32_t val);
    94101
     102extern void ser_text(SDL_TextInputEvent *ev);
     103extern void ser_key(SDL_KeyboardEvent *ev);
     104
    95105extern void mid_init(void);
    96106extern void mid_quit(void);
  • emu/cpu.c

    ra1fd5d5 rbb4fd0c  
    9292static void hw_init(void)
    9393{
    94         inf("initializing hardware");
     94        inf("starting hardware");
    9595
    9696        for (int32_t i = 0; i < ARRAY_COUNT(hw_map); ++i) {
    9797                hw_map[i].init();
     98        }
     99}
     100
     101static void hw_quit(void)
     102{
     103        inf("halting hardware");
     104
     105        for (int32_t i = 0; i < ARRAY_COUNT(hw_map); ++i) {
     106                hw_map[i].quit();
    98107        }
    99108}
     
    611620
    612621        bool run = true;
     622        bool down = false;
    613623
    614624        while (run) {
     
    621631
    622632                while (SDL_PollEvent(&ev) > 0) {
    623                         if (ev.type == SDL_QUIT) {
     633                        // Work around duplicate key-down events on Linux.
     634
     635                        if (ev.type == SDL_KEYDOWN) {
     636                                if (down) {
     637                                        continue;
     638                                }
     639
     640                                down = true;
     641                        }
     642                        else if (ev.type == SDL_KEYUP) {
     643                                down = false;
     644                        }
     645
     646                        if (ev.type == SDL_QUIT ||
     647                                        (ev.type == SDL_KEYDOWN && ev.key.keysym.sym == SDLK_ESCAPE)) {
    624648                                run = false;
     649                                continue;
     650                        }
     651
     652                        if (ev.type == SDL_TEXTINPUT) {
     653                                ser_text(&ev.text);
     654                                continue;
     655                        }
     656
     657                        if (ev.type == SDL_KEYDOWN) {
     658                                ser_key(&ev.key);
     659                                continue;
    625660                        }
    626661                }
     
    632667
    633668        inf("leaving CPU loop");
    634 }
     669        hw_quit();
     670}
  • emu/sdl.c

    ra1fd5d5 rbb4fd0c  
    2424#define ver3(...) _ver(sdl_verbose, 2, __VA_ARGS__)
    2525
     26SDL_Window *sdl_win;
     27SDL_Renderer *sdl_ren;
     28
    2629void sdl_init(void)
    2730{
     
    3639                fail("TTF_Init() failed: %s", TTF_GetError());
    3740        }
     41
     42        SDL_SetHint(SDL_HINT_RENDER_SCALE_QUALITY, "1");
     43
     44        sdl_win = SDL_CreateWindow("Emu", SDL_WINDOWPOS_UNDEFINED, SDL_WINDOWPOS_UNDEFINED,
     45                        WIN_W, WIN_H, 0);
     46
     47        if (sdl_win == NULL) {
     48                fail("SDL_CreateWindow() failed: %s", SDL_GetError());
     49        }
     50
     51        sdl_ren = SDL_CreateRenderer(sdl_win, -1, 0);
     52
     53        if (sdl_ren == NULL) {
     54                fail("SDL_CreateRenderer() failed: %s", SDL_GetError());
     55        }
     56
     57        SDL_StartTextInput();
    3858}
    3959
    4060void sdl_quit(void)
    4161{
     62        SDL_DestroyRenderer(sdl_ren);
     63        SDL_DestroyWindow(sdl_win);
    4264        TTF_Quit();
    4365        SDL_Quit();
  • emu/ser.c

    ra1fd5d5 rbb4fd0c  
    2222#define ver3(...) _ver(ser_verbose, 2, __VA_ARGS__)
    2323
     24#define CON_W 80
     25#define CON_H 25
     26
     27#define CON_BGR 0x00000000
     28#define CON_CUR 0x00e87000
     29#define CON_FGR ((SDL_Color){ .r = 255, .b = 255, .g = 255, .a = 255 })
     30
     31#define CON_FONT "ttf/vera-sans-mono.ttf"
     32
    2433int32_t ser_verbose = 0;
    2534
     35static uint8_t mem[CON_H][CON_W + 1];
     36
     37static TTF_Font *fon;
     38static int32_t fon_w, fon_h;
     39
     40static int32_t sur_w, sur_h;
     41static SDL_Surface *sur;
     42
     43static int32_t cur_x = 0, cur_y = 0;
     44
     45static void update(void)
     46{
     47        if (SDL_FillRect(sur, NULL, CON_BGR) < 0) {
     48                fail("SDL_FillRect() failed: %s", SDL_GetError());
     49        }
     50
     51        if (SDL_FillRect(sur, &(SDL_Rect){
     52                .x = cur_x * fon_w,
     53                .y = cur_y * fon_h,
     54                .w = fon_w,
     55                .h = fon_h
     56        }, CON_CUR) < 0) {
     57                fail("SDL_FillRect() failed: %s", SDL_GetError());
     58        }
     59
     60        for (int32_t y = 0; y < CON_H; ++y) {
     61                SDL_Surface *lin = TTF_RenderText_Blended(fon, (char *)mem[y], CON_FGR);
     62
     63                if (lin == NULL) {
     64                        fail("TTF_RenderText_Blended() failed: %s", TTF_GetError());
     65                }
     66
     67                if (SDL_BlitSurface(lin, NULL, sur, &(SDL_Rect){
     68                        .x = 0,
     69                        .y = y * fon_h,
     70                        .w = CON_W * fon_w,
     71                        .h = fon_h
     72                })) {
     73                        fail("SDL_BlitSurface() failed: %s", SDL_GetError());
     74                }
     75
     76                SDL_FreeSurface(lin);
     77        }
     78
     79        SDL_Texture *tex = SDL_CreateTextureFromSurface(sdl_ren, sur);
     80
     81        if (tex == NULL) {
     82                fail("SDL_CreateTextureFromSurface() failed: %s", SDL_GetError());
     83        }
     84
     85        if (SDL_RenderCopy(sdl_ren, tex, NULL, NULL) < 0) {
     86                fail("SDL_RenderCopy() failed: %s", SDL_GetError());
     87        }
     88
     89        SDL_DestroyTexture(tex);
     90        SDL_RenderPresent(sdl_ren);
     91}
     92
     93static void scroll(void)
     94{
     95        memmove(mem, mem + 1, (CON_H - 1) * (CON_W + 1));
     96        memset(mem + (CON_H - 1), ' ', CON_W);
     97}
     98
     99static void forw(void)
     100{
     101        if (cur_x < CON_W - 1) {
     102                ++cur_x;
     103                return;
     104        }
     105
     106        if (cur_y == CON_H - 1) {
     107                cur_x = 0;
     108                scroll();
     109                return;
     110        }
     111
     112        cur_x = 0;
     113        ++cur_y;
     114}
     115
     116static void back(void)
     117{
     118        if (cur_x > 0) {
     119                --cur_x;
     120                return;
     121        }
     122
     123        if (cur_y == 0) {
     124                return;
     125        }
     126
     127        cur_x = CON_W - 1;
     128        --cur_y;
     129}
     130
     131static void down(void)
     132{
     133        if (cur_y < CON_H - 1) {
     134                ++cur_y;
     135                return;
     136        }
     137
     138        scroll();
     139}
     140
     141static void echo(uint8_t c)
     142{
     143        switch (c) {
     144        case '\r':
     145                cur_x = 0;
     146                break;
     147
     148        case '\n':
     149                down();
     150                break;
     151
     152        case '\b':
     153                back();
     154                break;
     155
     156        default:
     157                if (c < 32) {
     158                        echo('^');
     159                        echo((uint8_t)(c + '@'));
     160                        return;
     161                }
     162
     163                mem[cur_y][cur_x] = c;
     164                forw();
     165                break;
     166        }
     167
     168        update();
     169}
     170
     171void ser_key(SDL_KeyboardEvent *ev)
     172{
     173        switch (ev->keysym.sym) {
     174        case SDLK_BACKSPACE:
     175                echo('\b');
     176                break;
     177
     178        case SDLK_RETURN:
     179                echo('\r');
     180                echo('\n');
     181                break;
     182        }
     183}
     184
     185void ser_text(SDL_TextInputEvent *ev)
     186{
     187        for (int32_t i = 0; ev->text[i] != 0; ++i) {
     188                echo((uint8_t)ev->text[i]);
     189        }
     190}
     191
    26192void ser_init(void)
    27193{
    28194        ver("ser init");
     195
     196        SDL_RWops *ops = SDL_RWFromFile(CON_FONT, "rb");
     197
     198        if (ops == NULL) {
     199                fail("error while opening font file " CON_FONT ": %s", SDL_GetError());
     200        }
     201
     202        fon = TTF_OpenFontRW(ops, 1, 32);
     203
     204        if (fon == NULL) {
     205                fail("error while loading font file " CON_FONT ": %s", TTF_GetError());
     206        }
     207
     208        fon_h = TTF_FontLineSkip(fon);
     209
     210        if (TTF_GlyphMetrics(fon, 'X', NULL, NULL, NULL, NULL, &fon_w) < 0) {
     211                fail("error while measuring font width: %s", TTF_GetError());
     212        }
     213
     214        sur_w = CON_W * fon_w;
     215        sur_h = CON_H * fon_h;
     216
     217        sur = SDL_CreateRGBSurface(0, sur_w, sur_h, 32, 0, 0, 0, 0);
     218
     219        if (sur == NULL) {
     220                fail("SDL_CreateRGBSurface() failed: %s", SDL_GetError());
     221        }
     222
     223        for (int32_t y = 0; y < CON_H; ++y) {
     224                for (int32_t x = 0; x < CON_W; ++x) {
     225                        mem[y][x] = ' ';
     226                }
     227
     228                mem[y][CON_W] = 0;
     229        }
     230
     231        update();
    29232}
    30233
     
    32235{
    33236        ver("ser quit");
     237
     238        SDL_FreeSurface(sur);
     239        TTF_CloseFont(fon);
    34240}
    35241
Note: See TracChangeset for help on using the changeset viewer.