From: Nils Faerber Date: Tue, 19 Mar 2013 19:24:35 +0000 (+0100) Subject: add missing files X-Git-Url: https://git.karo-electronics.de/?p=oswald.git;a=commitdiff_plain;h=dff6532fd5dbbd4a6c2f0fff2c428201b225c529 add missing files --- diff --git a/ui/embedvm.c b/ui/embedvm.c new file mode 100644 index 0000000..88ec457 --- /dev/null +++ b/ui/embedvm.c @@ -0,0 +1,311 @@ +/* + * EmbedVM - Embedded Virtual Machine for uC Applications + * + * Copyright (C) 2011 Clifford Wolf + * + * Permission to use, copy, modify, and/or distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + */ + +#include "embedvm.h" + +static inline int16_t signext(uint16_t val, uint16_t mask) +{ + val = val & mask; + if ((val & ~(mask >> 1)) != 0) + val |= ~mask; + return val; +} + +extern void embedvm_exec(struct embedvm_s *vm) +{ + uint8_t opcode = vm->mem_read(vm->ip, false, vm->user_ctx); + uint16_t addr = 0; + int16_t a = 0, b = 0; + int8_t sfa = 0; + + switch (opcode) + { + case 0x00 ... 0x3f: + sfa = signext(opcode, 0x3f); + embedvm_push(vm, embedvm_local_read(vm, sfa)); + vm->ip++; + break; + case 0x40 ... 0x7f: + sfa = signext(opcode, 0x3f); + embedvm_local_write(vm, sfa, embedvm_pop(vm)); + vm->ip++; + break; + case 0x80+0 ... 0x80+11: + case 0xa8+0 ... 0xa8+5: + b = embedvm_pop(vm); + case 0x80+12 ... 0x80+14: + a = embedvm_pop(vm); + switch (opcode) + { + case 0x80 + 0: embedvm_push(vm, a + b); break; + case 0x80 + 1: embedvm_push(vm, a - b); break; + case 0x80 + 2: embedvm_push(vm, a * b); break; + case 0x80 + 3: embedvm_push(vm, a / b); break; + case 0x80 + 4: embedvm_push(vm, a % b); break; + case 0x80 + 5: embedvm_push(vm, a << b); break; + case 0x80 + 6: embedvm_push(vm, a >> b); break; + case 0x80 + 7: embedvm_push(vm, a & b); break; + case 0x80 + 8: embedvm_push(vm, a | b); break; + case 0x80 + 9: embedvm_push(vm, a ^ b); break; + case 0x80 + 10: embedvm_push(vm, a && b); break; + case 0x80 + 11: embedvm_push(vm, a || b); break; + case 0x80 + 12: embedvm_push(vm, ~a); break; + case 0x80 + 13: embedvm_push(vm, -a); break; + case 0x80 + 14: embedvm_push(vm, !a); break; + case 0xa8 + 0: embedvm_push(vm, a < b); break; + case 0xa8 + 1: embedvm_push(vm, a <= b); break; + case 0xa8 + 2: embedvm_push(vm, a == b); break; + case 0xa8 + 3: embedvm_push(vm, a != b); break; + case 0xa8 + 4: embedvm_push(vm, a >= b); break; + case 0xa8 + 5: embedvm_push(vm, a > b); break; + + } + vm->ip++; + break; + case 0x90 ... 0x97: + a = signext(opcode, 0x07); + if ((a & 0x04) != 0) + a |= ~0x07; + embedvm_push(vm, a); + vm->ip++; + break; + case 0x98: + a = vm->mem_read(vm->ip+1, false, vm->user_ctx) & 0x00ff; + embedvm_push(vm, a); + vm->ip += 2; + break; + case 0x99: + a = vm->mem_read(vm->ip+1, false, vm->user_ctx) & 0x00ff; + embedvm_push(vm, signext(a, 0x00ff)); + vm->ip += 2; + break; + case 0x9a: + a = vm->mem_read(vm->ip+1, true, vm->user_ctx); + embedvm_push(vm, a); + vm->ip += 3; + break; + case 0x9b: + a = embedvm_pop(vm); + if (0) { + case 0x9c: + a = 0; + } + vm->sp = vm->sfp; + vm->ip = embedvm_pop(vm); + vm->sfp = embedvm_pop(vm); + if ((vm->sfp & 1) != 0) + vm->sfp &= ~1; + else + embedvm_push(vm, a); + break; + case 0x9d: + embedvm_pop(vm); + vm->ip++; + break; + case 0x9e: + addr = embedvm_pop(vm); + if (vm->mem_read(vm->ip+1, false, vm->user_ctx) == 0x9d) { + embedvm_push(vm, vm->sfp | 1); + embedvm_push(vm, vm->ip + 2); + } else { + embedvm_push(vm, vm->sfp); + embedvm_push(vm, vm->ip + 1); + } + vm->sfp = vm->sp; + vm->ip = addr; + break; + case 0x9f: + vm->ip = embedvm_pop(vm); + break; + case 0xa0 ... 0xa0+7: + if ((opcode & 1) == 0) { + addr = vm->ip + signext(vm->mem_read(vm->ip+1, false, vm->user_ctx), 0x00ff); + vm->ip += 2; + } else { + addr = vm->ip + vm->mem_read(vm->ip+1, true, vm->user_ctx); + vm->ip += 3; + } + switch (opcode) + { + case 0xa0: + case 0xa1: + vm->ip = addr; + break; + case 0xa2: + case 0xa3: + if (vm->mem_read(vm->ip, false, vm->user_ctx) == 0x9d) { + embedvm_push(vm, vm->sfp | 1); + embedvm_push(vm, vm->ip + 1); + } else { + embedvm_push(vm, vm->sfp); + embedvm_push(vm, vm->ip); + } + vm->sfp = vm->sp; + vm->ip = addr; + break; + case 0xa4: + case 0xa5: + if (embedvm_pop(vm)) + vm->ip = addr; + break; + case 0xa6: + case 0xa7: + if (!embedvm_pop(vm)) + vm->ip = addr; + break; + } + break; + case 0xae: + embedvm_push(vm, vm->sp); + vm->ip++; + break; + case 0xaf: + embedvm_push(vm, vm->sfp); + vm->ip++; + break; + case 0xb0 ... 0xb0+15: + { + uint8_t argc = embedvm_pop(vm); + int16_t argv[argc]; + for (sfa=0; sfacall_user(opcode - 0xb0, argc, argv, vm->user_ctx); + embedvm_push(vm, a); + } + vm->ip++; + break; + case 0xc0 ... 0xef: + if ((opcode & 0x07) == 5) { + /* this is a "bury" instruction */ + uint8_t depth = (opcode >> 3) & 0x07; + int16_t stack[depth+1]; + for (sfa = 0; sfa <= depth; sfa++) + stack[sfa] = embedvm_pop(vm); + embedvm_push(vm, stack[0]); + for (sfa = depth; sfa > 0; sfa--) + embedvm_push(vm, stack[sfa]); + embedvm_push(vm, stack[0]); + vm->ip++; + break; + } + if ((opcode & 0x07) == 6) { + /* this is a "dig" instruction */ + uint8_t depth = (opcode >> 3) & 0x07; + int16_t stack[depth+2]; + for (sfa = 0; sfa < depth+2; sfa++) + stack[sfa] = embedvm_pop(vm); + for (sfa = depth+1; sfa > 0; sfa--) + embedvm_push(vm, stack[sfa-1]); + embedvm_push(vm, stack[depth+1]); + vm->ip++; + break; + } + sfa = ((opcode >> 3) & 0x07) == 4 || ((opcode >> 3) & 0x07) == 5 ? 1 : 0; + switch (opcode & 0x07) + { + case 0: + addr = vm->mem_read(vm->ip+1, false, vm->user_ctx) & 0x00ff; + vm->ip += 2; + break; + case 1: + addr = vm->mem_read(vm->ip+1, true, vm->user_ctx); + vm->ip += 3; + break; + case 2: + addr = embedvm_pop(vm); + vm->ip++; + break; + case 3: + addr = (embedvm_pop(vm) << sfa) + (vm->mem_read(vm->ip+1, false, vm->user_ctx) & 0x00ff); + vm->ip += 2; + break; + case 4: + addr = (embedvm_pop(vm) << sfa) + vm->mem_read(vm->ip+1, true, vm->user_ctx); + vm->ip += 3; + break; + } + switch ((opcode >> 3) & 0x07) + { + case 0: + embedvm_push(vm, vm->mem_read(addr, false, vm->user_ctx) & 0x00ff); + break; + case 1: + vm->mem_write(addr, embedvm_pop(vm), false, vm->user_ctx); + break; + case 2: + embedvm_push(vm, signext(vm->mem_read(addr, false, vm->user_ctx), 0x00ff)); + break; + case 3: + vm->mem_write(addr, embedvm_pop(vm), false, vm->user_ctx); + break; + case 4: + embedvm_push(vm, vm->mem_read(addr, true, vm->user_ctx)); + break; + case 5: + vm->mem_write(addr, embedvm_pop(vm), true, vm->user_ctx); + break; + } + break; + case 0xf0 ... 0xf7: + for (sfa = 0; sfa <= (opcode & 0x07); sfa++) + embedvm_push(vm, 0); + vm->ip++; + break; + case 0xf8 ... 0xff: + a = embedvm_pop(vm); + vm->sp += 2 + 2*(opcode & 0x07); + embedvm_push(vm, a); + vm->ip++; + break; + } +} + +void embedvm_interrupt(struct embedvm_s *vm, uint16_t addr) +{ + embedvm_push(vm, vm->sfp | 1); + embedvm_push(vm, vm->ip); + vm->sfp = vm->sp; + vm->ip = addr; +} + +int16_t embedvm_pop(struct embedvm_s *vm) +{ + int16_t value = vm->mem_read(vm->sp, true, vm->user_ctx); + vm->sp += 2; + return value; +} + +void embedvm_push(struct embedvm_s *vm, int16_t value) +{ + vm->sp -= 2; + vm->mem_write(vm->sp, value, true, vm->user_ctx); +} + +int16_t embedvm_local_read(struct embedvm_s *vm, int8_t sfa) +{ + uint16_t addr = vm->sfp - 2*sfa + (sfa < 0 ? +2 : -2); + return vm->mem_read(addr, true, vm->user_ctx); +} + +void embedvm_local_write(struct embedvm_s *vm, int8_t sfa, int16_t value) +{ + uint16_t addr = vm->sfp - 2*sfa + (sfa < 0 ? +2 : -2); + vm->mem_write(addr, value, true, vm->user_ctx); +} + diff --git a/ui/embedvm.h b/ui/embedvm.h new file mode 100644 index 0000000..1381b24 --- /dev/null +++ b/ui/embedvm.h @@ -0,0 +1,53 @@ +/* + * EmbedVM - Embedded Virtual Machine for uC Applications + * + * Copyright (C) 2011 Clifford Wolf + * + * Permission to use, copy, modify, and/or distribute this software for any + * purpose with or without fee is hereby granted, provided that the above + * copyright notice and this permission notice appear in all copies. + * + * THE SOFTWARE IS PROVIDED "AS IS" AND THE AUTHOR DISCLAIMS ALL WARRANTIES + * WITH REGARD TO THIS SOFTWARE INCLUDING ALL IMPLIED WARRANTIES OF + * MERCHANTABILITY AND FITNESS. IN NO EVENT SHALL THE AUTHOR BE LIABLE FOR + * ANY SPECIAL, DIRECT, INDIRECT, OR CONSEQUENTIAL DAMAGES OR ANY DAMAGES + * WHATSOEVER RESULTING FROM LOSS OF USE, DATA OR PROFITS, WHETHER IN AN + * ACTION OF CONTRACT, NEGLIGENCE OR OTHER TORTIOUS ACTION, ARISING OUT OF + * OR IN CONNECTION WITH THE USE OR PERFORMANCE OF THIS SOFTWARE. + * + */ + +#ifndef EMBEDVM_H +#define EMBEDVM_H + +#include +#include + +#ifdef __cplusplus +extern "C" { +#endif + +struct embedvm_s +{ + uint16_t ip, sp, sfp; + void *user_ctx; + + int16_t (*mem_read)(uint16_t addr, bool is16bit, void *ctx); + void (*mem_write)(uint16_t addr, int16_t value, bool is16bit, void *ctx); + int16_t (*call_user)(uint8_t funcid, uint8_t argc, int16_t *argv, void *ctx); +}; + +extern void embedvm_exec(struct embedvm_s *vm); +extern void embedvm_interrupt(struct embedvm_s *vm, uint16_t addr); + +int16_t embedvm_pop(struct embedvm_s *vm); +void embedvm_push(struct embedvm_s *vm, int16_t value); + +int16_t embedvm_local_read(struct embedvm_s *vm, int8_t sfa); +void embedvm_local_write(struct embedvm_s *vm, int8_t sfa, int16_t value); + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/ui/oswald_fonts.c b/ui/oswald_fonts.c new file mode 100644 index 0000000..762c3c5 --- /dev/null +++ b/ui/oswald_fonts.c @@ -0,0 +1,40 @@ +#include "oswald_fonts.h" + +#include "fonts/4x6_horizontal_LSB_1.h" +#include "fonts/5x8_horizontal_LSB_1.h" +#include "fonts/5x12_horizontal_LSB_1.h" +#include "fonts/6x8_horizontal_LSB_1.h" +#include "fonts/6x10_horizontal_LSB_1.h" +#include "fonts/7x12b_horizontal_LSB_1.h" +#include "fonts/7x12_horizontal_LSB_1.h" +#include "fonts/8x8_horizontal_LSB_1.h" +#include "fonts/8x12_horizontal_LSB_1.h" +#include "fonts/8x14_horizontal_LSB_1.h" +#include "fonts/10x16_horizontal_LSB_1.h" +#include "fonts/12x16_horizontal_LSB_1.h" +#include "fonts/12x20_horizontal_LSB_1.h" +#include "fonts/16x26_horizontal_LSB_1.h" +#include "fonts/22x36_horizontal_LSB_1.h" +#include "fonts/24x40_horizontal_LSB_1.h" +#include "fonts/32x53_horizontal_LSB_1.h" + +const oswald_font oswald_fonts[LAST_FONT] = { + { 4, 6, (char **)font_4x6}, + { 5, 8, (char **)font_5x8}, + { 5, 12, (char **)font_5x12}, + { 6, 8, (char **)font_6x8}, + { 6, 10, (char **)font_6x10}, + { 7, 12, (char **)font_7x12}, + { 7, 12, (char **)font_7x12b}, + { 8, 8, (char **)font_8x8}, + { 8, 12, (char **)font_8x12}, + { 8, 14, (char **)font_8x14}, + { 10, 16, (char **)font_10x16}, + { 12, 16, (char **)font_12x16}, + { 12, 20, (char **)font_12x20}, + { 16, 26, (char **)font_16x26}, + { 22, 36, (char **)font_22x36}, + { 24, 40, (char **)font_24x40}, + { 32, 53, (char **)font_32x53}, +}; + diff --git a/ui/oswald_fonts.h b/ui/oswald_fonts.h new file mode 100644 index 0000000..0f590c4 --- /dev/null +++ b/ui/oswald_fonts.h @@ -0,0 +1,35 @@ +#ifndef _FONTS_H +#define _FONTS_H + +#include "oswald.h" + +typedef enum { + FONT_4x6 = 0, + FONT_5x8, + FONT_5x12, + FONT_6x8, + FONT_6x10, + FONT_7x12b, + FONT_7x12, + FONT_8x8, + FONT_8x12, + FONT_8x14, + FONT_10x16, + FONT_12x16, + FONT_12x20, + FONT_16x26, + FONT_22x36, + FONT_24x40, + FONT_32x53, + LAST_FONT +} oswald_font_face; + +typedef struct { + u8t width; + u8t height; + char **data; +} oswald_font; + +extern const oswald_font oswald_fonts[]; + +#endif diff --git a/ui/oswald_graphics.c b/ui/oswald_graphics.c new file mode 100644 index 0000000..36894ab --- /dev/null +++ b/ui/oswald_graphics.c @@ -0,0 +1,172 @@ +#include "oswald-ui.h" +#include "oswald_strings.h" +#include "oswald_fonts.h" + +#include "oswald_graphics.h" + + +void oswald_draw_Line(u8t xstart, u8t ystart, u8t xend, u8t yend) +{ + int x, y, t, dx, dy, incx, incy, pdx, pdy, ddx, ddy, es, el, err; + + dx = xend - xstart; + dy = yend - ystart; + + incx = (dx >= 0) ? 1 : -1; + incy = (dy >= 0) ? 1 : -1; + + if (dx<0) + dx = -dx; + if (dy<0) + dy = -dy; + + if (dx>dy) { + pdx = incx; pdy = 0; + ddx=incx; ddy=incy; + es =dy; el =dx; + } else { + pdx=0; pdy=incy; + ddx=incx; ddy=incy; + es =dx; el =dy; + } + + x = xstart; + y = ystart; + err = el/2; + lcd_set_pixel(x, y, TRUE); + + for (t = 0; t < el; ++t) { + err -= es; + if (err < 0) { + err += el; + x += ddx; + y += ddy; + } else { + x += pdx; + y += pdy; + } + lcd_set_pixel(x, y, TRUE); + } + lcd_update_display(); +} + +void oswald_draw_line_ww(u8t xstart, u8t ystart, u8t xend, u8t yend, u8t thickness) +{ + int i, x, y, t, dx, dy, incx, incy, pdx, pdy, ddx, ddy, es, el, err; + + dx = xend - xstart; + dy = yend - ystart; + + incx = (dx >= 0) ? 1 : -1; + incy = (dy >= 0) ? 1 : -1; + + if (dx<0) + dx = -dx; + if (dy<0) + dy = -dy; + + if (dx>dy) { + pdx = incx; pdy = 0; + ddx=incx; ddy=incy; + es =dy; el =dx; + } else { + pdx=0; pdy=incy; + ddx=incx; ddy=incy; + es =dx; el =dy; + } + + x = xstart; + y = ystart; + err = el/2; + lcd_set_pixel(x, y, TRUE); + for (i=1; i