]> https://gitweb.dealii.org/ - dealii.git/commitdiff
Fix a number of exceptions in Triangulation::begin/end/last_...(). 7585/head
authorWolfgang Bangerth <bangerth@colostate.edu>
Thu, 10 Jan 2019 14:01:48 +0000 (07:01 -0700)
committerWolfgang Bangerth <bangerth@colostate.edu>
Wed, 23 Jan 2019 00:16:56 +0000 (17:16 -0700)
include/deal.II/grid/tria.h
source/grid/tria.cc

index b73071eaa2a4ed1361dd497e97710a7e256ed624..88be12f2a269e3e609761d8feab332bdad3ef808 100644 (file)
@@ -3394,10 +3394,14 @@ public:
    *
    * @ingroup Exceptions
    */
-  DeclException1(ExcInvalidLevel,
+  DeclException2(ExcInvalidLevel,
                  int,
-                 << "The given level " << arg1
-                 << " is not in the valid range!");
+                 int,
+                 << "You are requesting information from refinement level "
+                 << arg1
+                 << " of a triangulation, but this triangulation only has "
+                 << arg2 << " refinement levels. The given level " << arg1
+                 << " must be *less* than " << arg2 << ".");
   /**
    * The function raising this exception can only operate on an empty
    * Triangulation, i.e., a Triangulation without grid cells.
index 3f1da7e21136ab1264024a6b682967b67be1b454..19dcf0c48d4c0074634617dae231fe4e5091a842 100644 (file)
@@ -12015,7 +12015,24 @@ template <int dim, int spacedim>
 typename Triangulation<dim, spacedim>::raw_cell_iterator
 Triangulation<dim, spacedim>::end_raw(const unsigned int level) const
 {
-  Assert(level < n_global_levels(), ExcInvalidLevel(level));
+  // This function may be called on parallel triangulations on levels
+  // that exist globally, but not on the local portion of the
+  // triangulation. In that case, just return the end iterator.
+  //
+  // We need to use levels.size() instead of n_levels() because the
+  // latter function uses the cache, but we need to be able to call
+  // this function at a time when the cache is not currently up to
+  // date.
+  if (level >= levels.size())
+    {
+      Assert(level < n_global_levels(),
+             ExcInvalidLevel(level, n_global_levels()));
+      return end();
+    }
+
+  // Query whether the given level is valid for the local portion of the
+  // triangulation.
+  Assert(level < levels.size(), ExcInvalidLevel(level, levels.size()));
   if (level < levels.size() - 1)
     return begin_raw(level + 1);
   else
@@ -12027,11 +12044,28 @@ template <int dim, int spacedim>
 typename Triangulation<dim, spacedim>::cell_iterator
 Triangulation<dim, spacedim>::end(const unsigned int level) const
 {
+  // This function may be called on parallel triangulations on levels
+  // that exist globally, but not on the local portion of the
+  // triangulation. In that case, just retrn the end iterator.
+  //
+  // We need to use levels.size() instead of n_levels() because the
+  // latter function uses the cache, but we need to be able to call
+  // this function at a time when the cache is not currently up to
+  // date.
+  if (level >= levels.size())
+    {
+      Assert(level < n_global_levels(),
+             ExcInvalidLevel(level, n_global_levels()));
+      return end();
+    }
+
+  // Query whether the given level is valid for the local portion of the
+  // triangulation.
+  Assert(level < levels.size(), ExcInvalidLevel(level, levels.size()));
   if (level < levels.size() - 1)
     return begin(level + 1);
-  Assert(level < n_global_levels() || level < levels.size(),
-         ExcInvalidLevel(level));
-  return end();
+  else
+    return end();
 }
 
 
@@ -12039,8 +12073,24 @@ template <int dim, int spacedim>
 typename Triangulation<dim, spacedim>::active_cell_iterator
 Triangulation<dim, spacedim>::end_active(const unsigned int level) const
 {
-  Assert(level < n_global_levels() || level < levels.size(),
-         ExcInvalidLevel(level));
+  // This function may be called on parallel triangulations on levels
+  // that exist globally, but not on the local portion of the
+  // triangulation. In that case, just return the end iterator.
+  //
+  // We need to use levels.size() instead of n_levels() because the
+  // latter function uses the cache, but we need to be able to call
+  // this function at a time when the cache is not currently up to
+  // date.
+  if (level >= levels.size())
+    {
+      Assert(level < n_global_levels(),
+             ExcInvalidLevel(level, n_global_levels()));
+      return end();
+    }
+
+  // Query whether the given level is valid for the local portion of the
+  // triangulation.
+  Assert(level < levels.size(), ExcInvalidLevel(level, levels.size()));
   return (level >= levels.size() - 1 ? active_cell_iterator(end()) :
                                        begin_active(level + 1));
 }
@@ -12213,11 +12263,27 @@ template <int dim, int spacedim>
 typename Triangulation<dim, spacedim>::raw_line_iterator
 Triangulation<dim, spacedim>::begin_raw_line(const unsigned int level) const
 {
+  // This function may be called on parallel triangulations on levels
+  // that exist globally, but not on the local portion of the
+  // triangulation. In that case, just return the end iterator.
+  //
+  // We need to use levels.size() instead of n_levels() because the
+  // latter function uses the cache, but we need to be able to call
+  // this function at a time when the cache is not currently up to
+  // date.
+  if (level >= levels.size())
+    {
+      Assert(level < n_global_levels(),
+             ExcInvalidLevel(level, n_global_levels()));
+      return end_line();
+    }
+
   switch (dim)
     {
       case 1:
-        Assert(level < n_global_levels() || level < levels.size(),
-               ExcInvalidLevel(level));
+        // Query whether the given level is valid for the local portion of the
+        // triangulation.
+        Assert(level < levels.size(), ExcInvalidLevel(level, levels.size()));
 
         if (level >= levels.size() || levels[level]->cells.cells.size() == 0)
           return end_line();
@@ -12283,6 +12349,21 @@ template <int dim, int spacedim>
 typename Triangulation<dim, spacedim>::raw_quad_iterator
 Triangulation<dim, spacedim>::begin_raw_quad(const unsigned int level) const
 {
+  // This function may be called on parallel triangulations on levels
+  // that exist globally, but not on the local portion of the
+  // triangulation. In that case, just return the end iterator.
+  //
+  // We need to use levels.size() instead of n_levels() because the
+  // latter function uses the cache, but we need to be able to call
+  // this function at a time when the cache is not currently up to
+  // date.
+  if (level >= levels.size())
+    {
+      Assert(level < n_global_levels(),
+             ExcInvalidLevel(level, n_global_levels()));
+      return end_quad();
+    }
+
   switch (dim)
     {
       case 1:
@@ -12290,8 +12371,9 @@ Triangulation<dim, spacedim>::begin_raw_quad(const unsigned int level) const
         return raw_hex_iterator();
       case 2:
         {
-          Assert(level < n_global_levels() || level < levels.size(),
-                 ExcInvalidLevel(level));
+          // Query whether the given level is valid for the local portion of the
+          // triangulation.
+          Assert(level < levels.size(), ExcInvalidLevel(level, levels.size()));
 
           if (level >= levels.size() || levels[level]->cells.cells.size() == 0)
             return end_quad();
@@ -12366,6 +12448,21 @@ template <int dim, int spacedim>
 typename Triangulation<dim, spacedim>::raw_hex_iterator
 Triangulation<dim, spacedim>::begin_raw_hex(const unsigned int level) const
 {
+  // This function may be called on parallel triangulations on levels
+  // that exist globally, but not on the local portion of the
+  // triangulation. In that case, just return the end iterator.
+  //
+  // We need to use levels.size() instead of n_levels() because the
+  // latter function uses the cache, but we need to be able to call
+  // this function at a time when the cache is not currently up to
+  // date.
+  if (level >= levels.size())
+    {
+      Assert(level < n_global_levels(),
+             ExcInvalidLevel(level, n_global_levels()));
+      return end_hex();
+    }
+
   switch (dim)
     {
       case 1:
@@ -12374,8 +12471,9 @@ Triangulation<dim, spacedim>::begin_raw_hex(const unsigned int level) const
         return raw_hex_iterator();
       case 3:
         {
-          Assert(level < n_global_levels() || level < levels.size(),
-                 ExcInvalidLevel(level));
+          // Query whether the given level is valid for the local portion of the
+          // triangulation.
+          Assert(level < levels.size(), ExcInvalidLevel(level, levels.size()));
 
           if (level >= levels.size() || levels[level]->cells.cells.size() == 0)
             return end_hex();

In the beginning the Universe was created. This has made a lot of people very angry and has been widely regarded as a bad move.

Douglas Adams


Typeset in Trocchi and Trocchi Bold Sans Serif.