From d4c7b58a4b97a33838aae71ebe41b09d4acadbfe Mon Sep 17 00:00:00 2001 From: Paul Romano Date: Wed, 27 Sep 2017 11:24:33 -0500 Subject: [PATCH] Change how error codes/messages are handled between C API and Python --- openmc/capi/core.py | 13 +++ openmc/capi/error.py | 109 ++++++++++++++------------ openmc/capi/nuclide.py | 2 +- openmc/capi/settings.py | 38 ++------- src/api.F90 | 5 +- src/error.F90 | 30 +++---- src/geometry_header.F90 | 23 ++++-- src/material_header.F90 | 19 ++++- src/nuclide_header.F90 | 15 +++- src/settings.F90 | 2 +- src/source_header.F90 | 7 +- src/tallies/tally.F90 | 5 +- src/tallies/tally_filter.F90 | 9 ++- src/tallies/tally_filter_energy.F90 | 14 +++- src/tallies/tally_filter_header.F90 | 12 ++- src/tallies/tally_filter_material.F90 | 16 +++- src/tallies/tally_filter_mesh.F90 | 8 +- src/tallies/tally_header.F90 | 47 ++++++++--- 18 files changed, 227 insertions(+), 147 deletions(-) diff --git a/openmc/capi/core.py b/openmc/capi/core.py index 4302a94f4..4335bcc46 100644 --- a/openmc/capi/core.py +++ b/openmc/capi/core.py @@ -157,3 +157,16 @@ def run_in_memory(intracomm=None): yield finally: finalize() + + +class _DLLGlobal(object): + """Data descriptor that exposes global variables from libopenmc.""" + def __init__(self, ctype, name): + self.ctype = ctype + self.name = name + + def __get__(self, instance, owner): + return self.ctype.in_dll(_dll, self.name).value + + def __set__(self, instance, value): + self.ctype.in_dll(_dll, self.name).value = value diff --git a/openmc/capi/error.py b/openmc/capi/error.py index 2058ceb20..8e37ea089 100644 --- a/openmc/capi/error.py +++ b/openmc/capi/error.py @@ -1,10 +1,45 @@ -from ctypes import c_int +from ctypes import c_int, c_char from . import _dll -class GeometryError(Exception): - pass +class Error(Exception): + """Root exception class for OpenMC.""" + + +class GeometryError(Error): + """Geometry-related error""" + + +class InvalidIDError(Error): + """Use of an ID that is invalid.""" + + +class AllocationError(Error): + """Error related to memory allocation.""" + + +class OutOfBoundsError(Error): + """Index in array out of bounds.""" + + +class DataError(Error): + """Error relating to nuclear data.""" + + +class PhysicsError(Error): + """Error relating to performing physics.""" + + +class InvalidArgumentError(Error): + """Argument passed was invalid.""" + + +class InvalidTypeError(Error): + """Tried to perform an operation on the wrong type.""" + + +_errmsg = (c_char*256).in_dll(_dll, 'openmc_err_msg') def _error_handler(err, func, args): @@ -14,53 +49,27 @@ def _error_handler(err, func, args): def errcode(s): return c_int.in_dll(_dll, s).value - if err == errcode('e_out_of_bounds'): - raise IndexError('Array index out of bounds.') - - elif err == errcode('e_cell_not_allocated'): - raise MemoryError("Memory has not been allocated for cells.") - - elif err == errcode('e_cell_invalid_id'): - raise KeyError("No cell exists with ID={}.".format(args[0])) - - elif err == errcode('e_cell_not_found'): - raise GeometryError("Could not find cell at position ({}, {}, {})" - .format(*args[0])) - - elif err == errcode('e_nuclide_not_allocated'): - raise MemoryError("Memory has not been allocated for nuclides.") - - elif err == errcode('e_nuclide_not_loaded'): - raise KeyError("No nuclide named '{}' has been loaded.") - - elif err == errcode('e_nuclide_not_in_library'): - raise KeyError("Specified nuclide doesn't exist in the cross " - "section library.") - - elif err == errcode('e_material_not_allocated'): - raise MemoryError("Memory has not been allocated for materials.") - - elif err == errcode('e_material_invalid_id'): - raise KeyError("No material exists with ID={}.".format(args[0])) - - elif err == errcode('e_tally_not_allocated'): - raise MemoryError("Memory has not been allocated for tallies.") - - elif err == errcode('e_tally_invalid_id'): - raise KeyError("No tally exists with ID={}.".format(args[0])) - - elif err == errcode('e_invalid_size'): - raise MemoryError("Array size mismatch with memory allocated.") - - elif err == errcode('e_cell_no_material'): - raise GeometryError("Operation on cell requires that it be filled" - " with a material.") - - elif err == errcode('w_below_min_bound'): - warn("Data has not been loaded beyond lower bound of {}.".format(args[0])) - - elif err == errcode('w_above_max_bound'): - warn("Data has not been loaded beyond upper bound of {}.".format(args[0])) + # Get error message set by OpenMC library + msg = _errmsg.value.decode() + # Raise exception type corresponding to error code + if err == errcode('e_allocate'): + raise AllocationError(msg) + elif err == errcode('e_out_of_bounds'): + raise OutOfBoundsError(msg) + elif err == errcode('e_invalid_argument'): + raise InvalidArgumentError(msg) + elif err == errcode('e_invalid_type'): + raise InvalidTypeError(msg) + if err == errcode('e_invalid_id'): + raise IDError(msg) + elif err == errcode('e_geometry'): + raise GeometryError(msg) + elif err == errcode('e_data'): + raise DataError(msg) + elif err == errcode('e_physics'): + raise PhysicsError(msg) + elif err == errcode('e_warning'): + warn(msg) elif err < 0: raise Exception("Unknown error encountered (code {}).".format(err)) diff --git a/openmc/capi/nuclide.py b/openmc/capi/nuclide.py index 26a98e32e..6e3245e9e 100644 --- a/openmc/capi/nuclide.py +++ b/openmc/capi/nuclide.py @@ -81,7 +81,7 @@ class _NuclideMapping(Mapping): def __getitem__(self, key): index = c_int() _dll.openmc_get_nuclide_index(key.encode(), index) - return NuclideView(index) + return NuclideView(index.value) def __iter__(self): for i in range(len(self)): diff --git a/openmc/capi/settings.py b/openmc/capi/settings.py index 40d1768cf..11b0eacef 100644 --- a/openmc/capi/settings.py +++ b/openmc/capi/settings.py @@ -1,6 +1,7 @@ from ctypes import c_int, c_int32, c_int64, c_double, c_char_p, POINTER from . import _dll +from .core import _DLLGlobal from .error import _error_handler _RUN_MODES = {1: 'fixed source', @@ -11,37 +12,12 @@ _RUN_MODES = {1: 'fixed source', class _Settings(object): - @property - def batches(self): - return c_int32.in_dll(_dll, 'n_batches').value - - @batches.setter - def batches(self, n): - _dll.openmc_set_batches(n) - - @property - def generations_per_batch(self): - return c_int32.in_dll(_dll, 'gen_per_batch').value - - @generations_per_batch.setter - def generations_per_batch(self, n): - _dll.openmc_set_generations_per_batch(n) - - @property - def inactive(self): - return c_int32.in_dll(_dll, 'n_inactive').value - - @inactive.setter - def inactive(self, n): - _dll.openmc_set_inactive_batches(n) - - @property - def particles(self): - return c_int64.in_dll(_dll, 'n_particles').value - - @particles.setter - def particles(self, n): - _dll.openmc_set_particles(n) + # Attributes that are accessed through a descriptor + batches = _DLLGlobal(c_int32, 'n_batches') + generations_per_batch = _DLLGlobal(c_int32, 'gen_per_batch') + inactive = _DLLGlobal(c_int32, 'n_inactive') + particles = _DLLGlobal(c_int64, 'n_particles') + verbosity = _DLLGlobal(c_int, 'verbosity') @property def run_mode(self): diff --git a/src/api.F90 b/src/api.F90 index c451920ac..1c995806b 100644 --- a/src/api.F90 +++ b/src/api.F90 @@ -194,7 +194,10 @@ contains instance = p % cell_instance - 1 err = 0 else - err = E_CELL_NOT_FOUND + err = E_GEOMETRY + call set_errmsg("Could not find cell/material at position (" // & + trim(to_str(xyz(1))) // "," // trim(to_str(xyz(2))) // "," // & + trim(to_str(xyz(3))) // ").") end if end function openmc_find diff --git a/src/error.F90 b/src/error.F90 index 93c56ec61..92902a04c 100644 --- a/src/error.F90 +++ b/src/error.F90 @@ -14,28 +14,18 @@ module error ! Error codes integer(C_INT), public, bind(C) :: E_UNASSIGNED = -1 - integer(C_INT), public, bind(C) :: E_OUT_OF_BOUNDS = -2 - integer(C_INT), public, bind(C) :: E_CELL_NOT_ALLOCATED = -3 - integer(C_INT), public, bind(C) :: E_CELL_INVALID_ID = -4 - integer(C_INT), public, bind(C) :: E_CELL_NOT_FOUND = -5 - integer(C_INT), public, bind(C) :: E_NUCLIDE_NOT_ALLOCATED = -6 - integer(C_INT), public, bind(C) :: E_NUCLIDE_NOT_LOADED = -7 - integer(C_INT), public, bind(C) :: E_NUCLIDE_NOT_IN_LIBRARY = -8 - integer(C_INT), public, bind(C) :: E_MATERIAL_NOT_ALLOCATED = -9 - integer(C_INT), public, bind(C) :: E_MATERIAL_INVALID_ID = -10 - integer(C_INT), public, bind(C) :: E_TALLY_NOT_ALLOCATED = -11 - integer(C_INT), public, bind(C) :: E_TALLY_INVALID_ID = -12 - integer(C_INT), public, bind(C) :: E_INVALID_SIZE = -13 - integer(C_INT), public, bind(C) :: E_CELL_NO_MATERIAL = -14 - integer(C_INT), public, bind(C) :: E_ALREADY_ALLOCATED = -15 - integer(C_INT), public, bind(C) :: E_ARGUMENT_INVALID = -16 - integer(C_INT), public, bind(C) :: E_WRONG_TYPE = -17 - integer(C_INT), public, bind(C) :: E_FILTER_NOT_ALLOCATED = -18 - integer(C_INT), public, bind(C) :: E_FILTER_INVALID_ID = -19 + integer(C_INT), public, bind(C) :: E_ALLOCATE = -2 + integer(C_INT), public, bind(C) :: E_OUT_OF_BOUNDS = -3 + integer(C_INT), public, bind(C) :: E_INVALID_SIZE = -4 + integer(C_INT), public, bind(C) :: E_INVALID_ARGUMENT = -5 + integer(C_INT), public, bind(C) :: E_INVALID_TYPE = -6 + integer(C_INT), public, bind(C) :: E_INVALID_ID = -7 + integer(C_INT), public, bind(C) :: E_GEOMETRY = -8 + integer(C_INT), public, bind(C) :: E_DATA = -9 + integer(C_INT), public, bind(C) :: E_PHYSICS = -10 ! Warning codes - integer(C_INT), public, bind(C) :: W_BELOW_MIN_BOUND = 1 - integer(C_INT), public, bind(C) :: W_ABOVE_MAX_BOUND = 2 + integer(C_INT), public, bind(C) :: E_WARNING = 1 ! Error message character(kind=C_CHAR), public, bind(C) :: openmc_err_msg(256) diff --git a/src/geometry_header.F90 b/src/geometry_header.F90 index 32b8fc915..4d77b45e3 100644 --- a/src/geometry_header.F90 +++ b/src/geometry_header.F90 @@ -437,10 +437,12 @@ contains index = cell_dict % get_key(id) err = 0 else - err = E_CELL_INVALID_ID + err = E_INVALID_ID + call set_errmsg("No cell exists with ID=" // trim(to_str(id)) // ".") end if else - err = E_CELL_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Memory has not been allocated for cells.") end if end function openmc_get_cell_index @@ -456,6 +458,7 @@ contains err = 0 else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in cells array is out of bounds.") end if end function openmc_cell_get_id @@ -487,7 +490,9 @@ contains ! error if the cell is filled with another universe if (cells(index) % fill /= NONE) then - err = E_CELL_NO_MATERIAL + err = E_GEOMETRY + call set_errmsg("Cannot set temperature on a cell filled & + &with a universe.") else ! find which material is associated with this cell (material_index ! is the index into the materials array) @@ -539,14 +544,22 @@ contains ! temperature was changed correctly. This needs to be done after ! changing the temperature based on the logical structure above. if (err == 0) then - if (outside_low) err = W_BELOW_MIN_BOUND - if (outside_high) err = W_ABOVE_MAX_BOUND + if (outside_low) then + err = E_WARNING + call set_errmsg("Nuclear data has not been loaded beyond lower & + &bound of T=" // trim(to_str(T)) // " K.") + else if (outside_high) then + err = E_WARNING + call set_errmsg("Nuclear data has not been loaded beyond upper & + &bound of T=" // trim(to_str(T)) // " K.") + end if end if end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in cells array is out of bounds.") end if end function openmc_cell_set_temperature diff --git a/src/material_header.F90 b/src/material_header.F90 index 44bfdd25b..1846551a7 100644 --- a/src/material_header.F90 +++ b/src/material_header.F90 @@ -85,7 +85,6 @@ contains real(8) :: sum_percent real(8) :: awr - err = E_UNASSIGNED if (allocated(m % atom_density)) then ! Set total density based on value provided m % density = density @@ -105,6 +104,9 @@ contains + m % atom_density(i) * awr * MASS_NEUTRON / N_AVOGADRO end do err = 0 + else + err = E_ALLOCATE + call set_errmsg("Material atom density array hasn't been allocated.") end if end function material_set_density @@ -246,10 +248,12 @@ contains index = material_dict % get_key(id) err = 0 else - err = E_MATERIAL_INVALID_ID + err = E_INVALID_ID + call set_errmsg("No material exists with ID=" // trim(to_str(id)) // ".") end if else - err = E_MATERIAL_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Memory has not been allocated for materials.") end if end function openmc_get_material_index @@ -314,6 +318,7 @@ contains end associate else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in materials array is out of bounds.") end if end function openmc_material_add_nuclide @@ -328,7 +333,6 @@ contains integer(C_INT), intent(out) :: n integer(C_INT) :: err - err = E_UNASSIGNED if (index >= 1 .and. index <= size(materials)) then associate (m => materials(index)) if (allocated(m % atom_density)) then @@ -336,10 +340,14 @@ contains densities = C_LOC(m % atom_density(1)) n = size(m % atom_density) err = 0 + else + err = E_ALLOCATE + call set_errmsg("Material atom density array has not been allocated.") end if end associate else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in materials array is out of bounds.") end if end function openmc_material_get_densities @@ -355,6 +363,7 @@ contains err = 0 else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in materials array is out of bounds.") end if end function openmc_material_get_id @@ -372,6 +381,7 @@ contains end associate else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in materials array is out of bounds.") end if end function openmc_material_set_density @@ -423,6 +433,7 @@ contains end associate else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in materials array is out of bounds.") end if end function openmc_material_set_densities diff --git a/src/nuclide_header.F90 b/src/nuclide_header.F90 index 0c0dcff72..f2b4a6951 100644 --- a/src/nuclide_header.F90 +++ b/src/nuclide_header.F90 @@ -866,10 +866,13 @@ contains index = nuclide_dict % get_key(to_lower(name_)) err = 0 else - err = E_NUCLIDE_NOT_LOADED + err = E_DATA + call set_errmsg("No nuclide named '" // trim(name_) // & + "' has been loaded.") end if else - err = E_NUCLIDE_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Memory for nuclides has not been allocated.") end if end function openmc_get_nuclide_index @@ -926,7 +929,9 @@ contains call nuclides(n) % init_grid(energy_min_neutron, & energy_max_neutron, n_log_bins) else - err = E_NUCLIDE_NOT_IN_LIBRARY + err = E_DATA + call set_errmsg("Nuclide '" // trim(name_) // "' is not present & + &in library.") end if end if @@ -949,9 +954,11 @@ contains err = 0 else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in nuclides array is out of bounds.") end if else - err = E_NUCLIDE_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Memory for nuclides has not been allocated yet.") end if end function openmc_nuclide_name diff --git a/src/settings.F90 b/src/settings.F90 index 7e81872a0..83aebce86 100644 --- a/src/settings.F90 +++ b/src/settings.F90 @@ -82,7 +82,7 @@ module settings ! The verbosity controls how much information will be printed to the screen ! and in logs - integer :: verbosity = 7 + integer(C_INT), bind(C) :: verbosity = 7 logical :: check_overlaps = .false. diff --git a/src/source_header.F90 b/src/source_header.F90 index c664316c7..a60696996 100644 --- a/src/source_header.F90 +++ b/src/source_header.F90 @@ -338,21 +338,24 @@ contains err = 0 end function openmc_extend_sources + function openmc_source_set_strength(index, strength) result(err) bind(C) integer(C_INT32_T), value, intent(in) :: index real(C_DOUBLE), value, intent(in) :: strength integer(C_INT) :: err - err = E_UNASSIGNED if (index >= 1 .and. index <= n_sources) then if (strength > ZERO) then external_source(index) % strength = strength err = 0 + else + err = E_INVALID_ARGUMENT + call set_errmsg("Source strength must be positive.") end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in external source array is out of bounds.") end if end function openmc_source_set_strength - end module source_header diff --git a/src/tallies/tally.F90 b/src/tallies/tally.F90 index bb228e892..9e40bfd6c 100644 --- a/src/tallies/tally.F90 +++ b/src/tallies/tally.F90 @@ -4410,13 +4410,15 @@ contains err = 0 if (index >= 1 .and. index <= n_tallies) then if (allocated(tallies(index) % obj)) then - err = E_ALREADY_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Tally type has already been set.") else select case (type_) case ('generic') allocate(TallyObject :: tallies(index) % obj) case default err = E_UNASSIGNED + call set_errmsg("Unknown tally type: " // trim(type_)) end select ! When a tally is allocated, set it to have 0 filters @@ -4424,6 +4426,7 @@ contains end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in tallies array is out of bounds.") end if end function openmc_tally_set_type diff --git a/src/tallies/tally_filter.F90 b/src/tallies/tally_filter.F90 index 3b96cade3..587f8dd90 100644 --- a/src/tallies/tally_filter.F90 +++ b/src/tallies/tally_filter.F90 @@ -86,10 +86,12 @@ contains err = 0 else - err = E_FILTER_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Filter type has not been set yet.") end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in filters array is out of bounds.") end if end function openmc_filter_get_type @@ -108,7 +110,8 @@ contains err = 0 if (index >= 1 .and. index <= n_filters) then if (allocated(filters(index) % obj)) then - err = E_ALREADY_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Filter type has already been set.") else select case (type_) case ('azimuthal') @@ -143,10 +146,12 @@ contains allocate(UniverseFilter :: filters(index) % obj) case default err = E_UNASSIGNED + call set_errmsg("Unknown filter type: " // trim(type_)) end select end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in filters array is out of bounds.") end if end function openmc_filter_set_type diff --git a/src/tallies/tally_filter_energy.F90 b/src/tallies/tally_filter_energy.F90 index 3530621b5..7f9655280 100644 --- a/src/tallies/tally_filter_energy.F90 +++ b/src/tallies/tally_filter_energy.F90 @@ -212,13 +212,16 @@ contains n = size(f % bins) err = 0 class default - err = E_WRONG_TYPE + err = E_INVALID_TYPE + call set_errmsg("Tried to get energy bins on a non-energy filter.") end select else - err = E_FILTER_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Filter type has not been set yet.") end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in filters array out of bounds.") end if end function openmc_energy_filter_get_bins @@ -240,13 +243,16 @@ contains allocate(f % bins(n)) f % bins(:) = energies class default - err = E_WRONG_TYPE + err = E_INVALID_TYPE + call set_errmsg("Tried to get energy bins on a non-energy filter.") end select else - err = E_FILTER_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Filter type has not been set yet.") end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in filters array out of bounds.") end if end function openmc_energy_filter_set_bins diff --git a/src/tallies/tally_filter_header.F90 b/src/tallies/tally_filter_header.F90 index 638e0e8a2..e6a6f20c3 100644 --- a/src/tallies/tally_filter_header.F90 +++ b/src/tallies/tally_filter_header.F90 @@ -7,6 +7,7 @@ module tally_filter_header use error use particle_header, only: Particle use stl_vector, only: VectorInt, VectorReal + use string, only: to_str use xml_interface, only: XMLNode use hdf5 @@ -189,6 +190,7 @@ contains err = 0 else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in filters array out of bounds.") end if end function openmc_filter_get_id @@ -206,10 +208,12 @@ contains err = 0 else - err = E_FILTER_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Filter type has not been set yet.") end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in filters array out of bounds.") end if end function openmc_filter_set_id @@ -225,10 +229,12 @@ contains index = filter_dict % get_key(id) err = 0 else - err = E_FILTER_INVALID_ID + err = E_INVALID_ID + call set_errmsg("No filter exists with ID=" // trim(to_str(id)) // ".") end if else - err = E_FILTER_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Memory has not been allocated for filters.") end if end function openmc_get_filter_index diff --git a/src/tallies/tally_filter_material.F90 b/src/tallies/tally_filter_material.F90 index 3eacc1fcb..14afdc842 100644 --- a/src/tallies/tally_filter_material.F90 +++ b/src/tallies/tally_filter_material.F90 @@ -129,13 +129,17 @@ contains n = size(f % materials) err = 0 class default - err = E_WRONG_TYPE + err = E_INVALID_TYPE + call set_errmsg("Tried to get material filter bins on a & + &non-material filter.") end select else - err = E_FILTER_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Filter type has not been set yet.") end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in filters array out of bounds.") end if end function openmc_material_filter_get_bins @@ -166,13 +170,17 @@ contains end do class default - err = E_WRONG_TYPE + err = E_INVALID_TYPE + call set_errmsg("Tried to set material filter bins on a & + &non-material filter.") end select else - err = E_FILTER_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Filter type has not been set yet.") end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in filters array out of bounds.") end if end function openmc_material_filter_set_bins diff --git a/src/tallies/tally_filter_mesh.F90 b/src/tallies/tally_filter_mesh.F90 index cfc793949..0428973c4 100644 --- a/src/tallies/tally_filter_mesh.F90 +++ b/src/tallies/tally_filter_mesh.F90 @@ -296,15 +296,19 @@ contains f % n_bins = product(meshes(index_mesh) % dimension) else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in 'meshes' array is out of bounds.") end if class default - err = E_WRONG_TYPE + err = E_INVALID_TYPE + call set_errmsg("Tried to set mesh on a non-mesh filter.") end select else - err = E_FILTER_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Filter type has not been set yet.") end if else err = E_OUT_OF_BOUNDS + call set_errmsg("Index in filters array out of bounds.") end if end function openmc_mesh_filter_set_mesh diff --git a/src/tallies/tally_header.F90 b/src/tallies/tally_header.F90 index 1ffd071f3..a823b7df5 100644 --- a/src/tallies/tally_header.F90 +++ b/src/tallies/tally_header.F90 @@ -11,7 +11,7 @@ module tally_header use nuclide_header, only: nuclide_dict use settings, only: reduce_tallies use stl_vector, only: VectorInt - use string, only: to_lower, to_f_string, str_to_int + use string, only: to_lower, to_f_string, str_to_int, to_str use tally_filter_header, only: TallyFilterContainer, filters, n_filters use tally_filter use trigger_header, only: TriggerObject @@ -301,6 +301,7 @@ contains k = filter_indices(i) if (k < 1 .or. k > n_filters) then err = E_OUT_OF_BOUNDS + call set_errmsg("Index in tally filter array out of bounds.") exit end if @@ -458,10 +459,12 @@ contains index = tally_dict % get_key(id) err = 0 else - err = E_TALLY_INVALID_ID + err = E_INVALID_ID + call set_errmsg("No tally exists with ID=" // trim(to_str(id)) // ".") end if else - err = E_TALLY_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Memory has not been allocated for tallies.") end if end function openmc_get_tally_index @@ -477,28 +480,32 @@ contains err = 0 else err = E_OUT_OF_BOUNDS + call set_errmsg('Index in tallies array is out of bounds.') end if end function openmc_tally_get_id function openmc_tally_get_filters(index, filter_indices, n) result(err) bind(C) - ! Return the list of nuclides assigned to a tally + ! Return the list of filters assigned to a tally integer(C_INT32_T), value :: index type(C_PTR), intent(out) :: filter_indices integer(C_INT), intent(out) :: n integer(C_INT) :: err - err = E_UNASSIGNED if (index >= 1 .and. index <= size(tallies)) then associate (t => tallies(index) % obj) if (allocated(t % filter)) then filter_indices = C_LOC(t % filter(1)) n = size(t % filter) err = 0 + else + err = E_ALLOCATE + call set_errmsg("Tally filters have not been allocated yet.") end if end associate else err = E_OUT_OF_BOUNDS + call set_errmsg('Index in tallies array is out of bounds.') end if end function openmc_tally_get_filters @@ -510,17 +517,20 @@ contains integer(C_INT), intent(out) :: n integer(C_INT) :: err - err = E_UNASSIGNED if (index >= 1 .and. index <= size(tallies)) then associate (t => tallies(index) % obj) if (allocated(t % nuclide_bins)) then nuclides = C_LOC(t % nuclide_bins(1)) n = size(t % nuclide_bins) err = 0 + else + err = E_ALLOCATE + call set_errmsg("Tally nuclides have not been allocated yet.") end if end associate else err = E_OUT_OF_BOUNDS + call set_errmsg('Index in tallies array is out of bounds.') end if end function openmc_tally_get_nuclides @@ -533,17 +543,20 @@ contains integer(C_INT), intent(out) :: shape_(3) integer(C_INT) :: err - err = E_UNASSIGNED if (index >= 1 .and. index <= size(tallies)) then associate (t => tallies(index) % obj) if (allocated(t % results)) then ptr = C_LOC(t % results(1,1,1)) shape_(:) = shape(t % results) err = 0 + else + err = E_ALLOCATE + call set_errmsg("Tally results have not been allocated yet.") end if end associate else err = E_OUT_OF_BOUNDS + call set_errmsg('Index in tallies array is out of bounds.') end if end function openmc_tally_results @@ -560,10 +573,12 @@ contains if (allocated(tallies(index) % obj)) then err = tallies(index) % obj % set_filters(filter_indices) else - err = E_TALLY_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Tally type has not been set yet.") end if else err = E_OUT_OF_BOUNDS + call set_errmsg('Index in tallies array is out of bounds.') end if end function openmc_tally_set_filters @@ -581,10 +596,12 @@ contains err = 0 else - err = E_FILTER_NOT_ALLOCATED + err = E_ALLOCATE + call set_errmsg("Tally type has not been set yet.") end if else err = E_OUT_OF_BOUNDS + call set_errmsg('Index in tallies array is out of bounds.') end if end function openmc_tally_set_id @@ -619,7 +636,9 @@ contains if (nuclide_dict % has_key(nuclide_)) then t % nuclide_bins(i) = nuclide_dict % get_key(nuclide_) else - err = E_NUCLIDE_NOT_LOADED + err = E_DATA + call set_errmsg("Nuclide '" // trim(to_f_string(string)) // & + "' has not been loaded yet.") return end if end select @@ -629,6 +648,7 @@ contains end associate else err = E_OUT_OF_BOUNDS + call set_errmsg('Index in tallies array is out of bounds.') end if end function openmc_tally_set_nuclides @@ -778,11 +798,13 @@ contains if (MT > 1) then t % score_bins(i) = MT else - err = E_ARGUMENT_INVALID + err = E_INVALID_ARGUMENT + call set_errmsg("Negative MT number cannot be used as a score.") end if else - err = E_ARGUMENT_INVALID + err = E_INVALID_ARGUMENT + call set_errmsg("Unknown score: " // trim(score_) // ".") end if end select @@ -792,6 +814,7 @@ contains end associate else err = E_OUT_OF_BOUNDS + call set_errmsg('Index in tallies array is out of bounds.') end if end function openmc_tally_set_scores