Commit a4ceb6a28f57dee5ce2e8fe4c4ce8fce43c6b83d

Authored by Charles Otto
1 parent d16f9df0

Clarify use of Common::seedRNG

Common::seedRNG uses a static variable to ensure that the RNG is seeded exactly
once per run of OpenBR. In spite of this, seedRNG was called from several
places, although the function would have an effect exactly once.

This commit
adds thread safety to seedRNG (previously the use of a static variable was
unsafe, although it could only cause a rather minor problem). More importantly
call seedRNG only from Context::initialize. If it is desirable to call seedRNG
more than once, changes will need to be made to support doing that in a
meaningful way.
openbr/core/common.cpp
... ... @@ -15,11 +15,15 @@
15 15 * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
16 16  
17 17 #include "common.h"
  18 +#include <QMutex>
18 19  
19 20 using namespace std;
20 21  
21 22 /**** GLOBAL ****/
22 23 void Common::seedRNG() {
  24 + static QMutex seedControl;
  25 + QMutexLocker lock(&seedControl);
  26 +
23 27 static bool seeded = false;
24 28 if (!seeded) {
25 29 srand(0); // We seed with 0 instead of time(NULL) to have reproducible randomness
... ... @@ -29,8 +33,6 @@ void Common::seedRNG() {
29 33  
30 34 QList<int> Common::RandSample(int n, int max, int min, bool unique)
31 35 {
32   - seedRNG();
33   -
34 36 QList<int> samples; samples.reserve(n);
35 37 int range = max-min;
36 38 if (range <= 0) qFatal("Non-positive range.");
... ... @@ -50,8 +52,6 @@ QList&lt;int&gt; Common::RandSample(int n, int max, int min, bool unique)
50 52  
51 53 QList<int> Common::RandSample(int n, const QSet<int> &values, bool unique)
52 54 {
53   - seedRNG();
54   -
55 55 QList<int> valueList = values.toList();
56 56 if (unique && (values.size() <= n)) return valueList;
57 57  
... ...
openbr/openbr_plugin.cpp
... ... @@ -891,6 +891,8 @@ void br::Context::initialize(int &amp;argc, char *argv[], QString sdkPath, bool use_
891 891  
892 892 qInstallMessageHandler(messageHandler);
893 893  
  894 + Common::seedRNG();
  895 +
894 896 // Search for SDK
895 897 if (sdkPath.isEmpty()) {
896 898 QStringList checkPaths; checkPaths << QDir::currentPath() << QCoreApplication::applicationDirPath();
... ...
openbr/plugins/independent.cpp
... ... @@ -35,7 +35,6 @@ static TemplateList Downsample(const TemplateList &amp;templates, int classes, int i
35 35 if ((classes != std::numeric_limits<int>::max()) && (uniqueLabels.size() < classes))
36 36 qWarning("Downsample requested %d classes but only %d are available.", classes, uniqueLabels.size());
37 37  
38   - Common::seedRNG();
39 38 QList<QString> selectedLabels = uniqueLabels;
40 39 if (classes < uniqueLabels.size()) {
41 40 std::random_shuffle(selectedLabels.begin(), selectedLabels.end());
... ...