CFD Online Discussion Forums

CFD Online Discussion Forums (https://www.cfd-online.com/Forums/)
-   FLUENT (https://www.cfd-online.com/Forums/fluent/)
-   -   Problem with interpreted UDF with UDM calculation (https://www.cfd-online.com/Forums/fluent/203683-problem-interpreted-udf-udm-calculation.html)

Kabador July 4, 2018 04:25

Problem with interpreted UDF with UDM calculation
 
EDIT: i sucessfully compiled all my UDF. I had to do some work on my envrionment paths...
But still the same problem, it crashes on initialization with the UDF defining the pressure inlet with mass as criterium
Hello everybody!

I am Modelling a Vacuum assisted resin transfer moulding (VRTM) of a porous medium.
My Simulation works fine, 5 UDF (viscosity, timestep, porosity) are running in interpreted mode. (cant run compiled, get the libudf error constantly)
But i simply cant write a UDF that computes the mass in the volume, saves it as a UDM so i can then use it for a pressure inlet UDF.

Here are the 2 UDF's i have written for the mass:

DEFINE_PROFILE(pressure_profile, t, i)
{
real x[ND_ND]; /* this will hold the position vector */
real y;
real mass;
face_t f;
real time = CURRENT_TIME;
Domain *domain;
Thread *ct;
cell_t c;
domain = Get_Domain(1);
begin_f_loop(f, t)
{
F_CENTROID(x, f, t);
y = x[1];
if (C_UDMI(c, t, 0) < 0.5)
F_PROFILE(f, t, i) = 101325;
else
F_PROFILE(f, t, i) = 350;
}
end_f_loop(f, t)

}

DEFINE_ADJUST(mass, domain)
{
real mass;
Thread *t;
cell_t c;
Domain *domain;
domain = Get_Domain(1);
begin_c_loop(c, t)
{
mass += C_R(c, t) * C_VOLUME(c, t);
}
end_c_loop(c, t)
C_UDMI(c, t, 0) = mass;
}

This UDF does work and runs in FLUENT, but it seems it does not save the correct value of mass, as the pressure does not go down after 0,5 kg aquired.

I thank all of you beforehand and hope u can help me with this problem.

`e` July 4, 2018 18:59

First, the DEFINE_ADJUST macro is called after the DEFINE_PROFILE macro. Second, the user-defined memory (UDM) are defined for each cell and modified with C_UDMI(c,t,i) where c is the cell in thread t and i represents the UDM index. Did you want the mass of the complete cell zone, or of the neighbouring (local) mass? For the former, you could use a loop within the DEFINE_PROFILE macro (take care with parallel processing with multiple partitions in the same cell thread), and for the latter you could use the neighbouring cell macro F_C0(f,t) within the face loop.

Kabador July 6, 2018 15:12

Thanks for the answer! Sorry i am a noob in programming.
Yes i want to:
1. compute the mass in the whole cell zone,
2. then check if it aquired enough mass
3. then edit the pressure so the flow stops

But i cant get it to run.
DEFINE_PROFILE(pressure_profile, t, i)
{

face_t f;
cell_t c;
real mass;

begin_c_loop(c, t)
{
mass += C_R(c, t) * C_VOLUME(c, t);
}
end_c_loop(c, t)

begin_f_loop(f, t)
{
if (mass < 0.5)
F_PROFILE(f, t, i) = 101325;
else
F_PROFILE(f, t, i) = 350;
}
end_f_loop(f, t)
}

`e` July 6, 2018 19:21

You're on the right track. A couple of things, the variable mass should be initialised with zero (otherwise the value is whatever was already in memory; garbage).

Code:

real mass = 0.0;
Second, the face loop is correctly running through each face on the thread t given by the DEFINE_PROFILE macro (which would correspond to your boundary), but the cell loop is also using this same thread whereas you want to loop over the interior cells of your domain. You would need to retrieve the thread for the cell zone instead (using an integer which is shown in the cell zones list).

Code:

...
Domain *domain = Get_Domain(1); /* domain pointer; the domain ID is one unless there are multiple phases */
int id_interior_cell_zone = 1; /* the ID shown in the cell zone list */
Thread *t_interior_cell_zone = Lookup_Thread(domain, id_interior_cell_zone);
...

begin_c_loop(c,t_interior_cell_zone)
{
        ...
}
end_c_loop(c,t_interior_cell_zone)

...



Note: if you are running with parallel processors, i.e. the domain is partitioned, then you would need to employ the relevant macros for communicating between processors to find the overall mass in the domain rather than the mass for each processor. See the chapter on "Parallel Considerations" in the UDF manual for reference.

Kabador July 8, 2018 03:36

Thanks for your help again!
With your suggestions and another forum post on parallelisation i made it work.

Here is the Code for other people who might have the same problems:

DEFINE_EXECUTE_AT_END(calcm)
{

#if !RP_HOST
cell_t c;
Domain *domain = Get_Domain(1);
int id_interior_cell_zone = 3;
Thread *t_interior_cell_zone = Lookup_Thread(domain, id_interior_cell_zone);

begin_c_loop(c, t_interior_cell_zone)
{
mass += C_R(c, t_interior_cell_zone) * C_VOLUME(c, t_interior_cell_zone);
}
end_c_loop(c, t_interior_cell_zone)

mass = PRF_GRSUM1(mass);

#endif //Host

printf("Masse: %g\n", mass); //prints the mass in each node on console
fflush(stdout);
}

DEFINE_PROFILE(pressure_profile, t, i)
{
face_t f;
cell_t c;

begin_f_loop(f, t)
{
if (mass < 0.8)
F_PROFILE(f, t, i) = 101325;
else
F_PROFILE(f, t, i) = 350;
}
end_f_loop(f, t)
}


All times are GMT -4. The time now is 20:50.