simplified undefined behavior for better compile time processing

--HG--
branch : trunk
diff --git a/jinja2/compiler.py b/jinja2/compiler.py
index 4f5ff0b..c963b8f 100644
--- a/jinja2/compiler.py
+++ b/jinja2/compiler.py
@@ -14,6 +14,7 @@
 from jinja2 import nodes
 from jinja2.visitor import NodeVisitor, NodeTransformer
 from jinja2.exceptions import TemplateAssertionError
+from jinja2.runtime import StaticLoopContext
 
 
 operators = {
@@ -36,6 +37,27 @@
         return generator.stream.getvalue()
 
 
+def has_safe_repr(value):
+    """Does the node have a safe representation?"""
+    if value is None:
+        return True
+    if isinstance(value, (int, long, float, basestring, StaticLoopContext)):
+        return True
+    if isinstance(value, (tuple, list)):
+        for item in value:
+            if not has_safe_repr(item):
+                return False
+        return True
+    elif isinstance(value, dict):
+        for key, value in value.iteritems():
+            if not has_safe_repr(key):
+                return False
+            if not has_safe_repr(value):
+                return False
+        return True
+    return False
+
+
 class Identifiers(object):
     """Tracks the status of identifiers in frames."""
 
@@ -235,7 +257,7 @@
         self.writeline('from jinja2.runtime import *')
         self.writeline('filename = %r' % self.filename)
         self.writeline('template_context = TemplateContext(global_context, '
-                       'make_undefined, filename)')
+                       'filename)')
 
         # generate the root render function.
         self.writeline('def root(context=template_context):', extra=1)
@@ -397,7 +419,7 @@
         for arg in node.defaults:
             self.visit(arg)
             self.write(', ')
-        self.write('), %r, make_undefined)' % accesses_arguments)
+        self.write('), %r)' % accesses_arguments)
 
     def visit_ExprStmt(self, node, frame):
         self.newline(node)
@@ -554,7 +576,7 @@
             self.write(repr(const))
         else:
             self.visit(node.arg, frame)
-        self.write(', make_undefined)')
+        self.write(')')
 
     def visit_Slice(self, node, frame):
         if node.start is not None: