Skip to content
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

Threads #2130

Merged
merged 3 commits into from Mar 20, 2018
Merged

Threads #2130

merged 3 commits into from Mar 20, 2018

Conversation

gassmoeller
Copy link
Member

Implements #59. I decided to make it a cmake variable instead of a input parameter, because we need the value right at the beginning of main.cc:main() before even initializing anything, and we do not know the name of the parameter file at that time. Unfortunately now we need to recompile if we want to change the setting, but at least it is user-controllable. Is this an acceptable solution?

@bangerth
Copy link
Contributor

What if you made it a run time parameter, say -j N? You'd then specify it when calling the executable if you want anything other than the default.

@tjhei
Copy link
Member

tjhei commented Mar 14, 2018

  1. anything except 1 will break PETSc (not that this has been tested recently, so I assume it is probably broken in other places) so keeping 1 as the default is a good idea.
  2. I don't like that it is a cmake parameter (does that mean you have to recompile the whole code-base if you change it?)

@gassmoeller
Copy link
Member Author

Currently we need to recompile everything to change this, yes. Unfortunately everything else is more complicated, because when parsing our runtime parameters we already need information about the MPI communicator (e.g. -h only outputs on process 0) so MPI_InitFinalize needs to be called before parsing runtime parameters. I could delay executing these commands (and only set a flag when parsing), but that makes the whole parsing code more complicated. Do you have an idea how to work around this?

If this breaks PETSc I should probably add a check to CMakeLists that not both are active at the same time.

@tjhei
Copy link
Member

tjhei commented Mar 14, 2018

Currently we need to recompile everything to change this, yes.

So this means it is more annoying to switch than editing main.cc. Hrm.

Unfortunately everything else is more complicated

Hang on: we have an environment variable DEAL_II_NUM_THREADS that is used, see http://www.dealii.org/developer/doxygen/deal.II/classMultithreadInfo.html#ae253b8ff679c4119f9c5bff4439fe606

Wouldn't that be enough? This means we would need to set the value to invalid_unsigned_int for the command line value to work.

@gassmoeller
Copy link
Member Author

Hmm, I tried exporting DEAL_II_NUM_THREADS=1 and that indeed limits the number of threads to 1. But can we set this environment variable by default to 1? I would like to keep the current behavior (threading disabled until somebody explicitly enables it). Mostly to follow the principle of least surprise to the user. Or do you think we should just enable this by default? I could also ask around on the mailing list what people think about the feature.

@tjhei
Copy link
Member

tjhei commented Mar 15, 2018

But can we set this environment variable by default to 1?

Not easily. Either we enable by default (I don't think this will be a problem) or safer:
Can you test early in main.cc:

const char *penv = getenv ("DEAL_II_NUM_THREADS");
unsigned int max_threads = (penv==nullptr) ? 1 : numbers::invalid_unsigned_int;

MPI::InitFinalize(...., max_threads);

@gassmoeller
Copy link
Member Author

Yes that seems to work. I like this solution, it is easy for people to set this if they want to, and everything stays as usual if you do nothing.

@bangerth
Copy link
Contributor

I'd still like to advocate for a command line option -j in the same way as it exists for make and ninja. (Though I'd also be happy if -j has no numeric argument and simply means "use as many threads as reasonable -- possibly limited by DEAL_II_NUM_THREADS. In other words, passing -j would set max_threads to numbers::invalid_unsigned_int, whereas the default is one.)

You can parse command line options before you initialize the MPI system.

@gassmoeller
Copy link
Member Author

I reorganized main() to parse the command line parameters before MPI initialization and made the parameter a command line option. Looks nicer and more intuitive now. I also removed the print_version() function as all of that information is in the header now and removed some duplication by introducing a new template function. Let's see what the tester says. Anything else? (I will follow up with a PR that further cleans main(), but that is unrelated).

@bangerth
Copy link
Contributor

One of the test fails by producing different output. I haven't looked at the code yet, but suspect you have something like

  if (dim>=2 && dim <=3)
    ...do something
  else
     Assert (false, ExcMessage(...));

To restore the previous error (and help the user a bit), just replace the assertion by

  Assert (dim >= 2 && dim <= 3, ...)

Since we're in the else block, the condition is of course always false.

loss you will see in these situations.

Multithreading is controlled by setting the command line parameter \texttt{-j}
or \texttt{--threads}. If the parameter is not set \aspect{} will create
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

comma after "set"

Multithreading is controlled by setting the command line parameter \texttt{-j}
or \texttt{--threads}. If the parameter is not set \aspect{} will create
exactly one thread per MPI process, i.e. multithreading is disabled. Appending
it will automatically spawn several threads per MPI process (a typical example
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

what is "it" here?

exactly one thread per MPI process, i.e. multithreading is disabled. Appending
it will automatically spawn several threads per MPI process (a typical example
is ``2''). Note that the internally used TBB library will determine the number
of threads as a reasonable number, i.e. if you start with 2~MPI processes on a
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

comma after "i.e."

source/main.cc Outdated
<< " --help (for this usage help)"
<< " -h, --help (for this usage help)"
<< std::endl
<< " -j, --threads (to use multi-threading)"
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

keep -h at either the top of the bottom of the list.

source/main.cc Outdated
default:
AssertThrow((dim >= 2) && (dim <= 3),
AssertThrow(false,
ExcMessage ("ASPECT can only be run in 2d and 3d but a "
"different space dimension is given in the parameter file."));
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

This is where the difference in output comes from. I'd say to just revert to the previous condition -- I know it's duplicative, but it's also instructive.

flow_problem.run();
}

run_simulator<3>(input_as_string,output_xml,output_plugin_graph);
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

nice simplification of code repetition

@gassmoeller
Copy link
Member Author

Done 😄.

@bangerth
Copy link
Contributor

OK to merge once the tester is happy.

@gassmoeller gassmoeller merged commit e006f57 into geodynamics:master Mar 20, 2018
@gassmoeller gassmoeller deleted the threads branch March 20, 2018 00:49
@gassmoeller gassmoeller mentioned this pull request Mar 20, 2018
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Development

Successfully merging this pull request may close these issues.

None yet

3 participants