/* BonLex program - tar fram data för .DXR filer */
/* EE 960715, 961027 */
/* Misslyckas med att hitta texter ex T043.dxr */

/* Hitta
		 * txtCastNames (eller CAS* om det inte fanns) därefter följer 
           CASt blocken som förhoppningsvis är 'giltiga'
         * Första STXT blocket därefter
*/
#define _STRICT_ANSI

#include <stdio.h>
#include <stdlib.h>
#include <strings.h>
#include <ctype.h>
#ifdef _AMIGA
  #include <dos.h>
#endif

#pragma msg 62 ignore
#pragma msg 187 ignore

#define ZCASt 0x43415374
#define ZSTXT 0x53545854
#define ZCAS_ 0x4341532a

char infile[128];
FILE *fp;

char ordData[80], temp; 
long int langd, slask, stxtpos, namepos, picpos,
             rawnum,rawlen,rawpos;
short int npic,nstxt,ncast,i,k,m;


long int alignfp(void)
{
  long int fpos;
  char tmpch;

  fpos = ftell(fp);
  if(fpos & 1) 
  {
    tmpch = fgetc(fp);
    fpos++;
  }
  return (fpos);
}

long int getmaxpos(void)
{
  long int fsize;

  fseek(fp, 4, SEEK_SET);
  fread(&fsize, sizeof(long int), 1, fp);
  return fsize;
}

long int findcast(long int maxpos)
{
  char tmpch, cmpstr[]="txtCastNames", inpstr[80];
  long int fpos;
  size_t len;

  fpos = alignfp();
  len = strlen(cmpstr);

  /* Detta ska vara en udda adress */
  tmpch = fgetc(fp);
  fpos++;

  /* Leta efter första bokstaven */
  while(fpos < maxpos)
  {
    tmpch = fgetc(fp);
    fpos++;
    if(tmpch == cmpstr[0])
    {
      #ifdef _AMIGA
        chkabort();
      #endif
      fread(inpstr, sizeof(char), (len - 1), fp);
      inpstr[len - 1] = '\0';
      if(strcmp(&cmpstr[1], inpstr)==0)
      {
        fpos--;
        printf("Hittade strängen vid pos 0x%08x\n", fpos);
        return fpos;
      }
      else
      {
        /* Backa filpekaren */
        fseek(fp, fpos, SEEK_SET);
      }
    }
    tmpch = fgetc(fp);
    fpos++;
  }
  printf("Hittade inte strängen \"%s\"\n",cmpstr);
  return -1;
}

long int findcas(long int maxpos, BOOL silent)
{
  char tmpch, cmpstr[]="CAS*", inpstr[80];
  long int fpos;
  size_t len;

  fpos = alignfp();
  len = strlen(cmpstr);

  /* Leta efter första bokstaven */
  while(fpos < maxpos)
  {
    tmpch = fgetc(fp);
    fpos++;
    if(tmpch == cmpstr[0])
    {
      #ifdef _AMIGA
        chkabort();
      #endif
      fread(inpstr, sizeof(char), (len - 1), fp);
      inpstr[len - 1] = '\0';
      if(strcmp(&cmpstr[1], inpstr)==0)
      {
        fpos--;
        if(!silent)
        {
          printf("Hittade CAS* vid pos 0x%08x\n", fpos);
        }
        return fpos;
      }
      else
      {
        /* Backa filpekaren */
        fseek(fp, fpos, SEEK_SET);
      }
    }
    tmpch = fgetc(fp);
    fpos++;
  }
  if(!silent)
  {
    printf("Hittade inte strängen \"%s\"\n",cmpstr);
  }
  return -1;
}

long int findcast2(long int maxpos)
{
  char tmpch, cmpstr[]="CASt", inpstr[16];
  long int fpos, blksize;
  size_t len;
  int i, allnum;

  fpos = alignfp();
  len = strlen(cmpstr);

  /* Detta ska vara en jämn adress */

  /* Leta efter första bokstaven */
  while(fpos < maxpos)
  {
    tmpch = fgetc(fp);
    fpos++;
    if(tmpch == cmpstr[0])
    {
      #ifdef _AMIGA
        chkabort();
      #endif
      fread(inpstr, sizeof(char), (len - 1), fp);
      inpstr[len - 1] = '\0';
      if(strcmp(&cmpstr[1], inpstr)==0)
      {
        /* Kolla om CASt blocket är OK */
        fread(&blksize, sizeof(long int), 1, fp);
        if(blksize < 0x66)
        {
          fseek(fp, (blksize - 7), SEEK_CUR);
        }
        else
        {
          fseek(fp, 0x5f, SEEK_CUR);
        }
        /* Först ska det vara ett T (ref 46-97) */
        tmpch = fgetc(fp);
        allnum = 0;
        if(tmpch == 'T') allnum = 1;

        /* Läs det som måste vara siffror */
        fread(inpstr, sizeof(char), 4, fp);
        inpstr[4] = '\0';

        /* Är alla siffror ?*/
        for(i=0; i<4; i++)
        {
          if(isdigit((int)(inpstr[i]))==0) allnum = 0;
        }
        if(allnum)
        {
          fpos--;
          printf("Hittade CASt vid pos 0x%08x\n", fpos);
          return fpos;
        }
        fpos = alignfp();
        tmpch = fgetc(fp);
        fpos++;
      }
    }
    tmpch = fgetc(fp);
    fpos++;
  }
  printf("Hittade inte CASt\n");
  return -1;
}


long int findstxt(long int maxpos)
{
  char tmpch, cmpstr[]="STXT", inpstr[16];
  long int fpos;
  size_t len;
  int i, alltext;

  fpos = alignfp();
  len = strlen(cmpstr);

  /* Detta ska vara en jämn adress */

  /* Leta efter första bokstaven */
  while(fpos < maxpos)
  {
    tmpch = fgetc(fp);
    fpos++;
    if(tmpch == cmpstr[0])
    {
      #ifdef _AMIGA
        chkabort();
      #endif
      fread(inpstr, sizeof(char), (len - 1), fp);
      inpstr[len - 1] = '\0';
      if(strcmp(&cmpstr[1], inpstr)==0)
      {
        /* printf("fp=0x%lx\n",ftell(fp)); */
        /* Kolla om STXT blocket är OK */
        fseek(fp, 16, SEEK_CUR);
        fread(inpstr, sizeof(char), 16, fp);

        /* Är det text? */
        alltext = 1;
        for(i=0; i<16; i++)
        {
          if(inpstr[i]<0x09 && inpstr[i]>=0x00) alltext = 0;
        }

        /* Kolla om det är "siffertabellen" */
        alltext = -alltext;
        for(i=1; i<6; i++)
        {
          if(inpstr[i]<'0' || inpstr[i]>'9') alltext = abs(alltext);
        }

        if(alltext>0)
        {
          fpos--;
          printf("Hittade STXT vid pos 0x%08x\n", fpos);
          return fpos;
        }
      }
      /* Backa filpekaren */
      fseek(fp, fpos, SEEK_SET);
    }
    tmpch = fgetc(fp);
    fpos++;
  }
  printf("Hittade inte STXT\n");
  return -1;
}


int main(int argc, char *argv[])
{
  long int maxpos, strfpos, castpos, stxtpos;

  /* Kolla ev. inparametrar */

  if(argc!=2) 
  {
    printf("Usage: %s filename\n", argv[0]);
    return 0;
  }
  else 
  {
    /* Fixa filnamn */
    if(strlen(argv[1])<4) 
    {
      sscanf(argv[1],"%d",&slask);
      sprintf(infile,"CD0:TEXT/T%03d.DXR",slask);
    }
  }

  /* Öppna filen */
  printf("Öppnar %s\n",infile);
  fp = fopen(infile, "r");

  /* Felhantering */
  if(fp == NULL)
  {    
    printf("\n*** Kunde inte öppna filen: %s \n",infile);
    return EXIT_FAILURE;
  }

  /* Sök */
  maxpos = getmaxpos();
  printf("Söker...\n");
  strfpos = findcast(maxpos - 16);
  if(strfpos>0)
  {
    castpos = findcast2(maxpos - 16);
    stxtpos = findstxt(maxpos -16);
  }
  else
  {
    maxpos = getmaxpos();
    strfpos = findcas(maxpos - 16, TRUE);
    strfpos = findcas(maxpos - 16, TRUE);
    strfpos = findcas(maxpos - 16, FALSE);
    if(strfpos>0)
    {
      castpos = findcast2(maxpos - 16);
      stxtpos = findstxt(maxpos -16);
    }
  }
  fclose(fp);
 
}



