Adding tracking of filename in which token is located.
authorMario de Sousa <msousa@fe.up.pt>
Thu, 14 Apr 2011 17:35:25 +0100
changeset 286 a4f4990d5c66
parent 284 64a4504633d4
child 287 9df7fcb9bde5
Adding tracking of filename in which token is located.
absyntax/absyntax.cc
absyntax/absyntax.hh
stage1_2/iec.flex
stage1_2/iec.y
stage3/visit_expression_type.cc
--- a/absyntax/absyntax.cc	Tue Apr 05 19:42:33 2011 +0100
+++ b/absyntax/absyntax.cc	Thu Apr 14 17:35:25 2011 +0100
@@ -49,24 +49,23 @@
 
 
 /* The base class of all symbols */
-symbol_c::symbol_c(void) {
-  this->first_line   = 0;
-  this->first_column = 0;
-  this->last_line    = 0;
-  this->last_column  = 0;
-}
-
-symbol_c::symbol_c(int first_line, int first_column, int last_line, int last_column) {
+symbol_c::symbol_c(
+                   int first_line, int first_column, const char *ffile,
+                   int last_line,  int last_column,  const char *lfile) {
+  this->first_file   = ffile,
   this->first_line   = first_line;
   this->first_column = first_column;
+  this->last_file    = lfile,
   this->last_line    = last_line;
   this->last_column  = last_column;
 }
 
 
 
-token_c::token_c(const char *value, int fl, int fc, int ll, int lc)
-  :symbol_c(fl, fc, ll, lc) {
+token_c::token_c(const char *value, 
+                 int fl, int fc, const char *ffile,
+                 int ll, int lc, const char *lfile)
+  :symbol_c(fl, fc, ffile, ll, lc, lfile) {
   this->value = value;
 //  printf("New token: %s\n", value);
 }
@@ -76,14 +75,18 @@
 
 
 
-list_c::list_c(int fl, int fc, int ll, int lc)
-  :symbol_c(fl, fc, ll, lc) {
+list_c::list_c(
+               int fl, int fc, const char *ffile,
+               int ll, int lc, const char *lfile)
+  :symbol_c(fl, fc, ffile, ll, lc, lfile) {
   n = 0;
   elements = NULL;
 }
 
-list_c::list_c(symbol_c *elem, int fl, int fc, int ll, int lc)
-  :symbol_c(fl, fc, ll, lc) {
+list_c::list_c(symbol_c *elem, 
+               int fl, int fc, const char *ffile,
+               int ll, int lc, const char *lfile)
+  :symbol_c(fl, fc, ffile, ll, lc, lfile) {
   n = 0;
   elements = NULL;
   add_element(elem);
@@ -123,113 +126,120 @@
 
 
 
-#define SYM_LIST(class_name_c)							\
-class_name_c::class_name_c(int fl, int fc, int ll, int lc)			\
-			:list_c(fl, fc, ll, lc) {}				\
-class_name_c::class_name_c(symbol_c *elem, int fl, int fc, int ll, int lc)	\
-			:list_c(elem, fl, fc, ll, lc) {}			\
-void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
-
-#define SYM_TOKEN(class_name_c)							\
-class_name_c::class_name_c(const char *value, int fl, int fc, int ll, int lc)	\
-			:token_c(value, fl, fc, ll, lc) {}			\
-void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
-
-#define SYM_REF0(class_name_c)					\
-class_name_c::class_name_c(int fl, int fc,			\
-			   int ll, int lc			\
-			  ): symbol_c(fl, fc, ll, lc) {}	\
-void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
-
-
-#define SYM_REF1(class_name_c, ref1)			\
-class_name_c::class_name_c(symbol_c *ref1,		\
-			   int fl, int fc,		\
-			   int ll, int lc		\
-			  ): symbol_c(fl, fc, ll, lc) {	\
-  this->ref1 = ref1;					\
-}							\
-void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
-
-
-#define SYM_REF2(class_name_c, ref1, ref2)		\
-class_name_c::class_name_c(symbol_c *ref1,		\
-			   symbol_c *ref2,		\
-			   int fl, int fc,		\
-			   int ll, int lc		\
-			  ): symbol_c(fl, fc, ll, lc) {	\
-  this->ref1 = ref1;					\
-  this->ref2 = ref2;					\
-}							\
-void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
-
-
-#define SYM_REF3(class_name_c, ref1, ref2, ref3)	\
-class_name_c::class_name_c(symbol_c *ref1,		\
-			   symbol_c *ref2,		\
-			   symbol_c *ref3,		\
-			   int fl, int fc,		\
-			   int ll, int lc		\
-			  ): symbol_c(fl, fc, ll, lc) {	\
-  this->ref1 = ref1;					\
-  this->ref2 = ref2;					\
-  this->ref3 = ref3;					\
-}							\
-void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
-
-
-#define SYM_REF4(class_name_c, ref1, ref2, ref3, ref4)	\
-class_name_c::class_name_c(symbol_c *ref1,		\
-			   symbol_c *ref2,		\
-			   symbol_c *ref3,		\
-			   symbol_c *ref4,		\
-			   int fl, int fc,		\
-			   int ll, int lc		\
-			  ): symbol_c(fl, fc, ll, lc) {	\
-  this->ref1 = ref1;					\
-  this->ref2 = ref2;					\
-  this->ref3 = ref3;					\
-  this->ref4 = ref4;					\
-}							\
-void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
-
-
-#define SYM_REF5(class_name_c, ref1, ref2, ref3, ref4, ref5)		\
-class_name_c::class_name_c(symbol_c *ref1,				\
-			   symbol_c *ref2,				\
-			   symbol_c *ref3,				\
-			   symbol_c *ref4,				\
-			   symbol_c *ref5,				\
-			   int fl, int fc,				\
-			   int ll, int lc				\
-			  ): symbol_c(fl, fc, ll, lc) {			\
-  this->ref1 = ref1;							\
-  this->ref2 = ref2;							\
-  this->ref3 = ref3;							\
-  this->ref4 = ref4;							\
-  this->ref5 = ref5;							\
-}									\
-void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
-
-
-
-#define SYM_REF6(class_name_c, ref1, ref2, ref3, ref4, ref5, ref6)	\
-class_name_c::class_name_c(symbol_c *ref1,				\
-			   symbol_c *ref2,				\
-			   symbol_c *ref3,				\
-			   symbol_c *ref4,				\
-			   symbol_c *ref5,				\
-			   symbol_c *ref6,				\
-			   int fl, int fc,				\
-			   int ll, int lc				\
-			  ): symbol_c(fl, fc, ll, lc) {			\
-  this->ref1 = ref1;							\
-  this->ref2 = ref2;							\
-  this->ref3 = ref3;							\
-  this->ref4 = ref4;							\
-  this->ref5 = ref5;							\
-  this->ref6 = ref6;							\
-}									\
+#define SYM_LIST(class_name_c)									\
+class_name_c::class_name_c(									\
+                           int fl, int fc, const char *ffile,					\
+                           int ll, int lc, const char *lfile)					\
+                        :list_c(fl, fc, ffile, ll, lc, lfile) {}				\
+class_name_c::class_name_c(symbol_c *elem, 							\
+                           int fl, int fc, const char *ffile,					\
+                           int ll, int lc, const char *lfile)					\
+			:list_c(elem, fl, fc, ffile, ll, lc, lfile) {}				\
+void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
+
+#define SYM_TOKEN(class_name_c)									\
+class_name_c::class_name_c(const char *value, 							\
+                           int fl, int fc, const char *ffile,					\
+                           int ll, int lc, const char *lfile)					\
+			:token_c(value, fl, fc, ffile, ll, lc, lfile) {}			\
+void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
+
+#define SYM_REF0(class_name_c)									\
+class_name_c::class_name_c(									\
+                           int fl, int fc, const char *ffile,					\
+                           int ll, int lc, const char *lfile)					\
+			  :symbol_c(fl, fc, ffile, ll, lc, lfile) {}				\
+void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
+
+
+#define SYM_REF1(class_name_c, ref1)								\
+class_name_c::class_name_c(symbol_c *ref1,							\
+                           int fl, int fc, const char *ffile,					\
+                           int ll, int lc, const char *lfile)					\
+			  :symbol_c(fl, fc, ffile, ll, lc, lfile) {				\
+  this->ref1 = ref1;										\
+}												\
+void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
+
+
+#define SYM_REF2(class_name_c, ref1, ref2)							\
+class_name_c::class_name_c(symbol_c *ref1,							\
+			   symbol_c *ref2,							\
+                           int fl, int fc, const char *ffile,					\
+                           int ll, int lc, const char *lfile)					\
+			  :symbol_c(fl, fc, ffile, ll, lc, lfile) {				\
+  this->ref1 = ref1;										\
+  this->ref2 = ref2;										\
+}												\
+void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
+
+
+#define SYM_REF3(class_name_c, ref1, ref2, ref3)						\
+class_name_c::class_name_c(symbol_c *ref1,							\
+			   symbol_c *ref2,							\
+			   symbol_c *ref3,							\
+                           int fl, int fc, const char *ffile,					\
+                           int ll, int lc, const char *lfile)					\
+			  :symbol_c(fl, fc, ffile, ll, lc, lfile) {				\
+  this->ref1 = ref1;										\
+  this->ref2 = ref2;										\
+  this->ref3 = ref3;										\
+}												\
+void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
+
+
+#define SYM_REF4(class_name_c, ref1, ref2, ref3, ref4)						\
+class_name_c::class_name_c(symbol_c *ref1,							\
+			   symbol_c *ref2,							\
+			   symbol_c *ref3,							\
+			   symbol_c *ref4,							\
+                           int fl, int fc, const char *ffile,					\
+                           int ll, int lc, const char *lfile)					\
+			  :symbol_c(fl, fc, ffile, ll, lc, lfile) {				\
+  this->ref1 = ref1;										\
+  this->ref2 = ref2;										\
+  this->ref3 = ref3;										\
+  this->ref4 = ref4;										\
+}												\
+void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
+
+
+#define SYM_REF5(class_name_c, ref1, ref2, ref3, ref4, ref5)					\
+class_name_c::class_name_c(symbol_c *ref1,							\
+			   symbol_c *ref2,							\
+			   symbol_c *ref3,							\
+			   symbol_c *ref4,							\
+			   symbol_c *ref5,							\
+                           int fl, int fc, const char *ffile,					\
+                           int ll, int lc, const char *lfile)					\
+			  :symbol_c(fl, fc, ffile, ll, lc, lfile) {				\
+  this->ref1 = ref1;										\
+  this->ref2 = ref2;										\
+  this->ref3 = ref3;										\
+  this->ref4 = ref4;										\
+  this->ref5 = ref5;										\
+}												\
+void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
+
+
+
+#define SYM_REF6(class_name_c, ref1, ref2, ref3, ref4, ref5, ref6)				\
+class_name_c::class_name_c(symbol_c *ref1,							\
+			   symbol_c *ref2,							\
+			   symbol_c *ref3,							\
+			   symbol_c *ref4,							\
+			   symbol_c *ref5,							\
+			   symbol_c *ref6,							\
+                           int fl, int fc, const char *ffile,					\
+                           int ll, int lc, const char *lfile)					\
+			  :symbol_c(fl, fc, ffile, ll, lc, lfile) {				\
+  this->ref1 = ref1;										\
+  this->ref2 = ref2;										\
+  this->ref3 = ref3;										\
+  this->ref4 = ref4;										\
+  this->ref5 = ref5;										\
+  this->ref6 = ref6;										\
+}												\
 void *class_name_c::accept(visitor_c &visitor) {return visitor.visit(this);}
 
 
--- a/absyntax/absyntax.hh	Tue Apr 05 19:42:33 2011 +0100
+++ b/absyntax/absyntax.hh	Thu Apr 14 17:35:25 2011 +0100
@@ -70,16 +70,15 @@
      */
     int first_line;
     int first_column;
+    const char *first_file;  /* filename referenced by first line/column */
     int last_line;
     int last_column;
+    const char *last_file;  /* filename referenced by last line/column */
 
   public:
     /* default constructor */
-    symbol_c(void);
-    symbol_c(int fl     /* first_line   */, 
-             int fc     /* first_column */,
-             int ll = 0 /* last_line    */,
-             int lc = 0 /* last_column  */
+    symbol_c(int fl = 0, int fc = 0, const char *ffile = NULL /* filename */,
+             int ll = 0, int lc = 0, const char *lfile = NULL /* filename */
             );
 
     /* default destructor */
@@ -96,7 +95,10 @@
     const char *value;
 
   public:
-    token_c(const char *value, int fl = 0, int fc = 0, int ll = 0, int lc = 0);
+    token_c(const char *value, 
+            int fl = 0, int fc = 0, const char *ffile = NULL /* filename */,
+            int ll = 0, int lc = 0, const char *lfile = NULL /* filename */
+           );
 };
 
 
@@ -107,8 +109,14 @@
     symbol_c **elements;
 
   public:
-    list_c(int fl = 0, int fc = 0, int ll = 0, int lc = 0);
-    list_c(symbol_c *elem, int fl = 0, int fc = 0, int ll = 0, int lc = 0);
+    list_c(int fl = 0, int fc = 0, const char *ffile = NULL /* filename */,
+           int ll = 0, int lc = 0, const char *lfile = NULL /* filename */
+          );
+
+    list_c(symbol_c *elem, 
+	   int fl = 0, int fc = 0, const char *ffile = NULL /* filename */,
+           int ll = 0, int lc = 0, const char *lfile = NULL /* filename */
+          );
      /* insert a new element */
     virtual void add_element(symbol_c *elem);
 };
@@ -116,131 +124,138 @@
 
 
 
-#define SYM_LIST(class_name_c)								\
-class class_name_c:	public list_c {							\
-  public:										\
-    class_name_c(int fl = 0, int fc = 0, int ll = 0, int lc = 0);			\
-    class_name_c(symbol_c *elem, int fl = 0, int fc = 0, int ll = 0, int lc = 0);	\
-    virtual void *accept(visitor_c &visitor);						\
-};
-
-
-#define SYM_TOKEN(class_name_c)								\
-class class_name_c: 	public token_c {						\
-  public:										\
-    class_name_c(const char *value, int fl = 0, int fc = 0, int ll = 0, int lc = 0);	\
-    virtual void *accept(visitor_c &visitor);						\
-};
-
-
-#define SYM_REF0(class_name_c)			\
-class class_name_c: public symbol_c {		\
-  public:					\
-    class_name_c(int fl = 0, int fc = 0, 	\
-		 int ll = 0, int lc = 0);	\
-    virtual void *accept(visitor_c &visitor);	\
-};
-
-
-#define SYM_REF1(class_name_c, ref1)			\
-class class_name_c: public symbol_c {			\
-  public:						\
-    symbol_c *ref1;					\
-  public:						\
-    class_name_c(symbol_c *ref1,			\
-		 int fl = 0, int fc = 0, 		\
-		 int ll = 0, int lc = 0);		\
-    virtual void *accept(visitor_c &visitor);		\
-};
-
-
-#define SYM_REF2(class_name_c, ref1, ref2)		\
-class class_name_c: public symbol_c {			\
-  public:						\
-    symbol_c *ref1;					\
-    symbol_c *ref2;					\
-  public:						\
-    class_name_c(symbol_c *ref1,			\
-		 symbol_c *ref2 = NULL,			\
-		 int fl = 0, int fc = 0, 		\
-		 int ll = 0, int lc = 0);		\
-    virtual void *accept(visitor_c &visitor);		\
-};
-
-
-#define SYM_REF3(class_name_c, ref1, ref2, ref3)	\
-class class_name_c: public symbol_c {			\
-  public:						\
-    symbol_c *ref1;					\
-    symbol_c *ref2;					\
-    symbol_c *ref3;					\
-  public:						\
-    class_name_c(symbol_c *ref1,			\
-		 symbol_c *ref2,			\
-		 symbol_c *ref3,			\
-		 int fl = 0, int fc = 0, 		\
-		 int ll = 0, int lc = 0);		\
-    virtual void *accept(visitor_c &visitor);		\
-};
-
-
-#define SYM_REF4(class_name_c, ref1, ref2, ref3, ref4)	\
-class class_name_c: public symbol_c {			\
-  public:						\
-    symbol_c *ref1;					\
-    symbol_c *ref2;					\
-    symbol_c *ref3;					\
-    symbol_c *ref4;					\
-  public:						\
-    class_name_c(symbol_c *ref1,			\
-		 symbol_c *ref2,			\
-		 symbol_c *ref3,			\
-		 symbol_c *ref4 = NULL,			\
-		 int fl = 0, int fc = 0, 		\
-		 int ll = 0, int lc = 0);		\
-    virtual void *accept(visitor_c &visitor);		\
-};
-
-
-#define SYM_REF5(class_name_c, ref1, ref2, ref3, ref4, ref5)		\
-class class_name_c: public symbol_c {					\
-  public:								\
-    symbol_c *ref1;							\
-    symbol_c *ref2;							\
-    symbol_c *ref3;							\
-    symbol_c *ref4;							\
-    symbol_c *ref5;							\
-  public:								\
-    class_name_c(symbol_c *ref1,					\
-		 symbol_c *ref2,					\
-		 symbol_c *ref3,					\
-		 symbol_c *ref4,					\
-		 symbol_c *ref5,					\
-		 int fl = 0, int fc = 0, 				\
-		 int ll = 0, int lc = 0);				\
-    virtual void *accept(visitor_c &visitor);				\
-};
-
-
-#define SYM_REF6(class_name_c, ref1, ref2, ref3, ref4, ref5, ref6)	\
-class class_name_c: public symbol_c {					\
-  public:								\
-    symbol_c *ref1;							\
-    symbol_c *ref2;							\
-    symbol_c *ref3;							\
-    symbol_c *ref4;							\
-    symbol_c *ref5;							\
-    symbol_c *ref6;							\
-  public:								\
-    class_name_c(symbol_c *ref1,					\
-		 symbol_c *ref2,					\
-		 symbol_c *ref3,					\
-		 symbol_c *ref4,					\
-		 symbol_c *ref5,					\
-		 symbol_c *ref6 = NULL,					\
-		 int fl = 0, int fc = 0, 				\
-		 int ll = 0, int lc = 0);				\
-    virtual void *accept(visitor_c &visitor);				\
+#define SYM_LIST(class_name_c)												\
+class class_name_c:	public list_c {											\
+  public:														\
+    class_name_c(													\
+                 int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, 					\
+                 int ll = 0, int lc = 0, const char *lfile = NULL /* filename */);					\
+    class_name_c(symbol_c *elem, 											\
+                 int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, 					\
+                 int ll = 0, int lc = 0, const char *lfile = NULL /* filename */);					\
+    virtual void *accept(visitor_c &visitor);										\
+};
+
+
+#define SYM_TOKEN(class_name_c)												\
+class class_name_c: 	public token_c {										\
+  public:														\
+    class_name_c(const char *value, 											\
+                 int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, 					\
+                 int ll = 0, int lc = 0, const char *lfile = NULL /* filename */);					\
+    virtual void *accept(visitor_c &visitor);										\
+};
+
+
+#define SYM_REF0(class_name_c)												\
+class class_name_c: public symbol_c {											\
+  public:														\
+    class_name_c(		 											\
+                 int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, 					\
+                 int ll = 0, int lc = 0, const char *lfile = NULL /* filename */);					\
+    virtual void *accept(visitor_c &visitor);										\
+};
+
+
+#define SYM_REF1(class_name_c, ref1)											\
+class class_name_c: public symbol_c {											\
+  public:														\
+    symbol_c *ref1;													\
+  public:														\
+    class_name_c(symbol_c *ref1,											\
+                 int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, 					\
+                 int ll = 0, int lc = 0, const char *lfile = NULL /* filename */);					\
+    virtual void *accept(visitor_c &visitor);										\
+};
+
+
+#define SYM_REF2(class_name_c, ref1, ref2)										\
+class class_name_c: public symbol_c {											\
+  public:														\
+    symbol_c *ref1;													\
+    symbol_c *ref2;													\
+  public:														\
+    class_name_c(symbol_c *ref1,											\
+		 symbol_c *ref2 = NULL,											\
+                 int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, 					\
+                 int ll = 0, int lc = 0, const char *lfile = NULL /* filename */);					\
+    virtual void *accept(visitor_c &visitor);										\
+};
+
+
+#define SYM_REF3(class_name_c, ref1, ref2, ref3)									\
+class class_name_c: public symbol_c {											\
+  public:														\
+    symbol_c *ref1;													\
+    symbol_c *ref2;													\
+    symbol_c *ref3;													\
+  public:														\
+    class_name_c(symbol_c *ref1,											\
+		 symbol_c *ref2,											\
+		 symbol_c *ref3,											\
+                 int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, 					\
+                 int ll = 0, int lc = 0, const char *lfile = NULL /* filename */);					\
+    virtual void *accept(visitor_c &visitor);										\
+};
+
+
+#define SYM_REF4(class_name_c, ref1, ref2, ref3, ref4)									\
+class class_name_c: public symbol_c {											\
+  public:														\
+    symbol_c *ref1;													\
+    symbol_c *ref2;													\
+    symbol_c *ref3;													\
+    symbol_c *ref4;													\
+  public:														\
+    class_name_c(symbol_c *ref1,											\
+		 symbol_c *ref2,											\
+		 symbol_c *ref3,											\
+		 symbol_c *ref4 = NULL,											\
+                 int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, 					\
+                 int ll = 0, int lc = 0, const char *lfile = NULL /* filename */);					\
+    virtual void *accept(visitor_c &visitor);										\
+};
+
+
+#define SYM_REF5(class_name_c, ref1, ref2, ref3, ref4, ref5)								\
+class class_name_c: public symbol_c {											\
+  public:														\
+    symbol_c *ref1;													\
+    symbol_c *ref2;													\
+    symbol_c *ref3;													\
+    symbol_c *ref4;													\
+    symbol_c *ref5;													\
+  public:														\
+    class_name_c(symbol_c *ref1,											\
+		 symbol_c *ref2,											\
+		 symbol_c *ref3,											\
+		 symbol_c *ref4,											\
+		 symbol_c *ref5,											\
+                 int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, 					\
+                 int ll = 0, int lc = 0, const char *lfile = NULL /* filename */);					\
+    virtual void *accept(visitor_c &visitor);										\
+};
+
+
+#define SYM_REF6(class_name_c, ref1, ref2, ref3, ref4, ref5, ref6)							\
+class class_name_c: public symbol_c {											\
+  public:														\
+    symbol_c *ref1;													\
+    symbol_c *ref2;													\
+    symbol_c *ref3;													\
+    symbol_c *ref4;													\
+    symbol_c *ref5;													\
+    symbol_c *ref6;													\
+  public:														\
+    class_name_c(symbol_c *ref1,											\
+		 symbol_c *ref2,											\
+		 symbol_c *ref3,											\
+		 symbol_c *ref4,											\
+		 symbol_c *ref5,											\
+		 symbol_c *ref6 = NULL,											\
+                 int fl = 0, int fc = 0, const char *ffile = NULL /* filename */, 					\
+                 int ll = 0, int lc = 0, const char *lfile = NULL /* filename */);					\
+    virtual void *accept(visitor_c &visitor);										\
 };
 
 
--- a/stage1_2/iec.flex	Tue Apr 05 19:42:33 2011 +0100
+++ b/stage1_2/iec.flex	Thu Apr 14 17:35:25 2011 +0100
@@ -184,11 +184,13 @@
  * back to the bison parser...
  */
 #define YY_USER_ACTION {\
-	  yylloc.first_line = current_tracking->lineNumber;\
-  	yylloc.first_column = current_tracking->currentTokenStart;\
-  	yylloc.last_line = current_tracking->lineNumber;\
-  	yylloc.last_column = current_tracking->currentChar - 1;\
-  	current_tracking->currentTokenStart = current_tracking->currentChar;\
+	yylloc.first_line = current_tracking->lineNumber;\
+	yylloc.first_column = current_tracking->currentTokenStart;\
+	yylloc.first_file = current_filename;\
+	yylloc.last_line = current_tracking->lineNumber;\
+	yylloc.last_column = current_tracking->currentChar - 1;\
+	yylloc.last_file = current_filename;\
+	current_tracking->currentTokenStart = current_tracking->currentChar;\
 	}
 
 
@@ -858,7 +860,13 @@
 			       * the first one (i.e. the one that gets stored in include_stack[0],
 			       * which is never free'd!
 			       */
-			    free((char *)current_filename);
+			    /* NOTE: We do __NOT__ free the malloc()'d memory since 
+			     *       pointers to this filename will be kept by many objects
+			     *       in the abstract syntax tree.
+			     *       This will later be used to provide correct error
+			     *       messages during semantic analysis (stage 3)
+			     */
+			    /* free((char *)current_filename); */
 			    current_filename = include_stack[include_stack_ptr].filename;
 			    yy_push_state(include_end);
 			  }
--- a/stage1_2/iec.y	Tue Apr 05 19:42:33 2011 +0100
+++ b/stage1_2/iec.y	Thu Apr 14 17:35:25 2011 +0100
@@ -116,10 +116,32 @@
 /* Macros used to pass the line and column locations when
  * creating a new object for the abstract syntax tree.
  */
-#define locloc(foo) foo.first_line, foo.first_column, foo.last_line, foo.last_column
-#define   locf(foo) foo.first_line, foo.first_column
-#define   locl(foo) foo.last_line,  foo.last_column
-
+#define locloc(foo) foo.first_line, foo.first_column, foo.first_file, foo.last_line, foo.last_column, foo.last_file
+#define   locf(foo) foo.first_line, foo.first_column, foo.first_file
+#define   locl(foo) foo.last_line,  foo.last_column, foo.last_file
+
+/* Redefine the default action to take for each rule, so that the filenames are correctly processed... */
+# define YYLLOC_DEFAULT(Current, Rhs, N)                                \
+         do                                                                  \
+           if (N)                                                            \
+             {                                                               \
+               (Current).first_line   = YYRHSLOC(Rhs, 1).first_line;         \
+               (Current).first_column = YYRHSLOC(Rhs, 1).first_column;       \
+               (Current).first_file   = YYRHSLOC(Rhs, 1).first_file;         \
+               (Current).last_line    = YYRHSLOC(Rhs, N).last_line;          \
+               (Current).last_column  = YYRHSLOC(Rhs, N).last_column;        \
+               (Current).last_file    = YYRHSLOC(Rhs, 1).last_file;          \
+             }                                                               \
+           else                                                              \
+             {                                                               \
+               (Current).first_line   = (Current).last_line   =              \
+                 YYRHSLOC(Rhs, 0).last_line;                                 \
+               (Current).first_column = (Current).last_column =              \
+                 YYRHSLOC(Rhs, 0).last_column;                               \
+               (Current).first_file   = (Current).last_file   =              \
+                 YYRHSLOC(Rhs, 0).last_file;                                 \
+             }                                                               \
+         while (0)
 
 
 /* A macro for printing out internal parser errors... */
@@ -182,8 +204,10 @@
 /* print an error message */
 void print_err_msg(int first_line,
                    int first_column,
+                   const char *first_filename,
                    int last_line,
                    int last_column,
+                   const char *last_filename,
                    const char *additional_error_msg);
 %}
 
@@ -194,6 +218,44 @@
 // %expect-rr 1
 
 
+/* The following definitions need to be inside a '%code requires' 
+ * so that they are also included in the header files. If this were not the case,
+ * YYLTYPE would be delcared as something in the iec.cc file, and another thing
+ * (actually the default value of YYLTYPE) in the iec.y.hh heder file.
+ */
+%code requires {
+/* define a new data type to store the locations, so we can also store
+ * the filename in which the token is expressed.
+ */
+/* NOTE: since this code will be placed in the iec.y.hh header file,
+ * as well as the iec.cc file that also includes the iec.y.hh header file,
+ * declaring the typedef struct yyltype__local here would result in a 
+ * compilation error when compiling iec.cc, as this struct would be
+ * declared twice.
+ * We therefore use the #if !defined YYLTYPE ...
+ * to make sure only the first declaration is parsed by the C++ compiler.
+ *
+ * At first glance it seems that what we really should do is delcare the
+ * YYLTYPE directly as an anonymous struct, thus:
+ * #define YYLTYPE struct{ ...}
+ * however, this also results in compilation errors.
+ *
+ * I (Mario) think this is kind of a hack. If you know how to
+ * do this re-declaration of YYLTYPE properly, please let me know!
+ */
+#if ! defined YYLTYPE && ! defined YYLTYPE_IS_DECLARED
+  typedef struct {
+    int first_line;
+    int first_column;
+    const char *first_file;
+    int last_line;
+    int last_column;
+    const char *last_file;
+  } yyltype__local;
+  #define YYLTYPE yyltype__local
+#endif
+}
+
 
 
 %union {
@@ -7829,13 +7891,24 @@
 
 void print_err_msg(int first_line,
                    int first_column,
+                   const char *first_filename,
                    int last_line,
                    int last_column,
+                   const char *last_filename,
                    const char *additional_error_msg) {
-  if (full_token_loc)
-  	fprintf(stderr, "%s:%d-%d..%d-%d: error : %s\n", current_filename, first_line, first_column, last_line, last_column, additional_error_msg);
-  else
-  	fprintf(stderr, "%s:%d: error : %s\n", current_filename, first_line, additional_error_msg);
+
+  const char *unknown_file = "<unknown_file>";
+  if (first_filename == NULL) first_filename = unknown_file;
+  if ( last_filename == NULL)  last_filename = unknown_file;
+
+  if (full_token_loc) {
+    if (first_filename == last_filename)
+      fprintf(stderr, "%s:%d-%d..%d-%d: error : %s\n", first_filename, first_line, first_column, last_line, last_column, additional_error_msg);
+    else
+      fprintf(stderr, "%s:%d-%d..%s:%d-%d: error : %s\n", first_filename, first_line, first_column, last_filename, last_line, last_column, additional_error_msg);
+  } else {
+      fprintf(stderr, "%s:%d: error : %s\n", first_filename, first_line, additional_error_msg);
+  }
   //fprintf(stderr, "error %d: %s\n", yynerrs /* a global variable */, additional_error_msg);
   print_include_stack();
   //fprintf(stderr, "%s(%d-%d): %s\n", current_filename, first_line, last_line, current_error_msg);
@@ -7926,8 +7999,10 @@
   res = new identifier_c(strdup(name), 
                          il_operator->first_line,
                          il_operator->first_column,
+                         il_operator->first_file,
                          il_operator->last_line,
-                         il_operator->last_column
+                         il_operator->last_column,
+                         il_operator->last_file
                         );
   free(il_operator);
   return res;
--- a/stage3/visit_expression_type.cc	Tue Apr 05 19:42:33 2011 +0100
+++ b/stage3/visit_expression_type.cc	Thu Apr 14 17:35:25 2011 +0100
@@ -43,8 +43,25 @@
 #include <string.h>
 #include <strings.h>
 
-
-
+/*
+static inline symbol_c * FIRST_(symbol_c *symbol1, symbol_c *symbol2) {
+  if (symbol1->first_file  == symbol2->first_file)   return symbol1;
+
+  if (symbol1->first_line   < symbol2->first_line)   return symbol1;
+  if (symbol1->first_line   > symbol2->first_line)   return symbol2;
+  if (symbol1->first_column < symbol2->first_column) return symbol1;
+  if (symbol1->first_column > symbol2->first_column) return symbol2;
+  return symbol1;
+}
+
+#define FIRST_(symbol1, symbol2) (((symbol1)->last_file   == (symbol2)->first_file)   ? (symbol1) :    \
+                                  ((symbol1)->first_file  == (symbol2)->last_file)    ? (symbol2) :    \
+                                  ((symbol1)->first_line   < (symbol2)->first_line)   ? (symbol1) :    \
+                                  ((symbol1)->first_line   > (symbol2)->first_line)   ? (symbol2) :    \
+                                  ((symbol1)->first_column < (symbol2)->first_column) ? (symbol1) :    \
+                                  ((symbol1)->first_column > (symbol2)->first_column) ? (symbol2) :    \
+                                  (symbol1))
+*/
 #define FIRST_(symbol1, symbol2) (((symbol1)->first_line   < (symbol2)->first_line)   ? (symbol1) :    \
                                   ((symbol1)->first_line   > (symbol2)->first_line)   ? (symbol2) :    \
                                   ((symbol1)->first_column < (symbol2)->first_column) ? (symbol1) :    \
@@ -58,9 +75,9 @@
                                   (symbol1))
 
 #define STAGE3_ERROR(symbol1, symbol2, msg) {                                          \
-    fprintf(stderr, "semantic error between (%d:%d) and (%d:%d): %s\n",                \
-           FIRST_(symbol1,symbol2)->first_line, FIRST_(symbol1,symbol2)->first_column, \
-           LAST_(symbol1,symbol2) ->last_line,  LAST_(symbol1,symbol2) ->last_column,  \
+    fprintf(stderr, "%s:(%d:%d) .. %s(%d:%d): %s\n",                                   \
+           FIRST_(symbol1,symbol2)->first_file, FIRST_(symbol1,symbol2)->first_line, FIRST_(symbol1,symbol2)->first_column, \
+           LAST_(symbol1,symbol2) ->last_file,  LAST_(symbol1,symbol2) ->last_line,  LAST_(symbol1,symbol2) ->last_column,  \
            msg);                                                                       \
     il_error = true;                                                                   \
     error_found = true;                                                                \