/**************************************************************************************
$Id: sysCall.c,v 1.3 2002/04/26 22:40:44 reddawg Exp $


**************************************************************************************/

#include <ubixos/video.h>
#include <ubixos/schedule.h>

asm(
  ".globl sysCall         \n"
  "sysCall:               \n"
  "   pusha               \n" /* Save all registers               */
  "   pushw %ds           \n" /* Set up the data segment          */
  "   pushw %es           \n"
  "   pushw %ss           \n" /* Note that ss is always valid     */
  "   pushw %ss           \n"
  "   popw %ds            \n"
  "   popw %es            \n"
  "                       \n"
  "   cmpl totalCalls,%eax \n"
  "   jae invalidCall     \n"
  "   call systemCalls(,%eax,4)       \n"
  "                       \n"
  "   popw %es            \n"
  "   popw %ds            \n" /* Restore registers                */
  "   popa                \n"
  "   iret                \n" /* Exit interrupt                   */
    );

void invalidCall() {
  kprintf("Invalid System Call!!\n");
  _current->status = AVAILABLE;
  schedule();
  }

int systemExit() {
  _current->status = AVAILABLE;
  schedule();
  return(1);
  }

int systemPrint() {
  char *data;
  asm(
    "movl %%ebx,%0\n"
    : "=g" (data)
    );
  kprintf("%s",data);
  return(1);
  }

int systemGetch() {
  int *data;
  asm(
    "movl %%ebx,%0\n"
    : "=g" (data)
    );
  asm("sti");
  data[0] = getch();
  return(1);
  }

int systemVM86() {
  int data;
  asm(
    "movl %%ebx,%0\n"
    : "=g" (data)
    );
  if (data == 1) {
    _current->tss.eflags |= 0x00020000;
    }
  else if (data == 2) {
    _current->tss.eflags &= 0x0001FFFF;
    }
  return(1);
  }