diff -urN ../composite.orig/composite.module ./composite.module
--- ../composite.orig/composite.module	2009-09-12 06:56:17.000000000 +0000
+++ ./composite.module	2010-05-06 13:56:45.000000000 +0000
@@ -454,35 +454,54 @@
         //   for other modules to do their processing first.
         $layout = composite_get_layout($node->composite_layout);
         if ($layout) {
-          $layout['data'] = $node->composite_layout_data;
-          $node->composite_content = composite_view($node, $layout, $node->composite_references);
-          foreach ($node->composite_content as $zone => $zone_item) {
-            $node->composite_content[$zone] = drupal_render($zone_item);
-          }
 
-          // Add this layout's css, if any
-          if ($layout['css']) {
-            drupal_add_css($layout['css']);
+          // Check for infinite loops
+          if (_composite_nodes_recursion_check($node->nid)) {
+            // FIXME: If the node is being rendered more than once, the message
+            // will appear more than once.
+            if (composite_access('zones', 'update', $node)) {
+              drupal_set_message(t('You have created an infinite loop. One node is displaying a second node which in turn displays the first node.'), 'error');
+            }
+            // Return here to avoid the end of the function unmarking the node
+            // as being rendered.
+            return;
           }
 
-          // Call the appropriate theme('composite_layout...', ...) function.
-          // However, because the number of arguments depends on the number
-          //   of zones in the layout layout, we have to use call_user_func_array
-          
-          // Add in the theme hook name and the first two arguments
-          $args = array(
-            'composite_layout_' . $layout['key'],  // theme hook
-            $layout,                               // layout
-            $node->composite_content               // composite_content
-          );
-
-          // Now add an argument for the contents of each zone
-          foreach ($layout['zones'] as $zone => $unused) {
-            $args[] = $node->composite_content[$zone];
+          else {
+            $layout['data'] = $node->composite_layout_data;
+            $node->composite_content = composite_view($node, $layout, $node->composite_references);
+            foreach ($node->composite_content as $zone => $zone_item) {
+              $node->composite_content[$zone] = drupal_render($zone_item);
+            }
+
+            // Add this layout's css, if any
+            if ($layout['css']) {
+              drupal_add_css($layout['css']);
+            }
+
+            // Call the appropriate theme('composite_layout...', ...) function.
+            // However, because the number of arguments depends on the number
+            //   of zones in the layout layout, we have to use call_user_func_array
+            
+            // Add in the theme hook name and the first two arguments
+            $args = array(
+              'composite_layout_' . $layout['key'],  // theme hook
+              $layout,                               // layout
+              $node->composite_content               // composite_content
+            );
+
+            // Now add an argument for the contents of each zone
+            foreach ($layout['zones'] as $zone => $unused) {
+              $args[] = $node->composite_content[$zone];
+            }
+            
+            // And call it
+            $node->body = call_user_func_array('theme', $args);
           }
-          
-          // And call it
-          $node->body = call_user_func_array('theme', $args);          
+
+          // Unmark the node as being redenred, this will happen only the in
+          // first loop thanks to the upper return statement.
+          _composite_nodes_recursion_check($node->nid, FALSE);
         }
       }
       break;
@@ -620,6 +639,37 @@
   return $composite_content;
 }
 
+/**
+ * Recursion check helper.
+ * 
+ * @param mixed $identifier
+ *   Any object identifier, mostly used is nid.
+ * @param bool $unmark = FALSE
+ *   (optional) Set this to TRUE when you get out from the recursion loop
+ *   to ensure this can be used in another site part which is getting
+ *   rendered.
+ * 
+ * @return boolean
+ *   TRUE if identifier is marked as being rendered, FALSE else.
+ */
+function _composite_nodes_recursion_check($identifier, $unmark = FALSE) {
+  static $rendered = array();
+
+  if ($unmark) {
+    $rendered[$identifier] = FALSE;
+  }
+
+  if (!isset($rendered[$identifier])) {
+    $rendered[$identifier] = TRUE;
+    // If not set, always return TRUE.
+    return FALSE;
+  }
+
+  // Identidifier already set, then check if it's marked as currently
+  // being redered.
+  return $rendered[$identifier];
+}
+
 /***********************************************************
 *               COMPOSITE LAYOUT SETS                      *
 ************************************************************/
diff -urN ../composite.orig/composite.node.inc ./composite.node.inc
--- ../composite.orig/composite.node.inc	2009-03-03 00:39:05.000000000 +0000
+++ ./composite.node.inc	2010-05-06 13:59:02.000000000 +0000
@@ -43,13 +43,17 @@
             break;
 
           case 'full':
-            if (_composite_nodes_recursion_check($node)) {
-              drupal_set_message(t('You have created an infinite loop. One node is displaying a second node which in turn displays the first node.'), 'error');
-              $output =  node_view($node, TRUE, FALSE);
+            // Check for recursion.
+            if (!_composite_nodes_recursion_check($node->nid)) {
+              $output =  node_view($node, FALSE, FALSE);
             }
             else {
-              $output =  node_view($node, FALSE, FALSE);
+              // If any, just return empty output.
+              return '';
             }
+            // Unmark the node as being recursed, if we did not return
+            // before, usefull if the recursion start is here.
+            _composite_nodes_recursion_check($node->nid);
             break;
         }
         return $output;
@@ -134,16 +138,3 @@
     return array();
   }
 }
-
-// Returns true if we there is an infinite loop.
-function _composite_nodes_recursion_check($node) {
-  static $nodes = array();
-
-  if (array_key_exists($node->nid, $nodes)) {
-    return true;
-  }
-  else {  
-    $nodes[$node->nid] = $node->nid;
-    return false;
-  }
-}
