#include <stdio.h>
#include <stdlib.h>
#include <string.h>
#include <ctype.h>

#include <dirent.h>
#include <unistd.h>
#include <sys/types.h>
#include <sys/stat.h>

#include "globals.h"

#define VERSION "asp2php 0.76.25 - August 17, 2005\n" \
    "Copyright 1998-2005 By Michael Kohn (mike@mikekohn.net)\n" \
    "For info and latest: http://asp2php.naken.cc/\n" \
    "This program falls under the GPL License (http://www.gnu.org/)\n"
#include "functions.h"

/* ASP to PHP converter                */
/* Copyright 1998-2004 by Michael Kohn */

/*

DataBase Types:

1: MySQL
2: ODBC
3: Oracle 8
4: Sybase
5: Postgres

Object Types:

-1: Nothing

 1: ADODB.Connection
 2: ADODB.RecordSet
 3: ADODB.Command
 5: FileSystem Object
 6: JMail
 7: CDONTS.NewMail

*/

char tokenpush[TOKENSIZE]={ 0 };
int tokentypepush=0;
char tokenpush2[TOKENSIZE]={ 0 };
int tokentypepush2=0;
FILE *in,*out;
int pushback=-1;
int indent=0,line=1,column=0;
char objects[80][50];
char objectstype[80][50];
int objectsptr=0;
int database_type=0;
int setvar=0;
int add_isnum=0,add_session=0,BOF=0;
int infunct=0,functptr=0,currdeffunct=-1;
char funct[FUNCTHEAP];
char classes[FUNCTHEAP];
char global_uid[70];
char global_passwd[70];
char global_database[70];
char global_address[70];
char global_dsn[70];
char sessionpool[256][200];
int sessionptr=0;
int classesptr=0;
int pngs=0,y2k=1,casesense=0,php=0;
int html=0,spacer=0;
char aspextensions[20][10];
int aspextensions_ptr=0;
int includes=0;
int javascript=0;
int loopcount=0;
int global_asa=0;
int gif2png=2;
int language=0;
int inbody=0;
int fixwin95paths=0;
int supress=0;
int inclass=0;
int flags=0;

void convert(char *infile, char *outfile);

int copyfiles(char *sourcedir, char *targetdir)
{
DIR *dp_asp;
DIR *dp_php;
struct dirent *direntp;
struct stat statbuf;
char newdir[2048];
char filename_asp[1024];
char filename_php[1024];
int t;

  dp_asp=opendir(sourcedir);

  while ((direntp=readdir(dp_asp))!=NULL)
  {
    if (strcmp(direntp->d_name,".")==0) continue;
    if (strcmp(direntp->d_name,"..")==0) continue;

    sprintf(filename_asp,"%s/%s",sourcedir,direntp->d_name);
    printf("working on file: %s\n",filename_asp);

    if (stat(filename_asp,&statbuf)==-1)
    {
      printf("Error: Couldn't stat file: %s\n\n",sourcedir);
      return 1;
    }

    if (statbuf.st_mode & S_IFDIR)
    {
      sprintf(filename_php,"%s/%s",targetdir,direntp->d_name);
      sprintf(filename_asp,"%s/%s",sourcedir,direntp->d_name);

      dp_php=opendir(filename_php);

      if (dp_php==0)
      {
        /* sprintf(newdir,"mkdir -p \"%s\"",filename_php); */
        /*
        sprintf(newdir,"mkdir -p \"%s\"",filename_php);
	if (system(newdir)!=0)
        */
#ifdef __MINGW32__
        if (mkdir(filename_php)!=0)
#else
        if (mkdir(filename_php,511)!=0)
#endif
        {
          printf("Error: Couldn't create dir: %s\n\n",filename_php);
	  return 1;
        }
      }
        else
      { closedir(dp_php); }

      if (copyfiles(filename_asp,filename_php)==1) return 1;
    }
      else
    {
      sprintf(filename_php,"%s/%s",targetdir,direntp->d_name);
      sprintf(filename_asp,"%s/%s",sourcedir,direntp->d_name);

      t=strlen(filename_php);

      if (is_asp_filename(filename_asp))
      {
        if (php==3) { change_extension(filename_php,".php3"); }
          else
        if (php==4) { change_extension(filename_php,".php4"); }
          else
        { change_extension(filename_php,".php"); }

        convert(filename_asp,filename_php);

        /* strcat(newdir,arguments); */

      }
        else
      if (extcmp(filename_php,".htm")==1 || extcmp(filename_php,".html")==1)
      {
        if (html==1 && extcmp(filename_php,".htm")==1)
        {
          change_extension(filename_php,".html");
        }

        convert(filename_asp,filename_php);
      }
        else
      {
        if (pngs==1 && extcmp(filename_php,".gif")==1 && gif2png!=0)
        {
          if (gif2png==2)
          {
            change_extension(filename_php,".png");
            sprintf(newdir,"convert \"%s\" \"%s\"",filename_asp,filename_php);

            if (system(newdir)!=0)
   	    {
              printf("Error: Couldn't copy file: %s\n\n",filename_asp);
              return 1;
	    }
          }
            else
          if (gif2png==1)
          {
            sprintf(newdir,"cp \"%s\" \"%s\" ; gif2png -d -O \"%s\"",filename_asp,filename_php,filename_php);

            if (system(newdir)!=0)
	    {
              printf("Error: Couldn't copy file: %s\n\n",filename_asp);
              return 1;
	    }
          }
        }
          else
	{
          if (copy_file(filename_asp,filename_php)!=0)
          {
            printf("Error: Couldn't copy file: %s\n\n",filename_asp);
            return 1;
          }
          /* sprintf(newdir,"cp \"%s\" \"%s\"",filename_asp,filename_php); */
        }
      }
    }
  }

  closedir(dp_asp);
  return 0; 
}

void start (char *infile, char *outfile)
{
char sourcedir[2048];
char targetdir[2048];
/* char command[2048]; */
DIR *dp_asp;
DIR *dp_php;
int t;

/* if something looks redundant it's cause I took this code
   from GTKap2php and adapted it to work here :) */

  strcpy(sourcedir,infile);
  strcpy(targetdir,outfile);

  t=strlen(sourcedir);
  while (t>0 && sourcedir[t-1]=='/') { sourcedir[t-1]=0; }
  t=strlen(targetdir);
  while (t>0 && targetdir[t-1]=='/') { targetdir[t-1]=0; }

  dp_asp=opendir(sourcedir);
  if (dp_asp==0)
  {
    printf("Error: ASP Source Dir %s doesn't exist.\n\n",sourcedir);
    return;
  } 
  
  dp_php=opendir(targetdir);
  if (dp_php==0)
  {
    printf("Creating PHP target dir: %s\n\n",targetdir);

/*

man i really *HATE* Microsoft windows.. i used system with
mkdir here cause it made life quite a bit easier with the -p
and all and setting up dir permissions automatically, but i
guess this doesn't work under DOS.

    sprintf(command,"mkdir -p \"%s\"",targetdir);
    t=system(command);

    if (t!=0)
*/

#ifdef __MINGW32__
    if (mkdir(targetdir)!=0)
#else
    if (mkdir(targetdir,511)!=0)
#endif
    {
      printf("Error: Couldn't create PHP target dir: %s\n\n",targetdir);
      return;
    }

    dp_php=opendir(targetdir);

    if (dp_php==0)
    {
      printf("Error: Couldn't create PHP target dir\n");
      return;
    }
  }

  closedir(dp_asp);
  closedir(dp_php);

  printf("Source Dir: %s\n",sourcedir);
  printf("Target Dir: %s\n\n",targetdir);

  fflush(stdout);
/*  printf("copying files\n"); */

  if (copyfiles(sourcedir,targetdir)==1)
  { 
    printf("Problem with sourcedir %s and targetdir %s\n",sourcedir,targetdir);
  }

  return;
}

void preparse(char *infile)
{
FILE *old_in;
char token[TOKENSIZE];
char temp[TOKENSIZE];
int t,tokentype,ch,lastchar;

  old_in=in;
  in=fopen(infile,"rb");
  if (in==NULL)
  { 
    printf("Preparse: Error reading file: %s\n",infile); 
    in=old_in;
    return;
  }

  while((ch=getc(in))!=EOF)
  {
    if (lastchar=='<' && ch=='%')
    {
      while((tokentype=gettoken(token))!=0)
      {
	if (tokentype==6) break;
	if (strcasecmp(token,"isnumeric")==0) add_isnum=1;
          else
	if (strcasecmp(token,"bof")==0) BOF=1;
          else
	if (strcasecmp(token,"function")==0)
	{
	  tokentype=gettoken(token);
          add_funct(token);
	}
	  else
	if (strcasecmp(token,"sub")==0)
	{
	  tokentype=gettoken(token);
          add_funct(token);
	}
          else
	if (strcasecmp(token,"end")==0)
        { tokentype=gettoken(token); }
          else
	if (strcasecmp(token,"exit")==0)
        { tokentype=gettoken(token); }

	if (strcasecmp(token,"session")==0) 
	{
	  add_session=1;
	  tokentype=gettoken(token);
	  if (strcmp(token,"(")==0)
	  {
	    tokentype=gettoken(token);

	    if (tokentype==10 || tokentype==11)
	    {
	      t=gettoken(temp);

	      if (strcmp(temp,")")==0)
	      {
                for (t=0; t<sessionptr; t++)
                {
                  if (strcmp(token,sessionpool[t])==0) break;
                }
              }
                else
              { t=0; }

              if (sessionptr==t)
              {
                strcpy(sessionpool[sessionptr++],token);
              }
            }
	  }
	}
      }
    }
      else
    if (lastchar=='<' && ch=='!')
    {
      lastchar=getc(in);
      ch=getc(in);

      if (lastchar=='-' && ch=='-')
      {
        tokentype=gettoken(token);
        if (strcasecmp(token,"#include")==0)
        {
          tokentype=gettoken(token);
          if (strcasecmp(token,"file")==0)
          {
            tokentype=gettoken(token);
            tokentype=gettoken(token);
            {
              remove_quotes(token);

              if (is_asp_filename(token)==1)
              {
                strcpy(temp,infile);
                dirname_kohn(temp);

                strcat(temp,token);
                if (fixwin95paths==1) fixwinpath(temp);
                printf("Preparsing include file: %s\n",temp);
                preparse(temp);
              }
            }
          }
        }
      }
    }
    pushback=-1;
    lastchar=ch;
  }

  fclose(in);

  in=old_in;
}

void convert(char *infile, char *outfile)
{
int t;

  add_session=0;
  objectsptr=0;
  infunct=0;
  functptr=0;
  indent=0;
  line=1;
  column=0;
  javascript=0;
  loopcount=0;

  if (strlen(outfile)==0)
  {
    strcpy(outfile,infile);
    t=strlen(outfile);
    while (outfile[t]!='.' && t>0) t--;
    if (t!=0) outfile[t]=0;

    if (php==0)
    { strcat(outfile,".php"); }
      else
    if (php==3)
    { strcat(outfile,".php3"); }
      else
    if (php==4)
    { strcat(outfile,".php4"); }
  }

  if (strcmp(outfile,"-")!=0)
  {
    out=fopen(outfile,"w");
    if (out==NULL)
    { printf("Error (convert()) opening output file: %s\n",outfile); return; }

    printf("Opening file: %s\n",infile);
    printf("Creating file: %s\n\n",outfile);
  }
    else
  {
    out=fdopen(STDOUT_FILENO,"w");
  }

  preparse(infile);

  for (t=0; t<80; t++)
  { objects[t][0]=0; }

  in=fopen(infile,"rb");
  if (in==NULL)
  { printf("Error reading file: %s\n",infile); exit(1); }

  if (add_session==1) insert_session();
  if (global_asa==1) { fprintf(out,"<? include('global.php'); ?>\n"); }

  line=1;
  copyhtml();

  if (supress==0)
  {
    putc('\n',out);
    printf("Done.\n");
  }

  fclose(in);
  fclose(out);
}

int main(int argc, char *argv[])
{
char infile[2048];
char outfile[2048];
int dirr=0,t;

  if (argc<2)
  {
    printf("Usage: asp2php { options } <infile.asp>\n");
    printf("          -o <output filename>\n");
    printf("          -dir (infile/outfile are dirs [READ DOCS!!])\n");
    printf("          -mysql -odbc -oracle -sybase -postgres (to select database)\n");
    printf("          -uid <database username>\n");
    printf("          -passwd <database password>\n");
    printf("          -database <database name or sid>\n");
    printf("          -address <database ip address or ip name>\n");
    printf("          -dsn <database ODBC dsn>\n");
    printf("          -pngs (convert references to gifs into pngs)\n");
    printf("          -y2k (if your asp came from a non-y2k compliant NT Box)\n");
    printf("          -php3 or -php4 (change extension to .php3 or .php4 instead of .php)\n");
    printf("          -toupper (change all variables to uppercase)\n");
    printf("          -tolower (change all variables to lowercase)\n");
    printf("          -html (change all references from htm to html)\n");
    printf("          -includes (change #inludes to php requires())\n");
    printf("          -addextension .xxx (asp2php convert files with .xxx extensions)\n");
    printf("          -spacer (space things out more)\n");
    printf("          -gif2png (use gif2png instead of ImageMagick [-pngs mode only])\n");
    printf("          -nomagick (don't convert gif files to png [-pngs mode only])\n");
    printf("          -global_asa (include global.php in all pages)\n");
    printf("          -fixwinpaths (fix windows paths [ '\\' becomes '/' ])\n");
    printf("          -longexternvars (use, for example, $HTTP_POST_VARS instead of $_POST)\n");
    printf("          -fulltags (asp2php will use <?php instead of <?)\n");
    printf("          -change_response_links (in response.write text as .asp will change to .php)\n\n");
    printf(VERSION);
    exit(1);
  }

  global_uid[0]=0;
  global_passwd[0]=0;
  global_dsn[0]=0;
  global_database[0]=0;
  global_address[0]=0;

  strcpy(aspextensions[aspextensions_ptr++],".asp");
  strcpy(aspextensions[aspextensions_ptr++],".asa");
  strcpy(aspextensions[aspextensions_ptr++],".aspx");

  strcpy(infile,"");
  strcpy(outfile,"");

  for(t=1; t<argc; t++)
  {
    if (strcasecmp(argv[t],"-o")==0)
    { strcpy(outfile,argv[++t]); }
      else
    if (strcasecmp(argv[t],"-mysql")==0)
    { database_type=0; }
      else
    if (strcasecmp(argv[t],"-odbc")==0)
    { database_type=1; }
      else
    if (strcasecmp(argv[t],"-oracle")==0)
    { database_type=2; }
      else
    if (strcasecmp(argv[t],"-sybase")==0)
    { database_type=3; }
      else
    if (strcasecmp(argv[t],"-postgres")==0)
    { database_type=4; }
      else
    if (strcasecmp(argv[t],"-uid")==0)
    { strcpy(global_uid,argv[++t]); }
      else
    if (strcasecmp(argv[t],"-y2k")==0)
    { y2k=0; }
      else
    if (strcasecmp(argv[t],"-passwd")==0)
    { strcpy(global_passwd,argv[++t]); }
      else
    if (strcasecmp(argv[t],"-database")==0)
    { strcpy(global_database,argv[++t]); }
      else
    if (strcasecmp(argv[t],"-address")==0)
    { strcpy(global_address,argv[++t]); }
      else
    if (strcasecmp(argv[t],"-dsn")==0)
    { strcpy(global_dsn,argv[++t]); }
      else
    if (strcasecmp(argv[t],"-supress")==0)
    { supress=1; }
      else
    if (strcasecmp(argv[t],"-pngs")==0)
    { pngs=1; }
      else
    if (strcasecmp(argv[t],"-toupper")==0)
    { casesense=2; }
      else
    if (strcasecmp(argv[t],"-tolower")==0)
    { casesense=1; }
      else
    if (strcasecmp(argv[t],"-php3")==0)
    { php=3; }
      else
    if (strcasecmp(argv[t],"-php4")==0)
    { php=4; }
      else
    if (strcasecmp(argv[t],"-dir")==0)
    { dirr=1; }
      else
    if (strcasecmp(argv[t],"-html")==0)
    { html=1; }
      else
    if (strcasecmp(argv[t],"-spacer")==0)
    { spacer=1; }
      else
    if (strcasecmp(argv[t],"-includes")==0)
    { includes=1; }
      else
    if (strcasecmp(argv[t],"-addextension")==0)
    { strcpy(aspextensions[aspextensions_ptr++],argv[++t]); }
      else
    if (strcasecmp(argv[t],"-global_asa")==0)
    { global_asa=1; }
      else
    if (strcasecmp(argv[t],"-gif2png")==0)
    { gif2png=1; }
      else
    if (strcasecmp(argv[t],"-nomagick")==0)
    { gif2png=0; }
      else
    if (strcasecmp(argv[t],"-fixwinpaths")==0)
    { fixwin95paths=1; }
      else
    if (strcasecmp(argv[t],"-fulltags")==0)
    { flags=flags|1; }
      else
    if (strcasecmp(argv[t],"-longexternvars")==0)
    { flags=flags|2; }
      else
    if (strcasecmp(argv[t],"-change_response_links")==0)
    { flags=flags|4; }
      else
    {
      if (strncmp(argv[t],"-",1)==0)
      { printf("Unknown option: %s\n",argv[t]); }
        else
      { strcpy(infile,argv[t]); }
    }
  }

  if (supress==0)
  {
    printf("-----------------------------------------------------\n");
    printf(VERSION);
    printf("-----------------------------------------------------\n\n");
  }

  if (dirr==1)
  { 
    printf("The following extensions will be treated as asp:\n\n");

    for (t=0; t<aspextensions_ptr; t++)
    {
      printf("-->  %s\n",aspextensions[t]);
    }

    if (outfile[0]==0)
    { printf("You must set the output dir with the -o option.\n\n"); }
      else
    { start(infile,outfile); }
  }
    else
  { convert(infile,outfile); }

  return 0;
}

