lexer_getfile
authorken <ken@mihrtec.com>
Fri, 21 Oct 2016 03:20:30 +0000 (20:20 -0700)
committerken <ken@mihrtec.com>
Fri, 21 Oct 2016 03:20:30 +0000 (20:20 -0700)
src/apc/lexer.c

index 1abe5b5..096016a 100644 (file)
@@ -18,6 +18,7 @@
 /* Posix */
 #include <unistd.h>
 #include <stdlib.h>
+#include <limits.h> //realpath, NAME_MAX, PATH_MAX
 #include <dirent.h>
 /* Local */
 #include "parser.tab.h"
 #define TK_STACKSIZE 1024
 #endif
 /* Public */
-int  lexer_init(void);
-int  lexer(void);
-int  lexer_lexfile(const char*);
-void lexer_pushtok(int, YYSTYPE);
-extern //lexer_lex.rl
-int lexer_lex(const char*);
+int         lexer_init(void);
+int         lexer(void);
+int         lexer_lexfile(const char*);
+void        lexer_pushtok(int, YYSTYPE);
+char const* lexer_get_current_filepath(void);
 struct dirent* lexer_direntpa[DE_STACKSIZE], **lexer_direntpp;
 /* Private */
+extern //lexer_lex.rl
+int         lexer_lex(const char*);
 extern //scanner.c
-int scanner_init(void);
+int         scanner_init(void);
 extern //scanner.c
-int scanner(void);
+int         scanner(void);
 static inline
-int dredge_current_depth(void);
+int         dredge_current_depth(void);
 extern //bison
-YYSTYPE yylval;
+YYSTYPE     yylval;
+static
+char const* current_filename;
 static
 struct tok
 { YYSTYPE lval;  //token val
   int     tok_t; //token type
-} token_stack[TK_STACKSIZE];
-static
-union tokp
-{ int*        tpt; //token pointer type
-  struct tok* tok;
-  YYSTYPE*    tvp; //token value pointer
-} tks, tkx;
+} token_stack[TK_STACKSIZE], *tsp, *tsx;
 
 /* Directory Entity Array/Stack
    Simple array for keeping track of dirents yet to be processed by the scanner.
@@ -77,20 +75,16 @@ union tokp
    times in a sequence!
 */
 #define TK_STACK     (token_stack)
-#define TK_STACKP    (tks.tok)
-#define TK_STACKPI   (tks.tpt)
-#define TK_STACKPL   (tks.tvp)
-#define TK_STACKX    (tkx.tok)
-#define TK_STACKXI   (tkx.tpt)
+#define TK_STACKP    (tsp)
+#define TK_STACKX    (tsx)
 #define TK_LEN()     (TK_STACKX - TK_STACKP)
 #define TK_INIT()    (TK_STACKP = TK_STACKX = TK_STACK)
 #define TK_POP()     (*TK_STACKP++)
-#define TK_POPI()    (*TK_STACKPI++);
-#define TK_POPL()    (*TK_STACKPL++);
 #define TK_PUSH(T,L) (*TK_STACKX++ = (struct tok){L,T})
 
 /* Initializer
-   The initializer returns boolean true if an error occurs, which may be handled   with standard errno.
+   The initializer returns boolean true if an error occurs, which may be handled
+   with standard errno.
 */
 int lexer_init
 ()
@@ -116,7 +110,8 @@ int lexer
     goto done;                                 \
   } while (0)
 ()
-{start:
+{ struct tok token;
+ start:
   while (DE_LEN() > 0)    //lex any directory entries in our stack
     if (lexer_lexfile(DE_POP()->d_name) == 0)
       FAIL("Lexer failed to tokenize [%s]\n",(*DE_STACKP)->d_name);
@@ -131,8 +126,9 @@ int lexer
            goto start;       //start over and lex them
         }
     }
-  yylval = TK_POPL();
-  return TK_POPI();
+  token = TK_POP();
+  yylval = token.lval;
+  return token.tok_t;
  done:
   yylval.val = 0;
   return 0;
@@ -151,30 +147,44 @@ void lexer_pushtok
       exit(EXIT_FAILURE);
     }
   TK_PUSH(tok, lval);
-  printf("Pushed Token  %i | %i\n", TK_STACK[TK_LEN() - 1].tok_t, TK_STACK[TK_LEN() - 1].lval.val);
 }
 
 /* Lexical analysis of a file
    Strips a filename to its base name, then sends it to lexer_lex
 */
 int lexer_lexfile
-#define MAX_FNAME 2048
 #define HIDDEN_WARNING "%s is hidden and will not be parsed!\n", filename
 ( const char  *filename
 )
-{ static char fname[MAX_FNAME];
+{ static char fname[NAME_MAX];
   char        *last_period = NULL, *iter;
 
   if (*filename == '.')
     { fprintf (stderr, HIDDEN_WARNING);
       return 0;
     }
-  strncpy(fname,filename,MAX_FNAME);
+  /* Copy the filename and remove its suffix */
+  strncpy(fname,filename,NAME_MAX);
   last_period = NULL;
-  for (iter = fname; *iter; iter++)
+  for (iter = fname; *iter; iter++)  //find the last '.' char
     if (*iter == '.')
       last_period = iter;
-  if (last_period)
-    *last_period = '\0';
+  if (last_period)                   //if we found one,
+    *last_period = '\0';             //truncate the string there
+  /* Register the current_filename */
+  current_filename = filename;
+  
   return lexer_lex(fname);
 }
+
+char const* lexer_get_current_filepath
+()
+{ static char        current_path[PATH_MAX];
+  static char const* last_filename;
+  if ((!last_filename || last_filename != current_filename) &&
+      (realpath(current_filename, current_path) != current_path))
+    { perror("realpath: ");
+      return NULL;
+    }
+  return (const char*)current_path;
+}