#include "raine.h"
#include "starhelp.h" // ByteSwap
#include "sasound.h"
#include <string.h>
#include "neocd.h"
#include "blit.h" // clear_game_screen
#include "files.h"
#include "palette.h"
#include "newspr.h"
#include "cache.h"
#include "profile.h"
#include "cdrom.h"
#include "dsw.h"
#include "iso.h"
#include "newmem.h"

static char *exts[] = {"prg","fix","spr","z80","pcm","pat","jue"};
#define TITLE_X_SYS "title_x.sys"

#define COPY_BIT(a, b) { \
    a <<= 1; \
    a |= (b & 0x01); \
    b >>= 1; }

void extract8(UINT8 *src, UINT8 *dst)
{
   int i;

   unsigned char bh = *src++;
   unsigned char bl = *src++;
   unsigned char ch = *src++;
   unsigned char cl = *src;
   unsigned char al, ah;

   for(i = 0; i < 4; i++)
   {
      al = ah = 0;

      COPY_BIT(al, ch)
      COPY_BIT(al, cl)
      COPY_BIT(al, bh)
      COPY_BIT(al, bl)

      COPY_BIT(ah, ch)
      COPY_BIT(ah, cl)
      COPY_BIT(ah, bh)
      COPY_BIT(ah, bl)

      *dst++ = ((ah << 4) | al);
   }
}

void spr_conv(UINT8 *src, UINT8 *dst, int len, unsigned char *usage_ptr)
{
    register int    i;
    int offset;

    for(i=0;i<len;i+=4) {
        if((i&0x7f)<64)
            offset=(i&0xffff80)+((i&0x7f)<<1)+4;
        else
            offset=(i&0xffff80)+((i&0x7f)<<1)-128;

        extract8(src,dst+offset);
        src+=4;
    }
    for (i=0; i<len; i+= 128) {
      int res = 0;
      int j;
      for (j=0; j<128; j++) {
	if (dst[i+j])
	  res++;
      }
      if (res == 0) // all transp
	usage_ptr[i/128] = 0;
      else if (res == 128)
	usage_ptr[i/128] = 2; // all solid
      else
	usage_ptr[i/128] = 1; // semi
    }
    // Unpack the sprites
    for (i=len-1; i>=0; i--) {
      dst[i*2+1] = dst[i]>>4;
      dst[i*2] = dst[i] & 0xf;
    }
}

static int load_type;

enum{
  ZIP_TYPE = 0,
  IPL_TYPE,
  ISO_TYPE,
  CUE_TYPE };

static int nb_tracks, alloc_tracks;
static char **mp3_track;

void init_load_type() {
  if (alloc_tracks) {
    int n;
    for (n=0; n<nb_tracks; n++) {
      free(mp3_track[n]);
    }
  }
  nb_tracks = 0;
  if (!stricmp(&neocd_path[strlen(neocd_path)-3],"zip"))
    load_type = ZIP_TYPE;
  else if (!stricmp(&neocd_path[strlen(neocd_path)-3],"txt")) 
    load_type = IPL_TYPE;
  else if (!stricmp(&neocd_path[strlen(neocd_path)-3],"cue")) {
    FILE *f = fopen(neocd_path,"r");
    if (f) {
      while (!feof(f)) {
	char buff[80];
	fgets(buff,80,f);
	if (!*buff) 
	  continue;
	int l = strlen(buff);
	while (buff[l-1] < 32 && l > 0) {
	  buff[l-1] = 0;
	  l--;
	}

	if (!strncmp(buff,"FILE",4)) {
	  char *end = strrchr(buff,'"');
	  if (!end) {
	    MessageBox("Error","cue format error","OK");
	    break;
	  }
	  *end = 0;
	  char *start = strchr(buff,'"');
	  if (!start) {
	    MessageBox("Error","cue format error","OK");
	    break;
	  }
	  if (!strncmp(end+2,"BINARY",6)) {
	    char *path = strrchr(neocd_path,SLASH[0]);
	    if (!path) {
	      MessageBox("Error","path format error","OK");
	      break;
	    }
	    strcpy(path+1,start+1);
	  } else if (!strncmp(end+2,"MP3",3)) {
	    if (alloc_tracks == nb_tracks) {
	      alloc_tracks += 10;
	      mp3_track = realloc(mp3_track,alloc_tracks*sizeof(char**));
	      if (!mp3_track) {
		MessageBox("Error","alloc error","OK");
		break;
	      }
	    }
	    mp3_track[nb_tracks++] = strdup(start+1);
	    print_debug("adding mp3 track %s\n",start+1);
	  } else {
	    MessageBox("Error","track format unknown","OK");
	    break;
	  }
	} // FILE
      } // feof
      fclose(f);
      load_type = CUE_TYPE;
    } // if (f)
  } else if (!stricmp(&neocd_path[strlen(neocd_path)-3],"iso")) 
    load_type = ISO_TYPE;
}

char *get_mp3_track(int n) {
  n-=2;
  if (load_type == CUE_TYPE && n < nb_tracks && n >= 0) {
    return mp3_track[n];
  }
  return NULL;
}

int get_size(char *filename) {
  switch(load_type) {
    case ZIP_TYPE: return size_zipped(neocd_path,filename,0);
    case IPL_TYPE: 
      if (!strchr(filename,SLASH[0])) {
	char file[1024];
	sprintf(file,"%s%s%s",neocd_dir,SLASH,filename);
	return size_file(file);
      }
      return size_file(filename);
  }
  // iso, cue
  return iso_size(neocd_path,filename);
}

static int load_neocd(char *name, UINT8 *dest, int size) {
  switch(load_type) {
    case ZIP_TYPE: return load_zipped(neocd_path, name, size, 0, dest, 1);
    case IPL_TYPE: 
      if (!strchr(name,SLASH[0])) {
	char file[1024];
	sprintf(file,"%s%s%s",neocd_dir,SLASH,name);
	return load_file(file,dest,size);
      }
      return load_file(name,dest,size);
    case CUE_TYPE:
    case ISO_TYPE: return load_from_iso(neocd_path, name, dest, size);
  }
  print_debug("couldn't load %s\n",name);
  return 0;
}

extern UINT8 *RAM_PAL;

static int    recon_filetype(char *ext, char *filename)
{
  int n;
  for (n=0; n<sizeof(exts)/sizeof(char*); n++)
    if (!strcmp(ext,exts[n]))
      return n;

  // else try to find the type in the filename !
  for (n=0; n<sizeof(exts)/sizeof(char*); n++)
    if (strstr(filename,exts[n]))
      return n;

  if (!strcmp(ext,"obj")) // sprites in art of fighting !!!!
    return SPR_TYPE;

  // really nothing to do !
  return    -1;
}

static void fix_extension(char *FileName, char *extension) {
  char *ext = strrchr(FileName,'.');
  if (ext) {
    char old[4];
    int size;
    ext++;
    strcpy(old,ext);
    strcpy(ext,extension);
    size = get_size(FileName);
    if (!size)
      strcpy(ext,old); // keep the original
  }
}

void neogeo_cdrom_load_title(void)
{
  /* Loads a title screen based on the currently selected region */
  // all the games do not contain a title screen...
  char            jue[4] = "jue";
  char            file[12] = TITLE_X_SYS;
  int size;
  UINT8 *buff;
  UINT8 *map;
  int                Readed;
  int                x, y;

#ifdef USE_VIDEO_GL
  int filter=neo4all_filter;
  neogeo_adjust_filter(1);
#endif
  //    sound_disable();

  file[6] = jue[GetLanguageSwitch()]; // adjust based on region

  size = get_size(file);
  if (!size) return;
  buff = (UINT8*)malloc(size);

  load_neocd(file,buff,size);
  memcpy(RAM_PAL,buff,0x5a0);
  ByteSwap(RAM_PAL,0x5a0);

  spr_conv(&buff[0x5a0], GFX, size-0x5a0, video_spr_usage);

  clear_game_screen(0);
  ClearPaletteMap();
  Readed = 0;
  for(y=0;y<80;y+=16)
  {
    for(x=0;x<144;x+=16)
    {
      MAP_PALETTE_MAPPED_NEW(
	  Readed,
	  16,
	  map);
      if (video_spr_usage[Readed]) {
	if (video_spr_usage[Readed] == 1)
	  Draw16x16_Trans_Mapped_Rot(&GFX[Readed<<8],(304-144)/2+ x+32,(224-80)/2+ y+32,map);
	else
	  Draw16x16_Mapped_Rot(&GFX[Readed<<8],(304-144)/2+ x+32,(224-80)/2+ y+32,map);
      }
      Readed++;
    }
  }

  DrawNormal();
  // SDL_Delay(1500);
}

static int    neogeo_cdrom_load_prg_file(char *FileName, unsigned int Offset)
{
  UINT8 *Ptr;
  int size;

  int len = 0x200000 - Offset;
  if (len <= 0)
    return 1;

  fix_extension(FileName,"prg");

  size = get_size(FileName);
  if (Offset + size > 0x200000) {
    size = 0x200000-Offset;
    if (size <= 0) return 1;
  }
  Ptr = RAM + Offset;
  if (file_cache(FileName,Offset,size,PRG_TYPE)) {
    return 1; // file already present
  }

  if (!load_neocd(FileName,Ptr,size)) {
    print_debug("could not load %s at %x,%x\n",FileName,Offset,size);
    return 0;
  }
  print_debug("loaded %s at %x,%x\n",FileName,Offset,size);
  ByteSwap(Ptr,size);

  cache_set_crc(Offset,size,PRG_TYPE);

  //    sound_enable();
  return 1;
}

void    fix_conv(UINT8 *Src, UINT8 *Ptr, int Taille, unsigned char *usage_ptr)
{
  int        i;
  unsigned char    usage;

  for(i=Taille;i>0;i-=32) {
    usage = 0;
    *Ptr++ = *(Src+16);
    usage |= *(Src+16);
    *Ptr++ = *(Src+24);
    usage |= *(Src+24);
    *Ptr++ = *(Src);
    usage |= *(Src);
    *Ptr++ = *(Src+8);
    usage |= *(Src+8);
    Src++;
    *Ptr++ = *(Src+16);
    usage |= *(Src+16);
    *Ptr++ = *(Src+24);
    usage |= *(Src+24);
    *Ptr++ = *(Src);
    usage |= *(Src);
    *Ptr++ = *(Src+8);
    usage |= *(Src+8);
    Src++;
    *Ptr++ = *(Src+16);
    usage |= *(Src+16);
    *Ptr++ = *(Src+24);
    usage |= *(Src+24);
    *Ptr++ = *(Src);
    usage |= *(Src);
    *Ptr++ = *(Src+8);
    usage |= *(Src+8);
    Src++;
    *Ptr++ = *(Src+16);
    usage |= *(Src+16);
    *Ptr++ = *(Src+24);
    usage |= *(Src+24);
    *Ptr++ = *(Src);
    usage |= *(Src);
    *Ptr++ = *(Src+8);
    usage |= *(Src+8);
    Src++;
    *Ptr++ = *(Src+16);
    usage |= *(Src+16);
    *Ptr++ = *(Src+24);
    usage |= *(Src+24);
    *Ptr++ = *(Src);
    usage |= *(Src);
    *Ptr++ = *(Src+8);
    usage |= *(Src+8);
    Src++;
    *Ptr++ = *(Src+16);
    usage |= *(Src+16);
    *Ptr++ = *(Src+24);
    usage |= *(Src+24);
    *Ptr++ = *(Src);
    usage |= *(Src);
    *Ptr++ = *(Src+8);
    usage |= *(Src+8);
    Src++;
    *Ptr++ = *(Src+16);
    usage |= *(Src+16);
    *Ptr++ = *(Src+24);
    usage |= *(Src+24);
    *Ptr++ = *(Src);
    usage |= *(Src);
    *Ptr++ = *(Src+8);
    usage |= *(Src+8);
    Src++;
    *Ptr++ = *(Src+16);
    usage |= *(Src+16);
    *Ptr++ = *(Src+24);
    usage |= *(Src+24);
    *Ptr++ = *(Src);
    usage |= *(Src);
    *Ptr++ = *(Src+8);
    usage |= *(Src+8);
    Src+=25;
    *usage_ptr++ = usage;
  }
}

int    neogeo_cdrom_load_fix_file(char *FileName, unsigned int Offset)
{
    UINT8    *Ptr, *buff;
    int size;

//    sound_disable();
    fix_extension(FileName,"fix");

    size = get_size(FileName);
    // size = 0 can happen in some weird disc images from fatal fury
    if (!size) return 1;

    Ptr = neogeo_fix_memory + Offset;
    if (Offset + size > 0x20000) {
      size = 0x20000-Offset;
      if (size <= 0) return 1;
    }
    if (file_cache(FileName,Offset,size,FIX_TYPE)) {
      return 1; // file already present
    }

    buff = (UINT8*)malloc(size);
    if (!load_neocd(FileName,buff,size)) return 0;
    fix_conv(buff, Ptr, size, video_fix_usage + (Offset>>5));
    free(buff);

    cache_set_crc(Offset,size,FIX_TYPE);

    return 1;
}

int    neogeo_cdrom_load_spr_file(char *FileName, unsigned int Offset)
{
    int size;

    UINT8 *Ptr,*buff;

    fix_extension(FileName,"spr");

    size = get_size(FileName);
    if (!size) return 1;

    Ptr = GFX + Offset*2;
    if (Offset + size > 0x400000) {
      size = 0x400000 - Offset;
      if (size < 0) return 1;
      print_debug("warn: sprite size correction %d\n",size);
    }
    if (file_cache(FileName,Offset*2,size*2,SPR_TYPE)) {
      return 1; // file already present
    }

    print_debug("Loading %s offset %x size %x\n",FileName,Offset*2,size*2);
    buff = malloc(size);
    if (!load_neocd(FileName,buff,size)) return 0;
    spr_conv(buff,Ptr,size,video_spr_usage + (Offset>>7));
    free(buff);
    cache_set_crc(Offset*2,size*2,SPR_TYPE);

    return 1;
}

static int    neogeo_cdrom_load_z80_file(char *FileName, unsigned int Offset)
{
    int size;

    fix_extension(FileName,"z80");
    size = get_size(FileName);
    if (!size) return 1;

    if (Offset + size > 0xffe0) {
      // The size must explicitely be fixed to ffe0 to leave the $800 last
      // bytes alone and avoid to overwrite the stack !
      size = 0xffe0-Offset;
      if (size <= 0) return 1;
    }
    if (file_cache(FileName,Offset,size,Z80_TYPE)) {
      return 1; // file already present
    }

    print_debug("load %s %x,%x\n",FileName,Offset,size);
    if (!load_neocd(FileName,&Z80ROM[Offset],size)) return 0;
    cache_set_crc(Offset,size,Z80_TYPE);

    return 1;
}

#define PATCH_Z80(a, b) { \
                            Z80ROM[(a)] = (b)&0xFF; \
                            Z80ROM[(a+1)] = ((b)>>8)&0xFF; \
                        }

void neogeo_cdrom_apply_patch(short *source, int offset, int bank)
{
    int master_offset;

    master_offset = (((bank*1048576) + offset)/256)&0xFFFF;

    while(*source != 0)
    {
        PATCH_Z80( source[0], ((source[1] + master_offset)>>1) );
        PATCH_Z80( source[0] + 2, (((source[2] + master_offset)>>1) - 1) );

        if ((source[3])&&(source[4]))
        {
            PATCH_Z80( source[0] + 5, ((source[3] + master_offset)>>1) );
            PATCH_Z80( source[0] + 7, (((source[4] + master_offset)>>1) - 1) );
        }

        source += 5;
    }
}

static int    neogeo_cdrom_load_pat_file(char *FileName, unsigned int Offset, unsigned int Bank)
{
    int size;
    UINT8 *buff;

    fix_extension(FileName,"pat");
    size = get_size(FileName);
    if (!size) return 1;

    buff = (UINT8*)malloc(size);
    if (!load_neocd(FileName,buff,size)) return 0;
    ByteSwap(buff,size); // byteswap for z80 ???

    neogeo_cdrom_apply_patch((short*)buff, Offset, Bank);
    free(buff);

    return 1;
}

int neogeo_cdrom_load_pcm_file(char *FileName, unsigned int Offset)
{
    int size;

    UINT8 *Ptr;

    /* Some files are clearly not intended to be loaded, see the weird pcm
       file in the ipl.txt of aof for example ! */
    int len = 0x100000 - Offset;
    if (len <= 0)
      return 1;

    fix_extension(FileName,"pcm");
    size = get_size(FileName);
    if (!size) return 1;

    if (Offset + size > 0x100000) {
      print_debug("size was fixed for pcm\n");
      size = 0x100000 - Offset;
      if (size <= 0) return 1;
    }
    if (file_cache(FileName,Offset,size,PCM_TYPE)) {
      return 1; // file already present
    }

    Ptr = PCMROM + Offset;
    print_debug("load %s %x,%x\n",FileName,Offset,size);
    if (!load_neocd(FileName,Ptr,size)) return 0;

    cache_set_crc(Offset,size,PCM_TYPE);

//    sound_enable();

    return 1;
}

static void finish_loading() {
  /* These writes are still necessary, they do what the bios would do if we
     were able to emulate every hardware address used by the cdrom. But we
     are very far from that, so it's much easier to do all the loading in
     only 1 time, and then call this function as if the bios had done it */

  // This one is necessary of art of fighting 3, or you get a black screen
  // during loading. I guess it's some kind of ack... !
  WriteByte(&RAM[0x10F6D9 ^ 1], 0x01);

  // This one clears copy protection (extracted from a tutorial on how to crack
  // neogeo cd games !)
  WriteByte(&RAM[0x10FE85^1], 0x01);
  /* I don't know where these writes come from since there are no comments
     at all (I love this, really !).
     Anyway, what I know is that they hide the fix layer in art of fighting
     when you have played the demo (even 1s of the demo is enough), then
     return to the main screen -> no fix layer if these writes are enabled */
  WriteLongSc(&RAM[0x10F68C], 0x00000000);
  WriteByte(&RAM[0x10F6DB^1], 0x01);
  WriteLongSc(&RAM[0x10F742], 0x00000000);
  WriteLongSc(&RAM[0x10F746], 0x00000000);

  // This is the particular write which blows fix area in aof (commented)
  // WriteByte(&RAM[0x10FDC2], 0x01);
  WriteByte(&RAM[0x10FDDC^1], 0x00); // c0DB60
  WriteByte(&RAM[0x10FDDD^1], 0x00); // c00712
  WriteByte(&RAM[0x10FE88^1], 0x00); // c07E88
  // WriteByte(&RAM[0x10FEC4^1], 0x01); // C0071C
  // this ec4 location prevents magician lord from testing the upload area
  // we'll have to test without it for a while...
  // At the same time, not setting this to 1 freezes mslug at start
  // there is definetely a problem with this address to be investigated...
  // Apparently this adress was linked to 10f6ea
}

int hextodec(char c) {
  switch (tolower(c)) {
    case '0':	return 0;
    case '1':	return 1;
    case '2':	return 2;
    case '3':	return 3;
    case '4':	return 4;
    case '5':	return 5;
    case '6':	return 6;
    case '7':	return 7;
    case '8':	return 8;
    case '9':	return 9;
    case 'a':	return 10;
    case 'b':	return 11;
    case 'c':	return 12;
    case 'd':	return 13;
    case 'e':	return 14;
    case 'f':	return 15;
    default:	return 0;
  }
}

int    neogeo_cdrom_process_ipl()
{
  char    Line[32];
  char    FileName[16];
  int        FileType;
  int        Bnk;
  int        Off;
  int        i, j;
  int	       ret=0;
  UINT8	*buf;
  int size = get_size("ipl.txt")+1;

  sa_pause_sound();
  if (size <= 0) return 0;
  if (!(buf = AllocateMem(size))) return 0;

  memset(buf,0,size);
  if(!load_neocd("ipl.txt",buf,size-1)) {
    ErrorMsg("Could not open IPL.TXT!");
    sa_unpause_sound();
    FreeMem(buf);
    return 0;
  }

  char* bufp = (char*)buf;
  while (1)
  {

    char* p = strchr(bufp,'\n');
    if (p==NULL) break;
    p++;
    int len = p-bufp;
    memcpy(Line,bufp, len);
    Line[len] = 0;
    bufp = p;

    Bnk=0;
    Off=0;
    i=0;
    j=0;
    while((Line[i] != ',')&&(Line[i]!=0))
      FileName[j++] = tolower(Line[i++]);
    FileName[j]=0;

    j -= 3;
    if (j>0) {
      FileType = recon_filetype(&FileName[j],FileName);
      i++;
      j=0;
      // Get the bank number (decimal)
      while(Line[i] != ',') {
	Bnk*=10;
	Bnk+=Line[i]-'0';
	i++;
      }

      i++;
      j=0;
      // Get the offset (hex)
      while(Line[i] != 0x0D) {
	Off*=16;
	Off+=hextodec(Line[i++]);
      }

      Bnk &= 3;

      ret++;
      {

	switch( FileType ) {
	  case PRG_TYPE:
	    if (!neogeo_cdrom_load_prg_file(FileName, Off)) {
	      sa_unpause_sound();
	      ErrorMsg("ipl.txt: error while loading prg.\n");
	      FreeMem(buf);
	      return 0;
	    }
	    break;
	  case FIX_TYPE:
	    if (!neogeo_cdrom_load_fix_file(FileName, (Off>>1))) {
	      sa_unpause_sound();
	      ErrorMsg("ipl.txt: error while loading fix.\n");
	      FreeMem(buf);
	      return 0;
	    }
	    break;
	  case SPR_TYPE:
	    if (!neogeo_cdrom_load_spr_file(FileName, (Bnk*0x100000) + Off)) {
	      ErrorMsg("ipl.txt: error while loading spr.\n");
	      sa_unpause_sound();
	      FreeMem(buf);
	      return 0;
	    }
	    break;
	  case Z80_TYPE:
	    if (!neogeo_cdrom_load_z80_file(FileName, (Off>>1))) {
	      ErrorMsg("ipl.txt: error while loading z80.\n");
	      sa_unpause_sound();
	      FreeMem(buf);
	      return 0;
	    }
	    break;
	  case PAT_TYPE:
	    if (!neogeo_cdrom_load_pat_file(FileName, Off, Bnk)) {
	      ErrorMsg("ipl.txt: error while loading pat.\n");
	      sa_unpause_sound();
	      FreeMem(buf);
	      return 0;
	    }
	    break;
	  case PCM_TYPE:
	    if (!neogeo_cdrom_load_pcm_file(FileName, (Bnk*0x80000) + (Off>>1))) {
	      ErrorMsg("ipl.txt: error while loading pcm.\n");
	      sa_unpause_sound();
	      FreeMem(buf);
	      return 0;
	    }
	    break;
	  default:
	    // I should really find a nice way to debug 1 day, but
	    // this is the fastest way. Disabled by default.
	      print_debug("didn't recognise %s (%d)\n",FileName,FileType);
	}
      }
    }
  }

  finish_loading();

  FreeMem(buf);
  sa_unpause_sound();
  reset_ingame_timer();
  return ret;
}

#define swab(src,dest,len) memcpy(dest,src,len); ByteSwap(dest,len);

static unsigned neogeo_cdrom_test_files(unsigned char *Ptr)
{
  unsigned ret=0;
  char    Entry[32], FileName[14];
  char    *Ext;
  int     i, j, Bnk, Off, Type;

  // pspDebugScreenInit();
  do {
    swab(Ptr, (UINT8 *)Entry, 32);
    i = 0;
    Ptr[1] = 0;

    while((Entry[i]!=0)&&(Entry[i]!=';')) {
      FileName[i] = tolower(Entry[i]);
      i++;
    }

    FileName[i] = 0;

    Bnk = Entry[16]&3;

    Off = ReadLong68k((unsigned char *)&Entry[18]); // Entry is byteswapped
    Ptr += 32;

    j=0;
    while(FileName[j] != '.' && FileName[j] != '\0')
      j++;

    if(FileName[j]=='\0')
    {
      //console_printf("Internal Error loading file: %s",FileName);
      //SDL_Delay(1000);
      print_debug("internal error loading file %s\n",FileName);
      exit(1);
      // ExitCallback(1,2,NULL);
    }

    j++;
    Ext=&FileName[j];

    ret++;
    // printf("Loading File: %s %02x %08x\n", FileName, Bnk, Off);
    //text_draw_loading(ret,check);

    Type = recon_filetype(Ext,FileName);
    switch( Type ) {
      case PRG_TYPE:
	neogeo_cdrom_load_prg_file(FileName, Off);
	break;
      case FIX_TYPE:
	neogeo_cdrom_load_fix_file(FileName, Off>>1);
	break;
      case SPR_TYPE:
	neogeo_cdrom_load_spr_file(FileName, (Bnk*0x100000) + Off);
	break;
      case Z80_TYPE:
	neogeo_cdrom_load_z80_file(FileName, Off>>1);
	break;
      case PAT_TYPE:
	neogeo_cdrom_load_pat_file(FileName, Off, Bnk);
	break;
      case PCM_TYPE:
	neogeo_cdrom_load_pcm_file(FileName, (Bnk*0x80000) + (Off>>1));
	break;
    }
  } while( *Ptr != 0);
  // printf("end of loading\n");
  return ret;
}

void    neogeo_cdrom_load_files(UINT8 *Ptr)
{
  unsigned nfiles=0;

  sa_pause_sound();

  // cdda_stop();
  //menu_raise();
  // cdda_current_track = 0;
  // now_loading();
  // neogeo_cdrom_load_title();

  nfiles=neogeo_cdrom_test_files(Ptr);

  /*
     else
     ERROR !!!!!!!!!!!!!!!!!!
     */

  finish_loading();

  //menu_unraise();
  sa_unpause_sound();
  reset_ingame_timer();
}

