-
Notifications
You must be signed in to change notification settings - Fork 1.1k
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
fixes issue where external variables are not properly initialized #29520
base: next
Are you sure you want to change the base?
Conversation
for (const auto elem_ptr : mesh.element_ptr_range()) | ||
{ | ||
auto dof_idx = elem_ptr->dof_number(sys_number, _heat_source_var, 0); | ||
solution.set(dof_idx, 12345); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I would use the ExternalProblem directly rather than those test objects to test the fix
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I'm not sure this is the fix I had in mind -- we don't necessarily have an initial value to put into this external variable until we run our OpenMC simulation. The problem is that even after we run OpenMC, the user objects are lagged by one time step (with the current MOOSE, not including any changes in this PR). This fix seems to be just manually adding an insertion point to initialize the variable (which for us would mean an extra OpenMC run -- as opposed to MOOSE just realizing we already ran OpenMC and properly keeping things up to date).
Is my understanding correct?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I believe you're correct. When I looked at the two input files you included it looked like for the external case heat_source was never initialized and so it defaulted to 0. Then in the first iteration layered_integral was calculated before heat_source was ever assigned a value which is why it was off for that first timestep. That's why I assumed it was an issue with initialization.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So I did some more digging and I think I may have changed the execute_on parameter during some of my debugging but forgot to change it back. So I went back and ran the two original input files you included and when both the aux kernel and user object are set to execute on timestep_end I'm getting the same results for both. The only difference being that for the external user object heat_source is 0 for t = 0 unless I initialize heat_source. I'm wondering if this issue may have been resolved in a different PR and adding an option to initialize and external variable was the only thing left to fix? I was going to try and do some testing with a time dependent problem and see if it still works.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
@aprilnovak So I ran similar problems that were time-dependent and both the external and non-external user object versions gave the same results. The only difference was that for the external user object, heat_source is initialized to 0. I think this issue may have been resolved earlier. Unfortunately I'm not sure which PR may have fixed it. For reference here are the two examples I ran. For the external one I modified the SyncSolutions function in BasicExternalProblem.C so that it set heat_source to 12345*time(). If you run into any similar issues let me know and I'll take another look!
time-depenent example.zip
_problem->init(); | ||
else | ||
mooseError("Problem doesn't exist in InitProblemAction!"); | ||
|
||
// check for external variable to initialize | ||
auto external_problem_ptr = std::dynamic_pointer_cast<ExternalProblem>(_problem); | ||
if (external_problem_ptr) | ||
external_problem_ptr->initializeVariable(); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
any chance you can move that call to initializeVariable inside the ExternalProblem init() ?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
then you wont need to define these new functions to the two test objects
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
So the issue I would run into there is that the FEProblemBase object _problem has not been initialized yet. Do you know if there is another way I can get a pointer to the external problem object at that point?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I think it's inited you can see it right above
_problem->init();
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yes, but you wanted it moved into ExternalProblem.C right?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
I guess I should clarify, it can be overridden in a derived class but the parent constructor is not going to call the overridden version.
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
the _problem->init call is not the constructor
you just need to redefine ExternalProblem::init to include the logic you want to add here
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
You can call down to the base FEProblemBase::init
from within your derived ExternalProblem::init
override
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
but sounds like we're not going to end up going down this path anyways
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
That's what I ended up doing. I was going to push it this morning but as you said I'm not sure that this is the right solution.
/** | ||
* Method to initialize variable before starting the simulation | ||
*/ | ||
virtual void initializeVariable() {} |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
virtual void initializeVariable() {} | |
virtual void initializeVariables() {} |
@@ -46,4 +46,9 @@ class ExternalProblem : public FEProblemBase | |||
* transfer to variables in Multiapp simulations. | |||
*/ | |||
virtual void addExternalVariables() {} | |||
|
|||
/** | |||
* Method to initialize variable before starting the simulation |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
* Method to initialize variable before starting the simulation | |
* Method to initialize variables before starting the simulation |
Job Documentation, step Docs: sync website on 339c477 wanted to post the following: View the site here This comment will be updated on new commits. |
Job Coverage, step Generate coverage on 339c477 wanted to post the following: Framework coverage
Modules coverageCoverage did not change Full coverage reportsReports
This comment will be updated on new commits. |
-issue was caused by external variables never being initialized -in InitProblemAction.C it now checks if there is an external variable -if there is then it calls initializeVariable -initializeVariable was added to BasicExternalProblem and SyncTestExternalProblem closes idaholab#18396
-Reverted BasicExternalProblem and SynceTestExternalProblem -Check to external variable initialization moved to FEProblemBase.C -function name changed to initializeVariables -initializeVariables can be modified in ExternalProblem.C but can also be overriden if needed
b05630b
to
4ce5b0a
Compare
Job Precheck, step Clang format on 4ce5b0a wanted to post the following: Your code requires style changes. A patch was auto generated and copied here
Alternatively, with your repository up to date and in the top level of your repository:
|
-issue was caused by external variables never being initialized
-in InitProblemAction.C it now checks if there is an external variable
-if there is then it calls initializeVariable
-initializeVariable was added to BasicExternalProblem and SyncTestExternalProblem
closes #18396
Reason
If a variable is not properly initialized then it can cause a lot of issues.
Design
Adds check to InitProblemAction that looks to see if there are any external variables. If there are then it calls the initialzeVariable function which must be defined in the desired external variable source file.
Impact
Allows users to utilize external variables for a broader range of issues.