stardis-solver

Solve coupled heat transfers
git clone git://git.meso-star.fr/stardis-solver.git
Log | Files | Refs | README | LICENSE

commit 0afe189976e87820a4fb025e062d5ec44d73cd40
parent 283f5c19e00c813cffee60dc4940ad5684ca3474
Author: Christophe Coustet <christophe.coustet@meso-star.com>
Date:   Thu, 13 Dec 2018 17:36:50 +0100

Allow to define a t0 value by medium

t0 is the time until the initial condition is maintained for this medium

Diffstat:
Msrc/sdis.h | 20++++++++++++++------
Msrc/sdis_medium.c | 6++++--
Msrc/sdis_medium_c.h | 22++++++++++++++++++++++
Msrc/sdis_solve_Xd.h | 114++++++++++++++++++++++++++++++++++++++++++++++++-------------------------------
Msrc/test_sdis_medium.c | 14++++++++++++++
Msrc/test_sdis_utils.h | 6++++--
6 files changed, 128 insertions(+), 54 deletions(-)

diff --git a/src/sdis.h b/src/sdis.h @@ -151,11 +151,15 @@ struct sdis_solid_shader { * submitted position and time */ sdis_medium_getter_T volumic_power; /* In W.m^-3 */ - /* Initial condition. A temperature < 0 means that the temperature is - * unknown for the submitted random walk vertex. */ + /* Initial/limit condition. A temperature < 0 means that the temperature is + * unknown for the submitted random walk vertex. + * This getter is always called at time >= t0 (see below). */ sdis_medium_getter_T temperature; + /* The time until the initial condition is maintained for this solid; + * can neither be negative nor infinity, default is 0. */ + double t0; }; -#define SDIS_SOLID_SHADER_NULL__ {NULL, NULL, NULL, NULL, NULL, NULL} +#define SDIS_SOLID_SHADER_NULL__ {NULL, NULL, NULL, NULL, NULL, NULL, 0} static const struct sdis_solid_shader SDIS_SOLID_SHADER_NULL = SDIS_SOLID_SHADER_NULL__; @@ -165,11 +169,15 @@ struct sdis_fluid_shader { sdis_medium_getter_T calorific_capacity; /* In J.K^-1.kg^-1 */ sdis_medium_getter_T volumic_mass; /* In kg.m^-3 */ - /* Initial condition. A temperature < 0 means that the temperature is - * unknown for the submitted position and time. */ + /* Initial/limit condition. A temperature < 0 means that the temperature is + * unknown for the submitted random walk vertex. + * This getter is always called at time >= t0 (see below). */ sdis_medium_getter_T temperature; + /* The time until the initial condition is maintained for this fluid; + * can neither be negative nor infinity, default is 0. */ + double t0; }; -#define SDIS_FLUID_SHADER_NULL__ {NULL, NULL, NULL} +#define SDIS_FLUID_SHADER_NULL__ {NULL, NULL, NULL, 0} static const struct sdis_fluid_shader SDIS_FLUID_SHADER_NULL = SDIS_FLUID_SHADER_NULL__; diff --git a/src/sdis_medium.c b/src/sdis_medium.c @@ -28,7 +28,8 @@ check_fluid_shader(const struct sdis_fluid_shader* shader) ASSERT(shader); return shader->calorific_capacity && shader->volumic_mass - && shader->temperature; + && shader->temperature + && 0 <= shader->t0 && shader->t0 < INF; } static int @@ -39,7 +40,8 @@ check_solid_shader(const struct sdis_solid_shader* shader) && shader->thermal_conductivity && shader->volumic_mass && shader->delta_solid - && shader->temperature; + && shader->temperature + && 0 <= shader->t0 && shader->t0 < INF; } static res_T diff --git a/src/sdis_medium_c.h b/src/sdis_medium_c.h @@ -18,6 +18,8 @@ #include "sdis.h" +#include <rsys/math.h> + struct sdis_medium { enum sdis_medium_type type; union { @@ -63,9 +65,19 @@ fluid_get_temperature (const struct sdis_medium* mdm, const struct sdis_rwalk_vertex* vtx) { ASSERT(mdm && mdm->type == SDIS_FLUID); + ASSERT(vtx->time >= mdm->shader.fluid.t0); return mdm->shader.fluid.temperature(vtx, mdm->data); } +static INLINE double + fluid_get_t0 +(const struct sdis_medium* mdm) +{ + ASSERT(mdm && mdm->type == SDIS_FLUID); + ASSERT(0 <= mdm->shader.fluid.t0 && mdm->shader.fluid.t0 < INF); + return mdm->shader.fluid.t0; +} + /******************************************************************************* * Solid local functions ******************************************************************************/ @@ -116,8 +128,18 @@ solid_get_temperature (const struct sdis_medium* mdm, const struct sdis_rwalk_vertex* vtx) { ASSERT(mdm && mdm->type == SDIS_SOLID); + ASSERT(vtx->time >= mdm->shader.solid.t0); return mdm->shader.solid.temperature(vtx, mdm->data); } +static INLINE double + solid_get_t0 +(const struct sdis_medium* mdm) +{ + ASSERT(mdm && mdm->type == SDIS_SOLID); + ASSERT(0 <= mdm->shader.solid.t0 && mdm->shader.solid.t0 < INF); + return mdm->shader.solid.t0; +} + #endif /* SDIS_MEDIUM_C_H */ diff --git a/src/sdis_solve_Xd.h b/src/sdis_solve_Xd.h @@ -606,12 +606,12 @@ XD(fluid_temperature) return RES_BAD_ARG; } - /* The hc upper bound can be 0 is h is uniformly 0. In that case the result + /* The hc upper bound can be 0 if h is uniformly 0. In that case the result * is the initial condition. */ if(enc->hc_upper_bound == 0) { /* Cannot be in the fluid without starting there. */ ASSERT(SXD_HIT_NONE(&rwalk->hit)); - rwalk->vtx.time = 0; + rwalk->vtx.time = fluid_get_t0(rwalk->mdm); tmp = fluid_get_temperature(rwalk->mdm, &rwalk->vtx); if(tmp >= 0) { T->value += tmp; @@ -621,8 +621,8 @@ XD(fluid_temperature) /* At t=0, the initial condition should have been reached. */ log_err(scn->dev, -"%s: undefined initial condition. " -"Time is 0 but the temperature remains unknown.\n", + "%s: undefined initial condition. " + "Time is 0 but the temperature remains unknown.\n", FUNC_NAME); return RES_BAD_OP; } @@ -655,27 +655,26 @@ XD(fluid_temperature) /* Sample the time using the upper bound. */ if(rwalk->vtx.time != INF) { - double mu, tau; + double mu, tau, t0; mu = enc->hc_upper_bound / (rho * cp) * enc->S_over_V; tau = ssp_ran_exp(rng, mu); - rwalk->vtx.time = MMAX(rwalk->vtx.time - tau, 0); - } - - /* Check the initial condition. */ - tmp = fluid_get_temperature(rwalk->mdm, &rwalk->vtx); - if(tmp >= 0) { - T->value += tmp; - T->done = 1; - return RES_OK; - } - - if(rwalk->vtx.time <= 0) { - /* The initial condition should have been reached. */ - log_err(scn->dev, -"%s: undefined initial condition. " -"Time is 0 but the temperature remains unknown.\n", - FUNC_NAME); - return RES_BAD_OP; + t0 = fluid_get_t0(rwalk->mdm); + rwalk->vtx.time = MMAX(rwalk->vtx.time - tau, t0); + if(rwalk->vtx.time == t0) { + /* Check the initial condition. */ + tmp = fluid_get_temperature(rwalk->mdm, &rwalk->vtx); + if(tmp >= 0) { + T->value += tmp; + T->done = 1; + return RES_OK; + } + /* The initial condition should have been reached. */ + log_err(scn->dev, + "%s: undefined initial condition. " + "Time is %g but the temperature remains unknown.\n", + FUNC_NAME, t0); + return RES_BAD_OP; + } } /* Uniformly sample the enclosure. */ @@ -1330,27 +1329,26 @@ XD(solid_temperature) /* Sample the time */ if(rwalk->vtx.time != INF) { - double tau, mu; + double tau, mu, t0; mu = (2*DIM*lambda) / (rho*cp*delta*fp_to_meter*delta*fp_to_meter); tau = ssp_ran_exp(rng, mu); - rwalk->vtx.time = MMAX(rwalk->vtx.time - tau, 0); - } - - /* Check the initial condition */ - tmp = solid_get_temperature(mdm, &rwalk->vtx); - if(tmp >= 0) { - T->value += tmp; - T->done = 1; - return RES_OK; - } - - if(rwalk->vtx.time <= 0) { - /* The initial condition should have been reached */ - log_err(scn->dev, - "%s: undefined initial condition. " - "The time is null but the temperature remains unknown.\n", - FUNC_NAME); - return RES_BAD_OP; + t0 = solid_get_t0(rwalk->mdm); + rwalk->vtx.time = MMAX(rwalk->vtx.time - tau, t0); + if(rwalk->vtx.time == t0) { + /* Check the initial condition */ + tmp = solid_get_temperature(mdm, &rwalk->vtx); + if(tmp >= 0) { + T->value += tmp; + T->done = 1; + return RES_OK; + } + /* The initial condition should have been reached */ + log_err(scn->dev, + "%s: undefined initial condition. " + "The time is %f but the temperature remains unknown.\n", + FUNC_NAME, t0); + return RES_BAD_OP; + } } /* Define if the random walk hits something along dir0 */ @@ -1483,18 +1481,46 @@ XD(probe_realisation) struct rwalk_context ctx; struct XD(rwalk) rwalk = XD(RWALK_NULL); struct XD(temperature) T = XD(TEMPERATURE_NULL); + double (*get_initial_temperature) + (const struct sdis_medium* mdm, const struct sdis_rwalk_vertex* vtx); + double t0; res_T res = RES_OK; ASSERT(medium && position && fp_to_meter > 0 && weight); switch(medium->type) { - case SDIS_FLUID: T.func = XD(fluid_temperature); break; - case SDIS_SOLID: T.func = XD(solid_temperature); break; + case SDIS_FLUID: + T.func = XD(fluid_temperature); + get_initial_temperature = fluid_get_temperature; + t0 = fluid_get_t0(medium); + break; + case SDIS_SOLID: + T.func = XD(solid_temperature); + get_initial_temperature = solid_get_temperature; + t0 = solid_get_t0(medium); + break; default: FATAL("Unreachable code\n"); break; } dX(set)(rwalk.vtx.P, position); /* Sample a time */ rwalk.vtx.time = sample_time(time_range, rng); + if(t0 >= rwalk.vtx.time) { + double tmp; + /* Check the initial condition. */ + rwalk.vtx.time = t0; + tmp = get_initial_temperature(medium, &rwalk.vtx); + if(tmp >= 0) { + *weight = tmp; + return RES_OK; + } + /* The initial condition should have been reached */ + log_err(scn->dev, + "%s: undefined initial condition. " + "The time is %f but the temperature remains unknown.\n", + FUNC_NAME, t0); + return RES_BAD_OP; + } + rwalk.hit = SXD_HIT_NULL; rwalk.mdm = medium; diff --git a/src/test_sdis_medium.c b/src/test_sdis_medium.c @@ -16,6 +16,8 @@ #include "sdis.h" #include "test_sdis_utils.h" +#include <rsys/math.h> + int main(int argc, char** argv) { @@ -61,6 +63,12 @@ main(int argc, char** argv) BA(sdis_fluid_create(dev, &fluid_shader, NULL, &fluid)); fluid_shader.temperature = DUMMY_FLUID_SHADER.temperature; + fluid_shader.t0 = -1; + BA(sdis_fluid_create(dev, &fluid_shader, NULL, &solid)); + fluid_shader.t0 = INF; + BA(sdis_fluid_create(dev, &fluid_shader, NULL, &solid)); + fluid_shader.t0 = DUMMY_FLUID_SHADER.t0; + BA(sdis_fluid_create(dev, &SDIS_FLUID_SHADER_NULL, NULL, &fluid)); OK(sdis_data_create(dev, 4, 16, NULL, &data)); @@ -97,6 +105,12 @@ main(int argc, char** argv) BA(sdis_solid_create(dev, &solid_shader, NULL, &solid)); solid_shader.temperature = DUMMY_SOLID_SHADER.temperature; + solid_shader.t0 = -1; + BA(sdis_solid_create(dev, &solid_shader, NULL, &solid)); + solid_shader.t0 = INF; + BA(sdis_solid_create(dev, &solid_shader, NULL, &solid)); + solid_shader.t0 = DUMMY_SOLID_SHADER.t0; + OK(sdis_device_ref_put(dev)); check_memory_allocator(&allocator); diff --git a/src/test_sdis_utils.h b/src/test_sdis_utils.h @@ -168,13 +168,15 @@ static const struct sdis_solid_shader DUMMY_SOLID_SHADER = { dummy_medium_getter, dummy_medium_getter, dummy_medium_getter, - dummy_medium_getter + dummy_medium_getter, + 0 }; static const struct sdis_fluid_shader DUMMY_FLUID_SHADER = { dummy_medium_getter, dummy_medium_getter, - dummy_medium_getter + dummy_medium_getter, + 0 };