Repository navigation
Expand file tree
/
Copy pathchain.cpp
More file actions
131 lines (104 loc) · 3.7 KB
/
Copy pathchain.cpp
File metadata and controls
131 lines (104 loc) · 3.7 KB
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
33
34
35
36
37
38
39
40
41
42
43
44
45
46
47
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
131
//! \file chain.cpp
//! \brief Depletion chain and associated information
#include "openmc/chain.h"
#include <cstdlib> // for getenv
#include <memory> // for make_unique
#include <string> // for stod
#include <fmt/core.h>
#include <pugixml.hpp>
#include "openmc/distribution.h" // for distribution_from_xml
#include "openmc/error.h"
#include "openmc/reaction.h"
#include "openmc/xml_interface.h" // for get_node_value
namespace openmc {
//==============================================================================
// ChainNuclide implementation
//==============================================================================
ChainNuclide::ChainNuclide(pugi::xml_node node)
{
name_ = get_node_value(node, "name");
if (check_for_node(node, "half_life")) {
half_life_ = std::stod(get_node_value(node, "half_life"));
}
if (check_for_node(node, "decay_energy")) {
decay_energy_ = std::stod(get_node_value(node, "decay_energy"));
}
// Read reactions to store MT -> product map
for (pugi::xml_node reaction_node : node.children("reaction")) {
std::string rx_name = get_node_value(reaction_node, "type");
if (!reaction_node.attribute("target"))
continue;
std::string rx_target = get_node_value(reaction_node, "target");
double branching_ratio = 1.0;
if (reaction_node.attribute("branching_ratio")) {
branching_ratio =
std::stod(get_node_value(reaction_node, "branching_ratio"));
}
int mt = reaction_mt(rx_name);
reaction_products_[mt].push_back({rx_target, branching_ratio});
}
for (pugi::xml_node source_node : node.children("source")) {
auto particle = get_node_value(source_node, "particle");
if (particle == "photon") {
photon_energy_ = distribution_from_xml(source_node);
break;
}
}
// Set entry in mapping
data::chain_nuclide_map[name_] = data::chain_nuclides.size();
}
ChainNuclide::~ChainNuclide()
{
data::chain_nuclide_map.erase(name_);
}
//==============================================================================
// DecayPhotonAngleEnergy implementation
//==============================================================================
void DecayPhotonAngleEnergy::sample(
double E_in, double& E_out, double& mu, uint64_t* seed) const
{
E_out = photon_energy_->sample(seed).first;
mu = Uniform(-1., 1.).sample(seed).first;
}
double DecayPhotonAngleEnergy::sample_energy_and_pdf(
double E_in, double mu, double& E_out, uint64_t* seed) const
{
E_out = photon_energy_->sample(seed).first;
return 0.5;
}
//==============================================================================
// Global variables
//==============================================================================
namespace data {
std::unordered_map<std::string, int> chain_nuclide_map;
vector<unique_ptr<ChainNuclide>> chain_nuclides;
} // namespace data
//==============================================================================
// Non-member functions
//==============================================================================
void read_chain_file_xml()
{
free_memory_chain();
char* chain_file_path = std::getenv("OPENMC_CHAIN_FILE");
if (!chain_file_path) {
return;
}
write_message(5, "Reading chain file: {}...", chain_file_path);
pugi::xml_document doc;
auto result = doc.load_file(chain_file_path);
if (!result) {
fatal_error(
fmt::format("Error processing chain file: {}", chain_file_path));
}
// Get root element
pugi::xml_node root = doc.document_element();
for (auto node : root.children("nuclide")) {
data::chain_nuclides.push_back(std::make_unique<ChainNuclide>(node));
}
}
void free_memory_chain()
{
data::chain_nuclides.clear();
data::chain_nuclide_map.clear();
}
} // namespace openmc