#include "jopen.h"

int
explicite(const char* s) {
   return (
     (strstr(s,"/")   != NULL) |
     (strstr(s,"./")  != NULL) |
     (strstr(s,"../") != NULL) 
   );
}

FILE* 
jopen(char* nom, char* defdir, char* defext)
{
   FILE* r;
   int l0, l1, l2; 
   char* nom_ext = NULL;
   char* curdir_nom = NULL;
   char* defdir_nom = NULL;

   r = NULL;
   l0 = strlen(nom);
   l1 = strlen(defdir);
   l2 = strlen(defext);
   // si explicite on essaie d'ouvrir sans, puis avec extension
   if ( (explicite(nom)) ) {
      // essai sans puis avec l'extension par defaut avec le séparateur ".foo"
      if ( (r=fopen(nom,"r")) == NULL ) {
         nom_ext = strcpy(malloc(l0+l2+2), nom);
         // ajouter un point si besoin -- d'ou le +2 dans malloc
         if ( defext[0] != '.' ) { 
            strcat(nom_ext, ".");
         }
         strcat(nom_ext, defext);
         r=fopen(nom_ext,"r");
         free(nom_ext); nom_ext=NULL;
         return r;    
      } else {
         return r;
      }
   } else { // nom implicite on le rend explicite et appel recursif
            // pour essai avec ./ puis defdir (qui doit être explicite)
      curdir_nom = strcpy(malloc(l0+3), "./" );
      strcat(curdir_nom, nom);
      if ( (r=jopen(curdir_nom, "", defext))==NULL ) {
         free(curdir_nom); curdir_nom=NULL;
         // si defdir est implicite le rendre explicite avec ./ en tête
         if ( explicite(defdir) ) {
             defdir_nom = strcpy(malloc(l1+l0+1),"");
         } else {
             defdir_nom = strcpy(malloc(l1+l0+4),"./");
         }
         defdir_nom = strcat(defdir_nom, defdir);
         // ajouter un / si besoin prévu par le +4 de malloc avec le ./
         if ( defdir[l1-1] != '/' ) {
            strcat(defdir_nom,"/");
         }
         defdir_nom = strcat(defdir_nom,nom);
         r=jopen(defdir_nom,"",defext);
         free(defdir_nom); defdir_nom=NULL;
         return r;
      } else { 
         free(curdir_nom); curdir_nom=NULL;
         return r;
      }
   }
}

// pas de garde fou sur inclusion recursive infinie
int
inclure(char *fich, char *defdir, char *defext) {
   FILE* fd;
   char s[STRSIZE];
   char s0[STRSIZE];

   if ( strncmp(fich,"-",STRSIZE)==0 ) {
     fd = stdin;
   } else {
     fprintf(stdout, "%s Including: %s\n", "%", fich);
     if ( (fd = jopen(fich, defdir, defext)) == NULL ) { return 0; };
   }  
   while ( fgets(s, STRSIZE, fd) != NULL ) {
      if ( strchr(s, '#') == s ) {
         sscanf(s,"#include %s",s0);
         if ( !inclure(s0,defdir,defext) ) { printf("%s Could not include %s\n","%",s0); };
      } else if ( strchr(s, '!') == s ) {
         fflush(stdout);
         system(&s[1]);
      } else {
         fprintf(stdout, "%s", s);
      }
   }
   return 1;
}
