Solving C-kernel-problems: inline assembler or library?

Question about which tools to use, bugs, the best way to implement a function, etc should go here. Don't forget to see if your question is answered in the wiki first! When in doubt post here.
Post Reply
brunsbarth
Posts: 4
Joined: Tue Jun 05, 2007 3:03 pm

Solving C-kernel-problems: inline assembler or library?

Post by brunsbarth »

Hi, I got a pretty simple question, I guess:

I progged an own asm-bootloader, that loads a c-kernel, basically the same as in your tutorials here.

Now there is one problem: I have to re-code all of the high-level-c-functions. Could anyone please tell me, whether or not, and how, it is possible to include just a few very simply c-libraries?

Otherwise:
How can I handle keyboard input? I got a few inline assembler scripts, but none of them working properly.....

Thanks for your help,
Brunsbarth
User avatar
Combuster
Member
Member
Posts: 9301
Joined: Wed Oct 18, 2006 3:45 am
Libera.chat IRC: [com]buster
Location: On the balcony, where I can actually keep 1½m distance
Contact:

Re: Solving C-kernel-problems: inline assembler or library?

Post by Combuster »

brunsbarth wrote:Now there is one problem: I have to re-code all of the high-level-c-functions. Could anyone please tell me, whether or not, and how, it is possible to include just a few very simply c-libraries?
You'd have to port a libc to do that. Try Newlib or PDClib for that.
How can I handle keyboard input? I got a few inline assembler scripts, but none of them working properly.....
The proper method to do so uses interrupts. Since you will need that sooner or later, you may want to do that anyway.

wiki page on the keyboard:
http://www.osdev.org/wiki/Keyboard_Input
some code that polls instead of using interrupts (non-c):
http://dimensionalrift.homelinux.net/co ... yboard.bas
"Certainly avoid yourself. He is a newbie and might not realize it. You'll hate his code deeply a few years down the road." - Sortie
[ My OS ] [ VDisk/SFS ]
brunsbarth
Posts: 4
Joined: Tue Jun 05, 2007 3:03 pm

Post by brunsbarth »

Thanks a lot... though I hoped not to have overseen something that obvious in the wiki, sorry :)

Brunsbarth
brunsbarth
Posts: 4
Joined: Tue Jun 05, 2007 3:03 pm

Post by brunsbarth »

Well, now i do get response on keyprints, but it turns out to be mess like this:

ðð‡éð‡éð‡éð‡éð‡éð‡éð‡éð‡éð‡éð‡éð‡éð‡éð‡éð‡éð‡éð‡éð‡éð

anyone had the problem before?
User avatar
AJ
Member
Member
Posts: 2646
Joined: Sun Oct 22, 2006 7:01 am
Location: Devon, UK
Contact:

Post by AJ »

Hi,

1. Are you checking for whether bit 7 is set - if so, it's a key release.
2. Are you converting scancodes to ASCII characters?

Cheers,
Adam
brunsbarth
Posts: 4
Joined: Tue Jun 05, 2007 3:03 pm

Post by brunsbarth »

well, this is my function:

Code: Select all

unsigned shift_state=0;
unsigned escaped=0;
unsigned char new_char;

char KeyboardISR()
{
   unsigned new_scan_code = in(0x60);
   if (escaped) new_scan_code += 256;
   switch(new_scan_code) {
   case 0x2a: shift_state = 1; break;
   case 0xaa: shift_state = 0; break;
   case 0xe0: escaped = 1; break;
   default:
      if (new_scan_code & 0x80) {
      } else {
         new_char=new_scan_code;
      }
  break;
  }

  out(0x20,0x20);
  return new_char;
}
may be better to post it, than to describe it :)

Brunsbarth
User avatar
AJ
Member
Member
Posts: 2646
Joined: Sun Oct 22, 2006 7:01 am
Location: Devon, UK
Contact:

Post by AJ »

Code: Select all

if (escaped) new_scan_code += 256;
Should be:

Code: Select all

if (escaped) 
{
  escaped = 0;
  new_scan_code += 256;
}
Otherwise all your characters will end up escaped after the first escape sequence!

Also, new_char is still a scan code. You need to convert it to ASCII (scancode!=ASCII character). The easiest way to do this IMHO is with a lookup table, for example:

Code: Select all

unsigned char kbduk[128] =
{
/*0*/  	0,  0 /*esc*/, 
/*2*/  	'1', '2', '3', '4', '5', '6', '7', '8',	'9', '0', '-', '=', '\b' /* bksp */,
/*16*/ 	'\t', 'q', 'w', 'e', 'r', 't', 'y', 'u', 'i', 'o', 'p', '[', ']', '\n' /* enter */,
/*29*/	0 /* ctrl */, 'a', 's', 'd', 'f', 'g', 'h', 'j', 'k', 'l', ';', '\'', '`',
/*42*/	0 /* LSh*/, '#', 'z', 'x', 'c', 'v', 'b', 'n', 'm', ',', '.', '/',   0 /*Rsh*/,
/*55*/  '*', 0 /*Alt*/, ' '/*spc*/, 0/*caplock*/, 
/*59*/	0/*F1*/, 0,   0,   0,   0,   0,   0,   0,   0, 0/*F10*/,
/*69*/  0/*numlock*/, 0 /*ScrollLock*/, 0/*Home*/, 0/*Up*/, 0/*PgUp*/, '-', 0/*Left*/, 
/*76*/	0, 0/*Right*/, '+', 0/*End*/, 0/*Down*/, 0/*PgDn*/,
/*82*/  0/*Ins*/, 0/*Del*/, 0,0,'\\',0/*F11*/, 0/*F12*/,0
};		

unsigned char kbduk_s[128] =
{
/*0*/  	0,  27 /*`*/, 
/*2*/  	'!', '"', '£', '$', '%', '^', '&', '*',	'(', ')', '_', '+', '\b' /* bksp */,
/*16*/ 	'\t', 'Q', 'W', 'E', 'R', 'T', 'Y', 'U', 'I', 'O', 'P', '{', '}', '\n' /* enter */,
/*29*/	0 /* ctrl */, 'A', 'S', 'D', 'F', 'G', 'H', 'J', 'K', 'L', ':', '@', '~',
/*42*/	0 /* LSh*/, '~', 'Z', 'X', 'C', 'V', 'B', 'N', 'M', '<', '>', '?',   0 /*RSh*/,
/*55*/  '*', 0 /*Alt*/, ' '/*spc*/, 0/*caplock*/, 
/*59*/	0/*F1*/, 0,   0,   0,   0,   0,   0,   0,   0, 0/*F10*/,
/*69*/  0/*numlock*/, 0 /*ScrollLock*/, 0/*Home*/, 0/*Up*/, 0/*PgUp*/, '-', 0/*Left*/, 
/*76*/	0, 0/*Right*/, '+', 0/*End*/, 0/*Down*/, 0/*PgDn*/,
/*82*/  0/*Ins*/, 0/*Del*/, 0,0,'|',0/*F11*/, 0/*F12*/,0
};	
That's adapted from Bran's kernel development tutorial. Then use:

Code: Select all

char ascii_char;
if(shift_state)
    ascii_char = kbduk_s[new_char];
else
    ascii_char = kbduk[new_char];
..and before anyone points it out, you need to make some condition for your escaped characters as they will need special action and will attempt to read past the end of the lookup tables.

Cheers,
Adam
Post Reply