A project to implement a console using the Mbed using VGA for video output and a PS/2 keyboard for the input. The eventual goal is to also include tools for managing SD cards, and a semi-self-hosting programming environment.

Dependencies:   PS2_MbedConsole fastlib SDFileSystem vga640x480g_mbedconsole lightvm mbed

MbedConsole is a cool little project to have a self-contained computer all on an Mbed. So far it has VGA and PS/2 support and can stand alone without a computer powering it. Next planned features are SD card support and a lightweight programmable VM complete with a file editor and self-hosted assembler.

You can view additional details about it at http://earlz.net/tags/mbedconsole

Committer:
earlz
Date:
Fri Sep 21 04:53:45 2012 +0000
Revision:
6:a4dff59ef214
Child:
7:2ac6752d47d2
Switched a virtual machine instead of trying to interpret directly. This is much easier for development, and should amazingly make it both faster and use less memory  :D

Who changed what in which revision?

UserRevisionLine numberNew contents of line
earlz 6:a4dff59ef214 1 #include "mbedconsole.h"
earlz 6:a4dff59ef214 2 #include "plEarlz.h"
earlz 6:a4dff59ef214 3 #include <stdint.h>
earlz 6:a4dff59ef214 4 #include <stdarg.h>
earlz 6:a4dff59ef214 5
earlz 6:a4dff59ef214 6
earlz 6:a4dff59ef214 7 //An extremely simple virtual machine to make this implementation about 10 times easier and probably a bit faster
earlz 6:a4dff59ef214 8
earlz 6:a4dff59ef214 9
earlz 6:a4dff59ef214 10
earlz 6:a4dff59ef214 11
earlz 6:a4dff59ef214 12
earlz 6:a4dff59ef214 13 int pl_stackpos=0;
earlz 6:a4dff59ef214 14 int pl_stack[MAXSTACK];
earlz 6:a4dff59ef214 15
earlz 6:a4dff59ef214 16
earlz 6:a4dff59ef214 17
earlz 6:a4dff59ef214 18
earlz 6:a4dff59ef214 19 int pl_dictionary_count=0;
earlz 6:a4dff59ef214 20 int pl_dictionary_size=0;
earlz 6:a4dff59ef214 21 WordKey *pl_dictionary; //todo: a hash table would be much faster
earlz 6:a4dff59ef214 22
earlz 6:a4dff59ef214 23 void pl_push(int val)
earlz 6:a4dff59ef214 24 {
earlz 6:a4dff59ef214 25 if(pl_stackpos>=MAXSTACK)
earlz 6:a4dff59ef214 26 {
earlz 6:a4dff59ef214 27 vputs("Stack overflow!");
earlz 6:a4dff59ef214 28 pl_error=StackOverflow;
earlz 6:a4dff59ef214 29 return;
earlz 6:a4dff59ef214 30 }
earlz 6:a4dff59ef214 31 pl_stack[pl_stackpos]=val;
earlz 6:a4dff59ef214 32 pl_stackpos++;
earlz 6:a4dff59ef214 33 }
earlz 6:a4dff59ef214 34 int pl_pop()
earlz 6:a4dff59ef214 35 {
earlz 6:a4dff59ef214 36 if(pl_stackpos<=0)
earlz 6:a4dff59ef214 37 {
earlz 6:a4dff59ef214 38 vputs("Stack underflow!");
earlz 6:a4dff59ef214 39 pl_error=StackUnderflow;
earlz 6:a4dff59ef214 40 return 0;
earlz 6:a4dff59ef214 41 }
earlz 6:a4dff59ef214 42 pl_stackpos--;
earlz 6:a4dff59ef214 43 return pl_stack[pl_stackpos];
earlz 6:a4dff59ef214 44 }
earlz 6:a4dff59ef214 45
earlz 6:a4dff59ef214 46 WordKey *pl_lookup(char* name)
earlz 6:a4dff59ef214 47 {
earlz 6:a4dff59ef214 48 for(int i=0;i<pl_dictionary_count;i++)
earlz 6:a4dff59ef214 49 {
earlz 6:a4dff59ef214 50 if(strlcmp(name, pl_dictionary[i].name, 12)==0)
earlz 6:a4dff59ef214 51 {
earlz 6:a4dff59ef214 52 return &pl_dictionary[i];
earlz 6:a4dff59ef214 53 }
earlz 6:a4dff59ef214 54 }
earlz 6:a4dff59ef214 55 return NULL;
earlz 6:a4dff59ef214 56 }
earlz 6:a4dff59ef214 57
earlz 6:a4dff59ef214 58 int pl_addword()
earlz 6:a4dff59ef214 59 {
earlz 6:a4dff59ef214 60 if(pl_dictionary_size==0){
earlz 6:a4dff59ef214 61 pl_dictionary=(WordKey*)malloc(sizeof(WordKey)*12);
earlz 6:a4dff59ef214 62 pl_dictionary_size=12;
earlz 6:a4dff59ef214 63 return 0;
earlz 6:a4dff59ef214 64 }
earlz 6:a4dff59ef214 65 if(pl_dictionary_size<=pl_dictionary_count)
earlz 6:a4dff59ef214 66 {
earlz 6:a4dff59ef214 67 void* tmp=realloc(pl_dictionary, pl_dictionary_size+sizeof(WordKey)*DICTIONARYSTEP);
earlz 6:a4dff59ef214 68 if(tmp==NULL)
earlz 6:a4dff59ef214 69 {
earlz 6:a4dff59ef214 70 vputs("Out of memory!! Epic Fail!!");
earlz 6:a4dff59ef214 71 return -1;
earlz 6:a4dff59ef214 72 }
earlz 6:a4dff59ef214 73 pl_dictionary=(WordKey*)tmp;
earlz 6:a4dff59ef214 74 pl_dictionary_size+=sizeof(WordKey)*DICTIONARYSTEP;
earlz 6:a4dff59ef214 75 }
earlz 6:a4dff59ef214 76 return pl_dictionary_count++;
earlz 6:a4dff59ef214 77 }
earlz 6:a4dff59ef214 78
earlz 6:a4dff59ef214 79
earlz 6:a4dff59ef214 80
earlz 6:a4dff59ef214 81 int forth_execute(uint8_t* block, int length)
earlz 6:a4dff59ef214 82 {
earlz 6:a4dff59ef214 83 int pos=0;
earlz 6:a4dff59ef214 84 while(pos<length)
earlz 6:a4dff59ef214 85 {
earlz 6:a4dff59ef214 86
earlz 6:a4dff59ef214 87 Opcode op=(Opcode)block[pos];
earlz 6:a4dff59ef214 88 //printf("opcode: %x\n",(int)op);
earlz 6:a4dff59ef214 89 switch(op)
earlz 6:a4dff59ef214 90 {
earlz 6:a4dff59ef214 91 case BranchTrue:
earlz 6:a4dff59ef214 92 if(pl_pop()){
earlz 6:a4dff59ef214 93 pos++;
earlz 6:a4dff59ef214 94 pos=*((uint16_t*)&block[pos]);
earlz 6:a4dff59ef214 95 }else{
earlz 6:a4dff59ef214 96 pos+=3;
earlz 6:a4dff59ef214 97 }
earlz 6:a4dff59ef214 98 break;
earlz 6:a4dff59ef214 99 case BranchFalse:
earlz 6:a4dff59ef214 100 if(!pl_pop()){
earlz 6:a4dff59ef214 101 pos++;
earlz 6:a4dff59ef214 102 pos=*((uint16_t*)&block[pos]);
earlz 6:a4dff59ef214 103 }else{
earlz 6:a4dff59ef214 104 pos+=3;
earlz 6:a4dff59ef214 105 }
earlz 6:a4dff59ef214 106 break;
earlz 6:a4dff59ef214 107 case Branch:
earlz 6:a4dff59ef214 108 pos++;
earlz 6:a4dff59ef214 109 pos=*((uint16_t*)&block[pos]);
earlz 6:a4dff59ef214 110 break;
earlz 6:a4dff59ef214 111 case Push:
earlz 6:a4dff59ef214 112 pos++;
earlz 6:a4dff59ef214 113 pl_push(*(uint32_t*)&block[pos]);
earlz 6:a4dff59ef214 114 pos+=4;
earlz 6:a4dff59ef214 115 break;
earlz 6:a4dff59ef214 116 case Pop:
earlz 6:a4dff59ef214 117 pos++;
earlz 6:a4dff59ef214 118 pl_pop();
earlz 6:a4dff59ef214 119 break;
earlz 6:a4dff59ef214 120 case Add:
earlz 6:a4dff59ef214 121 pos++;
earlz 6:a4dff59ef214 122 pl_push(pl_pop()+pl_pop());
earlz 6:a4dff59ef214 123 break;
earlz 6:a4dff59ef214 124 case Sub:
earlz 6:a4dff59ef214 125 pos++;
earlz 6:a4dff59ef214 126 pl_push(pl_pop()-pl_pop());
earlz 6:a4dff59ef214 127 break;
earlz 6:a4dff59ef214 128 case Mul:
earlz 6:a4dff59ef214 129 pos++;
earlz 6:a4dff59ef214 130 pl_push(pl_pop()*pl_pop());
earlz 6:a4dff59ef214 131 break;
earlz 6:a4dff59ef214 132 case Div:
earlz 6:a4dff59ef214 133 pos++;
earlz 6:a4dff59ef214 134 pl_push(pl_pop()/pl_pop());
earlz 6:a4dff59ef214 135 break;
earlz 6:a4dff59ef214 136 case Mod:
earlz 6:a4dff59ef214 137 pos++;
earlz 6:a4dff59ef214 138 pl_push(pl_pop()%pl_pop());
earlz 6:a4dff59ef214 139 break;
earlz 6:a4dff59ef214 140 case CallInt:
earlz 6:a4dff59ef214 141 pos++;
earlz 6:a4dff59ef214 142 uint32_t tmp=*(uint32_t*)&block[pos];
earlz 6:a4dff59ef214 143 ((BuiltinFunction)tmp)();
earlz 6:a4dff59ef214 144 pos+=4;
earlz 6:a4dff59ef214 145 break;
earlz 6:a4dff59ef214 146
earlz 6:a4dff59ef214 147
earlz 6:a4dff59ef214 148 default:
earlz 6:a4dff59ef214 149 vputs("Unknown opcode!!");
earlz 6:a4dff59ef214 150 return;
earlz 6:a4dff59ef214 151 }
earlz 6:a4dff59ef214 152 }
earlz 6:a4dff59ef214 153 return 0;
earlz 6:a4dff59ef214 154 }