diff --git a/macro/MacroDriver.cc b/macro/MacroDriver.cc
index 4d2399ec0ba91f9a300ecd708c45839305dc54d4..1375e3e46d0a8bf365b25888055455da9e682e3a 100644
--- a/macro/MacroDriver.cc
+++ b/macro/MacroDriver.cc
@@ -205,3 +205,13 @@ MacroDriver::error(const Macro::parser::location_type &l, const MacroValue *valu
 
   error(l, sval->value);
 }
+
+void
+MacroDriver::printvars(const Macro::parser::location_type &l) const
+{
+  cout << "Macroprocessor: Printing macro variable values at line " << l << endl;
+  for (map<string, const MacroValue *>::const_iterator it = env.begin();
+       it != env.end(); it++)
+    cout << "|- " << it->first << " = " << it->second->print() << endl;
+  cout << endl;
+}
diff --git a/macro/MacroDriver.hh b/macro/MacroDriver.hh
index c76947de228faadaac514920e6796e93a4069b33..08c5d3882ff9a8f813f365eb1c2c09a385b059eb 100644
--- a/macro/MacroDriver.hh
+++ b/macro/MacroDriver.hh
@@ -197,6 +197,9 @@ public:
   //! Error handler
   void error(const Macro::parser::location_type &l, const string &m) const;
 
+  //! Print variables
+  void printvars(const Macro::parser::location_type &l) const;
+
   //! Set a variable
   void set_variable(const string &name, const MacroValue *value);
 
diff --git a/macro/MacroFlex.ll b/macro/MacroFlex.ll
index 9c9bc66f79bc73b4f9df8d7d439ceb13a1dfa29c..503dc7bf367186e9a035e65e7eb36df20dc5066b 100644
--- a/macro/MacroFlex.ll
+++ b/macro/MacroFlex.ll
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2008-2016 Dynare Team
+ * Copyright (C) 2008-2017 Dynare Team
  *
  * This file is part of Dynare.
  *
@@ -236,6 +236,8 @@ CONT \\\\
 <STMT>line                  { return token::LINE; }
 <STMT>define                { return token::DEFINE; }
 
+<STMT>echomacrovars{SPC}*{EOL} { driver.printvars(*yylloc); BEGIN(INITIAL); }
+
 <STMT>for                   { reading_for_statement = true; return token::FOR; }
 <STMT>endfor                { driver.error(*yylloc, "@#endfor is not matched by a @#for statement"); }
 
diff --git a/macro/MacroValue.cc b/macro/MacroValue.cc
index b20beb5db8d00392f2a8192a17fd2f76c7b48af7..05a331eefda56dae5d10fb8893800a31ced27e4d 100644
--- a/macro/MacroValue.cc
+++ b/macro/MacroValue.cc
@@ -1,5 +1,5 @@
 /*
- * Copyright (C) 2008-2014 Dynare Team
+ * Copyright (C) 2008-2017 Dynare Team
  *
  * This file is part of Dynare.
  *
@@ -280,6 +280,12 @@ IntMV::toString() const
   return ss.str();
 }
 
+string
+IntMV::print() const
+{
+  return toString();
+}
+
 const MacroValue *
 IntMV::toArray() const
 {
@@ -398,6 +404,12 @@ StringMV::toString() const
   return value;
 }
 
+string
+StringMV::print() const
+{
+  return toString();
+}
+
 const MacroValue *
 StringMV::toArray() const
 {
diff --git a/macro/MacroValue.hh b/macro/MacroValue.hh
index 1097841d9831f9e0c37b5c5e116c6bce691dfbe9..9bcf71bbd66b696379c6c02ce785acdd34e28c89 100644
--- a/macro/MacroValue.hh
+++ b/macro/MacroValue.hh
@@ -91,6 +91,8 @@ public:
   virtual const MacroValue *operator[](const MacroValue &mv) const throw (TypeError, OutOfBoundsError);
   //! Converts value to string
   virtual string toString() const = 0;
+  //! Converts value to be printed
+  virtual string print() const = 0;
   //! Converts value to array form
   virtual const MacroValue *toArray() const = 0;
   //! Gets length
@@ -147,6 +149,7 @@ public:
   //! Computes logical negation
   virtual const MacroValue *operator!() const throw (TypeError);
   virtual string toString() const;
+  virtual string print() const;
   //! Converts value to array form
   /*! Returns an integer array containing a single value */
   virtual const MacroValue *toArray() const;
@@ -187,6 +190,7 @@ public:
   virtual const MacroValue *operator[](const MacroValue &mv) const throw (TypeError, OutOfBoundsError);
   //! Returns underlying string value
   virtual string toString() const;
+  virtual string print() const;
   //! Converts value to array form
   /*! Returns a string array containing a single value */
   virtual const MacroValue *toArray() const;
@@ -226,6 +230,7 @@ public:
   virtual const MacroValue *operator[](const MacroValue &mv) const throw (TypeError, OutOfBoundsError);
   //! Returns a string containing the concatenation of string representations of elements
   virtual string toString() const;
+  virtual string print() const;
   //! Returns itself
   virtual const MacroValue *toArray() const;
   //! Gets length
@@ -335,6 +340,23 @@ ArrayMV<T>::toString() const
   return ss.str();
 }
 
+template<typename T>
+string
+ArrayMV<T>::print() const
+{
+  ostringstream ss;
+  ss << "[";
+  for (typename vector<T>::const_iterator it = values.begin();
+       it != values.end(); it++)
+    {
+      if (it != values.begin())
+        ss << ", ";
+      ss << *it;
+    }
+  ss << "]";
+  return ss.str();
+}
+
 template<typename T>
 const MacroValue *
 ArrayMV<T>::toArray() const