1#ifndef VIENNASHE_SRH_KINETICS_HPP
2#define VIENNASHE_SRH_KINETICS_HPP
36 template <
typename DeviceType,
typename TimeStepQuantitiesT >
38 typename DeviceType::cell_type
const & cell,
39 TimeStepQuantitiesT
const & quantities,
44 return quantities.electron_density().at(cell);
46 return quantities.hole_density().at(cell);
49 template <
typename DeviceType,
typename TimeStepQuantitiesT >
51 typename DeviceType::facet_type
const & facet,
52 TimeStepQuantitiesT
const & quantities,
55 typedef typename DeviceType::mesh_type mesh_type;
56 typedef typename DeviceType::facet_type facet_type;
57 typedef typename DeviceType::cell_type cell_type;
58 typedef typename viennagrid::result_of::const_coboundary_range<mesh_type, facet_type, cell_type>::type CellOnFacetContainer;
64 return quantities.electron_density().at(cells_on_facet[1]);
66 return quantities.electron_density().at(cells_on_facet[0]);
68 return std::sqrt(quantities.electron_density().at(cells_on_facet[0]) * quantities.electron_density().at(cells_on_facet[1]));
73 return quantities.hole_density().at(cells_on_facet[1]);
75 return quantities.hole_density().at(cells_on_facet[0]);
77 return std::sqrt(quantities.hole_density().at(cells_on_facet[0]) * quantities.hole_density().at(cells_on_facet[1]));
92 template <
typename DeviceType,
typename ElementType,
typename TimeStepQuantitiesT >
95 ElementType
const & el,
97 TimeStepQuantitiesT
const & quantities,
99 std::size_t index_H = 0)
107 for (std::size_t i = 0; i < quantities.unknown_she_quantities().size(); ++i)
113 const double kinetic_energy = quantities.unknown_she_quantities()[i].get_kinetic_energy(el, index_H);
123 const double sigma_n = vth * collision_cs;
132 for (std::size_t i = 0; i < quantities.unknown_she_quantities().size(); ++i)
138 const double kinetic_energy = quantities.unknown_she_quantities()[i].get_kinetic_energy(el, index_H);
149 const double sigma_p = vth * collision_cs;
171 template <
typename DeviceType,
typename ElementType,
typename TimeStepQuantitiesT >
173 DeviceType
const &
device,
174 ElementType
const & el,
176 TimeStepQuantitiesT
const & quantities,
178 std::size_t index_H = 0)
188 for (std::size_t i = 0; i < quantities.unknown_she_quantities().size(); ++i)
195 const double kinetic_energy = quantities.unknown_she_quantities()[i].get_kinetic_energy(el, index_H);
197 const double total_energy = quantities.unknown_she_quantities()[i].get_value_H(index_H);
198 double gamma_generation = collision_cs * velocity * std::exp( (total_trap_energy - total_energy) / kBT );
207 const double sigma_n = vth * collision_cs;
210 return sigma_n * n_aux * std::exp( + trap.
energy() / kBT);
217 for (std::size_t i = 0; i < quantities.unknown_she_quantities().size(); ++i)
224 const double kinetic_energy = quantities.unknown_she_quantities()[i].get_kinetic_energy(el, index_H);
226 const double total_energy = quantities.unknown_she_quantities()[i].get_value_H(index_H);
227 double gamma_generation = collision_cs * velocity * std::exp( (total_energy - total_trap_energy) / kBT ) ;
236 const double sigma_p = vth * collision_cs;
239 return sigma_p * p_aux * std::exp( - trap.
energy() / kBT);
258 template <
typename DeviceType,
typename ElementType,
typename TimeStepQuantitiesT >
260 DeviceType
const &
device,
261 ElementType
const & el,
263 TimeStepQuantitiesT
const & quantities)
275 if (with_full_newton)
281 double electron_rec_rate = 0;
282 double electron_gen_rate = 0;
284 double hole_rec_rate = 0;
285 double hole_gen_rate = 0;
287 const double box_volume = viennagrid::volume(el);
294 for (std::size_t i = 0; i < quantities.unknown_she_quantities().size(); ++i)
296 for (std::size_t index_H = 1; index_H < quantities.unknown_she_quantities()[i].get_value_H_size()-1; ++index_H)
298 const long f00_index = quantities.unknown_she_quantities()[i].get_unknown_index(el, index_H);
304 const double kinetic_energy = quantities.unknown_she_quantities()[i].get_kinetic_energy(el, index_H);
306 const double f00 = quantities.unknown_she_quantities()[i].get_values(el, index_H)[0];
308 if (assemble_electrons)
313 electron_rec_rate += box_volume * energy_spacing *
gamma_recombination * f00 * dispersion_n.density_of_states(kinetic_energy);
314 electron_gen_rate += box_volume * energy_spacing *
gamma_generation * f00 * dispersion_n.density_of_states(kinetic_energy);
321 hole_rec_rate += box_volume * energy_spacing *
gamma_recombination * f00 * dispersion_p.density_of_states(kinetic_energy);
322 hole_gen_rate += box_volume * energy_spacing *
gamma_generation * f00 * dispersion_p.density_of_states(kinetic_energy);
329 double denominator = electron_rec_rate + electron_gen_rate + hole_rec_rate + hole_gen_rate;
331 ft = (electron_rec_rate + hole_gen_rate) / denominator;
334 if (ft > 1.0 && ft < 1.001) ft = 1.0;
335 if (ft < 0 && ft > -0.001) ft = 0.0;
355 template <
typename DeviceType,
typename ElementType,
typename TimeStepQuantitiesT >
357 TimeStepQuantitiesT
const & quantities,
360 std::size_t index_H = 0)
380 template <
typename DeviceType,
typename ElementType,
typename TimeStepQuantitiesT >
382 TimeStepQuantitiesT
const & quantities,
385 std::size_t index_H = 0)
Common routines for the assembly of SHE equations.
The main SHE configuration class. To be adjusted by the user for his/her needs.
viennashe::physics::dispersion_proxy dispersion_relation(viennashe::carrier_type_id ctype) const
Returns the dispersion relation for electrons.
equation_id get_electron_equation() const
bool with_holes() const
Returns true if holes are considered in the simulation.
equation_id get_hole_equation() const
nonlinear_solver_config_type & nonlinear_solver()
Returns the configuration object for the nonlinear solver.
bool with_electrons() const
Returns true if electrons are considered in the simulation.
double get_lattice_temperature(cell_type const &c) const
Returns the lattice temperature on a cell.
long get_material(cell_type const &elem) const
Returns the material id of the provided cell.
MeshT const & mesh() const
Returns the underlying mesh.
Defines the physical properties of a device, e.g. doping. This is the implementation for 2d and highe...
A proxy object for a dispersion relation. Does NOT take ownership of the provided pointer!
double velocity(double ekin, double theta=0, double phi=0) const
Returns the velocity as a function of kinetic energy (and angles, eventually)
Exception in case a (requested) quantity cannot be found.
long id() const
Returns the current linear solver ID.
void energy(double e)
Returns the trap energy in Joule (zero energy refers to the center of the band gap.
void collision_cross_section(double ccs)
Sets the collision cross section (SI units)
Exception for the case that a requested feature is not available (due to configuration or due to not ...
Contains forward declarations and definition of small classes that must be defined at an early stage.
A logging facility providing fine-grained control over logging in ViennaSHE.
bool is_semiconductor(long material_id)
Convenience function for checking whether the supplied material ID refers to a semiconductor.
double get_carrier_concentration(DeviceType const &device, typename DeviceType::cell_type const &cell, TimeStepQuantitiesT const &quantities, viennashe::carrier_type_id ctype)
double gamma_recombination_impl(viennashe::trap_level const &trap, DeviceType const &device, ElementType const &el, viennashe::config const &conf, TimeStepQuantitiesT const &quantities, viennashe::carrier_type_id ctype, std::size_t index_H=0)
Implementation of the recombination term without any occupancies considered.
double gamma_generation_impl(viennashe::trap_level const &trap, DeviceType const &device, ElementType const &el, viennashe::config const &conf, TimeStepQuantitiesT const &quantities, viennashe::carrier_type_id ctype, std::size_t index_H=0)
Implementation of the generation term without any occupancies considered.
double gamma_generation(viennashe::trap_level const &trap, DeviceType const &device, ElementType const &el, viennashe::config const &conf, TimeStepQuantitiesT const &quantities, viennashe::carrier_type_id ctype, double occupancy, std::size_t index_H=0)
Returns the carrier generation, where the occupancies have been considered!
double evaluate(viennashe::trap_level const &trap, DeviceType const &device, ElementType const &el, viennashe::config const &conf, TimeStepQuantitiesT const &quantities)
Returns the trap occupancy based on a bipolar SHE or DD solution.
double gamma_recombination(viennashe::trap_level const &trap, DeviceType const &device, ElementType const &el, viennashe::config const &conf, TimeStepQuantitiesT const &quantities, viennashe::carrier_type_id ctype, double occupancy, std::size_t index_H=0)
Returns the carrier recombination, where the occupancies have been considered!
double get_thermal_velocity(double temperature, viennashe::carrier_type_id ctype)
Returns the thermal velocity at the given lattice temperature for a given carrier type.
double get_band_edge(viennashe::carrier_type_id const &ctype)
Returns the band edge relative to the reference energy (mid-gap)
double get_auxilary_concentration(double temperature, viennashe::carrier_type_id ctype)
Returns the auxilary carrier concentration.
std::string electron_distribution_function()
std::string hole_distribution_function()
double box_height(SHEQuantity const &quan, ElementType const &elem, std::size_t index_H)
Returns the height of the control box with respect to energy at the provided element (vertex or edge)...
The main ViennaSHE namespace. All functionality resides inside this namespace.
carrier_type_id
Enumeration type for selecting the carrier type.
static const double kB
Boltzmann constant.
@ newton_nonlinear_solver
Gummel iteration.
Contains the definition of a trap level.