/*  Copyright 2008 Theo Berkau 
    This file is part of Yabause.

    Yabause is free software; you can redistribute it and/or modify
    it under the terms of the GNU General Public License as published by
    the Free Software Foundation; either version 2 of the License, or
    (at your option) any later version.

    Yabause is distributed in the hope that it will be useful,
    but WITHOUT ANY WARRANTY; without even the implied warranty of
    MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE.  See the
    GNU General Public License for more details.

    You should have received a copy of the GNU General Public License
    along with Yabause; if not, write to the Free Software
    Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301  USA
*/

#include <stdio.h>
#include <stdlib.h>
#include <stdarg.h>
#include <string.h>
#include <malloc.h>
#include <wiiuse/wpad.h>
#include <ogcsys.h>
#include <gccore.h>
#include <fat.h>
#include <di/di.h>
#include "../cs0.h"
#include "../m68kcore.h"
#include "../peripheral.h"
#include "../vidsoft.h"
#include "../vdp2.h"
#include "../yui.h"
#include "perwii.h"
#include "sndwii.h"
#include "menu.h"
#ifdef DEBUG
#include "font.h"
#endif


#ifdef HAVE_LIBGL
#define USE_OPENGL
#endif

#ifdef USE_OPENGL
#include "../ygl.h"
extern Mtx model;
#define DEFAULT_FIFO_SIZE       (256*1024)
GXColor background = {0, 0, 0, 0xff};
#endif

#ifdef HAVE_LIBGLUT
//#define GLUT_BITMAP_HELVETICA_12        ((void*)7)
//#define GLUT_BITMAP_TIMES_ROMAN ((void*)4)
//#define GLUT_BITMAP_HELVETICA_12        ((void*)4)
//GLUTAPI void *glutBitmapHelvetica12;
#endif

#include "../yui.h"

/* Wii includes */
#include "iowii.h"
//#include "syswii.h"

int YuiExec(void);

void Check_Bios_Exist(void);
void Check_SD_Init(void);
void Check_Read_Dir(void);
void scroll_filelist(s8 delta);
void print_filelist(void);

/* Constants */

static u32 *xfb[2] = { NULL, NULL };
int fbsel = 0;
static GXRModeObj *rmode = NULL;
volatile int done=0;
volatile int resetemu=0;
int running=1;
static void *_console_buffer = NULL;
void __console_init_ex(void *conbuffer,int tgt_xstart,int tgt_ystart,int tgt_stride,int con_xres,int con_yres,int con_stride);


SH2Interface_struct *SH2CoreList[] = {
&SH2Interpreter,
&SH2DebugInterpreter,
NULL
};

PerInterface_struct *PERCoreList[] = {
&PERDummy,
&PERWiiKeyboard,
&PERWiiClassic,
NULL
};

CDInterface *CDCoreList[] = {
&DummyCD,
&ISOCD,
NULL
};

SoundInterface_struct *SNDCoreList[] = {
&SNDDummy,
&SNDWII,
NULL
};

VideoInterface_struct *VIDCoreList[] = {
&VIDDummy,
&VIDSoft,
NULL
};

M68K_struct *M68KCoreList[] = {
&M68KDummy,
&M68KC68K,
#ifdef HAVE_Q68
&M68KQ68,
#endif
NULL
};

static char cartfilename[512]="/SSROMS/cart.bin";
static char bupfilename[512]="/SSROMS/bkram.bin";
static char biosfilename[512]="/SSROMS/bios.bin";
static char isofilename[512]="/SSROMS/game.cue";

extern int vdp2width, vdp2height;
int wii_width, wii_height;

#define FILES_PER_PAGE	5
#define ROMS_DIR	"/SSROMS"
#ifdef WIIDEBUG
   FILE *debugfp;
   int  first=1;
extern int count_fps;
#endif

struct file *filelist = NULL;
u32 nb_files = 0;

s32 selected = 0, start = 0;
int cuemenuflag = 0;

extern void sleep(u32);
void gotoxy(int x, int y);
void OnScreenDebugMessage(char *string, ...);
void DoMenu();
int GameExec();
int LoadCue();

int menuselect=1;

static BOOL flag_mount = FALSE;

#ifdef USE_OPENGL
GLenum MatorixMode;
Mtx44 project;



////GLUTAPI void APIENTRY glutBitmapCharacter(void *font, int character) {
//void glutBitmapCharacter(void *font, int character) {
//}

GLAPI void GLAPIENTRY glMatrixMode( GLenum mode ) {
	MatorixMode=mode;
}

void Mtx44Identity(Mtx44 mt)
{
        s32 i,j;

        for(i=0;i<4;i++) {
                for(j=0;j<4;j++) {
                        if(i==j) mt[i][j] = 1.0;
                        else mt[i][j] = 0.0;
                }
        }
}

GLAPI void GLAPIENTRY glOrtho( GLdouble left, GLdouble right,
                                 GLdouble bottom, GLdouble top,
                                 GLdouble near_val, GLdouble far_val ) {
  if(MatorixMode==GL_PROJECTION) {
    Mtx44Identity(project);
    guOrtho(project,top, bottom, left, right, near_val, far_val);
    GX_LoadProjectionMtx(project, GX_ORTHOGRAPHIC);
  } else if (MatorixMode==GL_TEXTURE) {
    guLightOrtho(model, top, bottom, left, right, 1, 1, 0, 0);    
    GX_LoadTexMtxImm(model, GX_TEXMTX0,GX_MTX3x4);
  }
}


GLAPI void GLAPIENTRY glViewport( GLint x, GLint y,
                                    GLsizei width, GLsizei height ) {
  GX_SetViewport(x, y, width, height, 0, 1);
}

GLAPI void GLAPIENTRY glRasterPos2i( GLint x, GLint y ) {
  rmode->viXOrigin = x;
  rmode->viYOrigin = y;
}

GLAPI void GLAPIENTRY glPixelZoom( GLfloat xfactor, GLfloat yfactor ) {
}

//GLAPI void GLAPIENTRY glDrawPixels( GLsizei width, GLsizei height,
//                                    GLenum format, GLenum type,
//                                    const GLvoid *pixels ) {
//}
#endif

void YuiSetVideoAttribute(int type, int val) {
}

int YuiSetVideoMode(int width, int height, int bpp, int fullscreen) {
        return 0;
}

void fat_remount()
{
   if(flag_mount)
   {
      fatUnmount("fat:/");
      //__io_wiisd.shutdown();
      flag_mount = FALSE;
   }
   fatInitDefault();
   flag_mount = TRUE;
}

void reset()
{
   //exit(0);//
   resetemu=1;
}

void powerdown()
{
   done = 1;
}

int DVDStopMotor()
{
   static char dvdstr[] ATTRIBUTE_ALIGN(32) = "/dev/di";
   s32 fd;
   u8 buf[0x20];
   u8 outbuf[0x20];

   if ((fd = IOS_Open(dvdstr,0)) < 0)
      return 0;
	
   ((u32 *)buf)[0x00] = 0xE3000000;
   ((u32 *)buf)[0x01] = 0;
   ((u32 *)buf)[0x02] = 0;

   IOS_Ioctl(fd, buf[0], buf, 0x20, outbuf, 0x20);

   IOS_Close(fd);

   return 1;
}

int main(int argc, char **argv)
{
   WPAD_Init();
   PAD_Init();
   SYS_SetResetCallback(reset);
   SYS_SetPowerCallback(powerdown);
   DVDStopMotor();
	
   fatInitDefault();
   //fat_remount();

   DoMenu();

   exit(0);
   return 0;
}

int YuiExec()
{
   yabauseinit_struct yinit;
   int ret;
   static int FirstRun = 1;
   FILE *fp;


if(FirstRun) {
   //FirstRun=0;

#ifndef NOHIGHRESO
   VIDEO_Init();
   //Check_SD_Init();
#endif

#ifndef HIGHRESO
   switch(VIDEO_GetCurrentTvMode()) 
   {
      case VI_NTSC:
         rmode = &TVNtsc240Ds;
	 break;
      case VI_PAL:
         rmode = &TVPal264Ds;
 	 break;
      case VI_MPAL:
	 rmode = &TVMpal480IntDf;
	 break;
      default:
         rmode = &TVNtsc240Ds;
	 break;
   }
#else
/*
   switch(VIDEO_GetCurrentTvMode()) 
   {
      case VI_NTSC:
         rmode = &TVNtsc480IntDf;
	 break;
      case VI_PAL:
         rmode = &TVPal528IntDf;
 	 break;
      case VI_MPAL:
	 rmode = &TVMpal480IntDf;
	 break;
      default:
         rmode = &TVNtsc480IntDf;
	 break;
   }
*/
#endif

#ifndef HIGHRESO 
   // Allocate two buffers(may not be necessary)
   xfb[0] = MEM_K0_TO_K1(SYS_AllocateFramebuffer(rmode));
   xfb[1] = MEM_K0_TO_K1(SYS_AllocateFramebuffer(rmode));
	
   VIDEO_Configure(rmode);
   VIDEO_ClearFrameBuffer (rmode, xfb[0], COLOR_BLACK);
   VIDEO_ClearFrameBuffer (rmode, xfb[1], COLOR_BLACK);
   VIDEO_SetNextFramebuffer(xfb[0]);
   VIDEO_SetBlack(FALSE);
   VIDEO_Flush();
   VIDEO_WaitVSync();
   if(rmode->viTVMode&VI_NON_INTERLACE) 
      VIDEO_WaitVSync();

#else
   VIDEO_ClearFrameBuffer (rmode, xfb[0], COLOR_BLACK);
   VIDEO_ClearFrameBuffer (rmode, xfb[1], COLOR_BLACK);
   VIDEO_SetNextFramebuffer(xfb[0]);
   VIDEO_Flush ();
   VIDEO_WaitVSync();
#endif

#if 0
   //free(_console_buffer);
   //if(_console_buffer != NULL) free(_console_buffer);
   _console_buffer = malloc(10*10*VI_DISPLAY_PIX_SZ);
   __console_init_ex(_console_buffer,10,10,rmode->fbWidth*VI_DISPLAY_PIX_SZ,10,10,10*VI_DISPLAY_PIX_SZ);
#endif

   wii_width  = rmode->fbWidth / 2;
   wii_height = rmode->xfbHeight;
 

#ifdef USE_OPENGL
        // setup the fifo and then init the flipper
        void *gp_fifo = NULL;
        gp_fifo = memalign(32,DEFAULT_FIFO_SIZE);
        memset(gp_fifo,0,DEFAULT_FIFO_SIZE);

        GX_Init(gp_fifo,DEFAULT_FIFO_SIZE);

        // clears the bg to color and clears the z buffer
        GX_SetCopyClear(background, 0x00ffffff);
#endif

} else {
   //YabauseReset();
   //YabauseResetButton();
}
#ifdef WIIDEBUG
   if((debugfp=fopen("/SSROMS/debug.txt","a"))==NULL)
      exit(-1);
   fprintf(debugfp,"-----------------------------\r\n");
   fprintf(debugfp,"Start %s\r\n",isofilename);
   fprintf(debugfp,"width=%d\r\n",VIDEO_PadFramebufferWidth(rmode->fbWidth));
   fprintf(debugfp,"height=%d\r\n",rmode->xfbHeight*VI_DISPLAY_PIX_SZ);
   fprintf(debugfp,"xfbH=%d\r\n",rmode->xfbHeight);
   fprintf(debugfp,"fbW=%d\r\n",rmode->fbWidth);
   fclose(debugfp);
#endif

   memset(&yinit, 0, sizeof(yabauseinit_struct));
   yinit.percoretype = PERCORE_WIICLASSIC;
   yinit.sh2coretype = SH2CORE_INTERPRETER;
   yinit.vidcoretype = VIDCORE_SOFT;
   yinit.sndcoretype = SNDCORE_WII;
   yinit.cdcoretype = CDCORE_ISO;
#ifdef HAVE_Q68
   yinit.m68kcoretype = M68KCORE_Q68;
#else
   yinit.m68kcoretype = M68KCORE_C68K;
#endif
   //yinit.carttype = CART_NONE;
   yinit.carttype = CART_DRAM32MBIT;
   yinit.regionid = REGION_AUTODETECT;
   //if (strcmp(biosfilename, "") == 0) {
   if ((fp=fopen(biosfilename, "rb")) == NULL) {
      yinit.biospath = NULL;
   } else {
      yinit.biospath = biosfilename;
      fclose(fp);
   //fat_remount();
   }
   yinit.cdpath = isofilename;
   yinit.buppath = bupfilename;
   //yinit.buppath = NULL;
   yinit.mpegpath = NULL;
   yinit.cartpath = NULL;
   //yinit.cartpath = cartfilename;
   yinit.netlinksetting = NULL;
   yinit.flags = VIDEOFORMATTYPE_NTSC;

   // Hijack the fps display
   VIDSoft.OnScreenDebugMessage = OnScreenDebugMessage;



   if ((ret = YabauseInit(&yinit)) == 0)
   {
      EnableAutoFrameSkip();
      VIDEO_ClearFrameBuffer(rmode, xfb[fbsel], COLOR_BLACK);
#ifdef WIIDEBUG
   if((debugfp=fopen("/SSROMS/debug.txt","a"))==NULL)
      exit(-1);
   fprintf(debugfp,"YabauseInit return\r\n");
   fclose(debugfp);
#endif

      while(!done)
      {
         if (PERCore->HandleEvents() != 0)
            return -1;
         if (resetemu)
         {
            YabauseReset();
            resetemu = 0;
            SYS_SetResetCallback(reset);
         }
      }
      YabauseDeInit();
      done=0;
      resetemu=0;
   }
   else
   {
      while(!done)
         VIDEO_WaitVSync();
   }
#ifdef WIIDEBUG
   if((debugfp=fopen("/SSROMS/debug.txt","a"))==NULL)
      exit(-1);
   fprintf(debugfp,"YabauseInit ret=%d\r\n",ret);
   fclose(debugfp);
#endif

   return 0;
}

void YuiErrorMsg(const char *string)
{
#if 0
   if (strncmp(string, "Master SH2 invalid opcode", 25) == 0)
   {
      if (!running)
         return;
      running = 0;
      printf("%s\n", string);
   }
#endif
}

void YuiSwapBuffers()
{
   int i, j;
   u32 *curfb;
   u32 *buf;

   fbsel ^= 1;
   curfb = xfb[fbsel];
   buf = dispbuffer;
   unsigned int index; 

#ifdef WIIDEBUG
   if((debugfp=fopen("/SSROMS/debug.txt","a"))==NULL)
      exit(-1);
if(count_fps==10) {
   fprintf(debugfp,"in width=%d\r\n",VIDEO_PadFramebufferWidth(rmode->fbWidth));
   fprintf(debugfp,"in height=%d\r\n",rmode->xfbHeight*VI_DISPLAY_PIX_SZ);
   fclose(debugfp);
   first=0;
}
#endif


#ifndef OLD_COLDE
   //for (j = 0; j < 224; j++)
   for (j = 0; j < wii_height; j++)
   {
      //for (i = 0; i < 320; i++)
      for (i = 0; i < wii_width; i++)
      {
         u8 y, cb, cr;
         u8 r, g, b;

         index =  ((int)((double)(j)*(double)(vdp2height)/(double)wii_height)*vdp2width) + (int)((double)(i)*(double)(vdp2width)/(double)wii_width);
	//index=0;	
      
         r = *(buf+index) >> 24;
         g = *(buf+index) >> 16;
         b = *(buf+index) >> 8;
/*
         r = buf[index] >> 24;
         g = buf[index] >> 16;
         b = buf[index] >> 8;
*/
         //buf++;
        
         y  = ( 257 * r + 504 * g +  98 * b +  16000) / 1000;
         cb = (-148 * r - 291 * g + 439 * b + 128000) / 1000; //b-y
         cr = ( 439 * r - 368 * g -  71 * b + 128000) / 1000; //r-y

         //curfb[((int)((double)j*224.0/(double)vdp2height)*320) + (int)((double)i*320.0/(double)vdp2width)] = (y << 24) | (cb << 16) | (y << 8) | cr;
         //curfb[0] = (y << 24) | (cb << 16) | (y << 8) | cr;
         *curfb = (y << 24) | (cb << 16) | (y << 8) | cr;
         curfb++;
#else
   for (j = 0; j < vdp2height; j++)
   {
      for (i = 0; i < vdp2width; i++)
      {
         u8 y, cb, cr;
         u8 r, g, b;

         //index = ((u16)((double)j*(double)vdp2height/224.0))*320+((u16)((double)i*(double)vdp2width/320.0));
         // This isn't pretty
         int y1, cb1, cr1;
         int cb, cr;
         u8 r, g, b;
      
         r = buf[0] >> 24;
         g = buf[0] >> 16;
         b = buf[0] >> 8;
         buf++;
        
         y1 = (299 * r + 587 * g + 114 * b) / 1000;
         cb1 = (-16874 * r - 33126 * g + 50000 * b + 12800000) / 100000;
         cr1 = (50000 * r - 41869 * g - 8131 * b + 12800000) / 100000;
         cb = (cb1 + cb1) >> 1;
         cr = (cr1 + cr1) >> 1;

         curfb[0] = (y1 << 24) | (cb << 16) | (y1 << 8) | cr;
         curfb++;
#endif
      }
   }

   VIDEO_SetNextFramebuffer (xfb[fbsel]);
   VIDEO_Flush ();
}

void gotoxy(int x, int y)
{
   printf("\033[%d;%dH", y, x);
}

void OnScreenDebugMessage(char *string, ...)
{
#if 0
   va_list arglist;
   char debug_buff[256];

   va_start(arglist, string);
   gotoxy(0, 1);
   vprintf(string, arglist);
   printf("\n");
   gotoxy(0, 1);
#ifdef DEBUG
   sprintf(debug_buff, string, arglist);
        //Write menu/debug text on screen
        GXColor fontColor = {150,255,150,255};
        write_font_init_GX(fontColor);
                write_font(10,35,debug_buff, 1.0);
#endif
   va_end(arglist);
#endif
}

int ClearMenu(const unsigned long *bmp)
{
   fbsel ^= 1;
   memcpy (xfb[fbsel], bmp, MENU_SIZE * 2);
   VIDEO_SetNextFramebuffer (xfb[fbsel]);
   VIDEO_Flush ();
   return 0;   
}

typedef struct
{
   char *name;
   int (*func)();
} menuitem_struct;

int MenuNone()
{
   return 0;
}

menuitem_struct menuitem[] = {
{ "Start emulation", YuiExec },
{ "Load ISO/CUE", LoadCue },
{ "Settings", MenuNone },
{ "About", MenuNone },
{ "Exit", NULL },
{ NULL, NULL }
};

void InitMenu()
{
   VIDEO_Init();
   switch(VIDEO_GetCurrentTvMode()) 
   {
      case VI_NTSC:
         rmode = &TVNtsc480IntDf;
	 break;
      case VI_PAL:
         rmode = &TVPal528IntDf;
 	 break;
      case VI_MPAL:
	 rmode = &TVMpal480IntDf;
	 break;
      default:
         rmode = &TVNtsc480IntDf;
	 break;
   }

   xfb[0] = MEM_K0_TO_K1(SYS_AllocateFramebuffer(rmode));
   xfb[1] = MEM_K0_TO_K1(SYS_AllocateFramebuffer(rmode));
   VIDEO_Configure(rmode);
   VIDEO_ClearFrameBuffer (rmode, xfb[0], COLOR_BLACK);
   VIDEO_ClearFrameBuffer (rmode, xfb[1], COLOR_BLACK);
   VIDEO_SetNextFramebuffer(xfb[0]);
   VIDEO_SetBlack(FALSE);
   VIDEO_Flush();
   VIDEO_WaitVSync();
   if(rmode->viTVMode&VI_NON_INTERLACE) 
      VIDEO_WaitVSync();
   //free(_console_buffer);
   if(_console_buffer != NULL) free(_console_buffer);
   _console_buffer = malloc(280*100*VI_DISPLAY_PIX_SZ);
   __console_init_ex(_console_buffer,180,200,rmode->fbWidth*VI_DISPLAY_PIX_SZ,280,100,280*VI_DISPLAY_PIX_SZ);
}

void DoMenu()
{
   //int menuselect=0;
   int i;
   int nummenu=0;

   InitMenu();

   for (i = 0; menuitem[i].name != NULL; i++)
      nummenu++;

   for (;;)
   {
      VIDEO_WaitVSync();
      WPAD_ScanPads();
      PAD_ScanPads();

      // Get Wii Remote/Keyboard/etc. presses
      if (WPAD_ButtonsDown(0) & WPAD_CLASSIC_BUTTON_UP ||
          WPAD_ButtonsDown(0) & WPAD_BUTTON_RIGHT ||
          PAD_ButtonsDown(0) & PAD_BUTTON_UP)
      {
         if(cuemenuflag==0) {
         menuselect--;
         if (menuselect < 0)
            menuselect = nummenu-1;
         } else {
	    scroll_filelist(-1);
         }
      }
      else if (WPAD_ButtonsDown(0) & WPAD_CLASSIC_BUTTON_DOWN ||
               WPAD_ButtonsDown(0) & WPAD_BUTTON_LEFT ||
               PAD_ButtonsDown(0) & PAD_BUTTON_DOWN)
      {          
         if(cuemenuflag==0) {
         menuselect++;
         if (menuselect == nummenu)
            menuselect = 0; 
         } else {
	    scroll_filelist(1);
         }
      }

      if (WPAD_ButtonsDown(0) & WPAD_CLASSIC_BUTTON_A ||
          WPAD_ButtonsDown(0) & WPAD_BUTTON_A ||
          WPAD_ButtonsDown(0) & WPAD_BUTTON_2 ||
          PAD_ButtonsDown(0) & PAD_BUTTON_A) 
      {
          if(cuemenuflag==0) {
          if (menuitem[menuselect].func)
          {
             if (menuitem[menuselect].func())
                return;
             InitMenu();
          }
          else
             return;
          } else { //cuesubmenu
	     //cuemenuflag = 0;
	     GameExec();
          }
      }

      // Draw menu
      ClearMenu(menu_bmp);

      printf("\033[2J");
      //printf("\033[2;0H");
      gotoxy(0, 0);
      if(cuemenuflag==0) {
      // Draw menu items
      for (i = 0; i < nummenu; i++)
      {
         if (menuselect == i) {
            //printf("\033[%d;%dm", 30+9, 0);
            printf("\033[%d;%dm\033[35m", 30+9, 0);
            printf("%s\033[0m\n", menuitem[i].name);
         } else {
            printf("\033[%d;%dm", 30+7, 0);
            printf("%s\n", menuitem[i].name);
         }
      }     
      } else { //select cue submenu
	  print_filelist();
      }
   }
}

int GameExec()
{
   cuemenuflag = 0;
   printf("\033[2;0H");
   //strcpy(isofilename, "/SSROMS/");
   strcpy(isofilename, ROMS_DIR);
   strcat(isofilename, "/");
   strcat(isofilename, filelist[selected].filename);
   menuselect=0;
   return 0;
}
////////



void Check_SD_Init(void)
{
	s32 ret;
	
	//printf("\t[*] Initializing libfat...");
	fflush(stdout);
	ret = sd_init();
	if (!ret) {
		printf(" ERROR! Return to Wii Menu in 5s...");
		sleep(5);
		//Exit_ToWiiMenu();
		exit(0);
	}
	//printf(" OK!\n");
}

void Check_Read_Dir(void)
{
	s32 ret;
	
	//printf("\t[*] Reading SD card...");
	fflush(stdout);
	ret = sd_readdir(ROMS_DIR, &filelist, &nb_files);
	if (ret < 0) {
		printf(" ERROR! (ret = %d) Return to Wii Menu in 5s...", ret);
		sleep(5);
		//Exit_ToWiiMenu();
		exit(0);
	}
	//printf(" OK!\n");
}

void scroll_filelist(s8 delta)
{
	s32 index;

	/* No files */
	if (!nb_files)
		return;

	/* Select next entry */
	selected += delta;

	/* Out of the list? */
	if (selected <= -1)
		selected = nb_files - 1;
	if (selected >= nb_files)
		selected = 0;

	/* List scrolling */
	index = (selected - start);
	if (index >= FILES_PER_PAGE)
		start += (index - FILES_PER_PAGE) + 1;
	if (index <= -1)
		start += index;
}

void print_filelist(void)
{
	u32 cnt;

	//printf("\t[*] Available files on the SD card:\n\n");

	/* No files */
	if (!nb_files) {
		printf("No files available!\n");
		return;
	}

	for (cnt = start; cnt < nb_files; cnt++) {
		/* Files per page limit */
		if ((cnt - start) >= FILES_PER_PAGE)
			break;

		/* Selected file */
		if (cnt == selected) {
			//printf("\t\t>> ");
                      printf("\033[%d;%dm\033[35m", 30+9, 0);
		      printf("%s\033[0m\n", filelist[cnt].filename);
		} else {
			//printf("\t\t   ");
		      printf("\033[%d;%dm", 30+7, 0);
		      printf("%s\n", filelist[cnt].filename);
		}
		fflush(stdout);

		/* Print filename */
		//printf("%s\n", filelist[cnt].filename);
		//fflush(stdout);
	}
}

////////
int LoadCue()
{
   cuemenuflag = 1;
   printf("\033[2;0H");
   gotoxy(0, 0);
   Check_Read_Dir();
   //fat_remount();

   return 0;
}


