Global Metrics
path: .metrics.cognitive.sum
old: 0.0
new: 1.0
path: .metrics.cognitive.average
old: 0.0
new: 0.058823529411764705
path: .metrics.nexits.sum
old: 0.0
new: 6.0
path: .metrics.nexits.average
old: 0.0
new: 0.35294117647058826
path: .metrics.nargs.average
old: 0.0
new: 0.4117647058823529
path: .metrics.nargs.sum
old: 0.0
new: 7.0
path: .metrics.nom.total
old: 1.0
new: 17.0
path: .metrics.nom.functions
old: 1.0
new: 17.0
path: .metrics.cyclomatic.average
old: 1.0
new: 1.318181818181818
path: .metrics.cyclomatic.sum
old: 5.0
new: 29.0
path: .metrics.mi.mi_visual_studio
old: 38.368347146440925
new: 27.796422685956298
path: .metrics.mi.mi_original
old: 65.60987362041398
new: 47.53188279298526
path: .metrics.mi.mi_sei
old: 58.03765837266502
new: 33.15313015509651
path: .metrics.loc.blank
old: 8.0
new: 21.0
path: .metrics.loc.ploc
old: 38.0
new: 67.0
path: .metrics.loc.sloc
old: 68.0
new: 125.0
path: .metrics.loc.cloc
old: 22.0
new: 37.0
path: .metrics.loc.lloc
old: 7.0
new: 13.0
path: .metrics.halstead.volume
old: 993.0576916718502
new: 1667.5688237022168
path: .metrics.halstead.N2
old: 81.0
new: 108.0
path: .metrics.halstead.effort
old: 9831.271147551315
new: 62102.5630895998
path: .metrics.halstead.n2
old: 45.0
new: 29.0
path: .metrics.halstead.estimated_program_length
old: 285.1871371398456
new: 227.32001075644683
path: .metrics.halstead.n1
old: 11.0
new: 20.0
path: .metrics.halstead.N1
old: 90.0
new: 189.0
path: .metrics.halstead.length
old: 171.0
new: 297.0
path: .metrics.halstead.purity_ratio
old: 1.66776103590553
new: 0.7653872416041981
path: .metrics.halstead.difficulty
old: 9.9
new: 37.241379310344826
path: .metrics.halstead.level
old: 0.101010101010101
new: 0.026851851851851852
path: .metrics.halstead.vocabulary
old: 56.0
new: 49.0
path: .metrics.halstead.bugs
old: 0.1529743188378401
new: 0.5227392315268155
path: .metrics.halstead.time
old: 546.1817304195176
new: 3450.1423938666553
Spaces Data
Minimal test - lines (43, 43)
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.level
old: null
new: 0.3333333333333333
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.vocabulary
old: 1.0
new: 8.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.length
old: 1.0
new: 10.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.volume
old: 0.0
new: 30.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.purity_ratio
old: null
new: 1.7509775004326935
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.N1
old: 0.0
new: 8.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.effort
old: 0.0
new: 90.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.n1
old: 0.0
new: 6.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.n2
old: 1.0
new: 2.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.bugs
old: 0.0
new: 0.006694329500821694
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.N2
old: 1.0
new: 2.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.difficulty
old: 0.0
new: 3.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.estimated_program_length
old: null
new: 17.509775004326936
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.halstead.time
old: 0.0
new: 5.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.nexits.sum
old: 0.0
new: 1.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.nexits.average
old: null
new: 1.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.mi.mi_visual_studio
old: null
new: 89.52267462886361
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.mi.mi_original
old: null
new: 153.0837736153568
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.mi.mi_sei
old: null
new: 145.25416890283572
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.cognitive.average
old: null
new: 0.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.nom.functions
old: 0.0
new: 1.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.nom.total
old: 0.0
new: 1.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.nargs.average
old: null
new: 0.0
path: .spaces[0].spaces[0].spaces[0].spaces[0].metrics.loc.lloc
old: 0.0
new: 1.0
Code
T* operator->() const& { return &ref(); }
Minimal test - lines (14, 123)
path: .spaces[0].metrics.cyclomatic.sum
old: 4.0
new: 28.0
path: .spaces[0].metrics.cyclomatic.average
old: 1.0
new: 1.3333333333333333
path: .spaces[0].metrics.nexits.average
old: 0.0
new: 0.35294117647058826
path: .spaces[0].metrics.nexits.sum
old: 0.0
new: 6.0
path: .spaces[0].metrics.cognitive.sum
old: 0.0
new: 1.0
path: .spaces[0].metrics.cognitive.average
old: 0.0
new: 0.058823529411764705
path: .spaces[0].metrics.nom.functions
old: 1.0
new: 17.0
path: .spaces[0].metrics.nom.total
old: 1.0
new: 17.0
path: .spaces[0].metrics.mi.mi_visual_studio
old: 40.594346395795455
new: 29.2329831871729
path: .spaces[0].metrics.mi.mi_original
old: 69.41633233681023
new: 49.98840125006565
path: .spaces[0].metrics.mi.mi_sei
old: 61.93706617403583
new: 35.449363072364825
path: .spaces[0].metrics.nargs.average
old: 0.0
new: 0.4117647058823529
path: .spaces[0].metrics.nargs.sum
old: 0.0
new: 7.0
path: .spaces[0].metrics.loc.cloc
old: 16.0
new: 30.0
path: .spaces[0].metrics.loc.lloc
old: 7.0
new: 13.0
path: .spaces[0].metrics.loc.sloc
old: 55.0
new: 110.0
path: .spaces[0].metrics.loc.ploc
old: 34.0
new: 61.0
path: .spaces[0].metrics.loc.blank
old: 5.0
new: 19.0
path: .spaces[0].metrics.halstead.volume
old: 966.8211003634626
new: 1618.4036531247048
path: .spaces[0].metrics.halstead.N2
old: 78.0
new: 104.0
path: .spaces[0].metrics.halstead.bugs
old: 0.15104350317976994
new: 0.5374152336913978
path: .spaces[0].metrics.halstead.estimated_program_length
old: 271.3831322572005
new: 208.64999456941564
path: .spaces[0].metrics.halstead.level
old: 0.10023310023310024
new: 0.025
path: .spaces[0].metrics.halstead.n2
old: 43.0
new: 26.0
path: .spaces[0].metrics.halstead.length
old: 168.0
new: 293.0
path: .spaces[0].metrics.halstead.purity_ratio
old: 1.615375787245241
new: 0.7121160224212137
path: .spaces[0].metrics.halstead.N1
old: 90.0
new: 189.0
path: .spaces[0].metrics.halstead.vocabulary
old: 54.0
new: 46.0
path: .spaces[0].metrics.halstead.difficulty
old: 9.976744186046512
new: 40.0
path: .spaces[0].metrics.halstead.effort
old: 9645.726791998266
new: 64736.14612498819
path: .spaces[0].metrics.halstead.time
old: 535.8737106665703
new: 3596.452562499344
path: .spaces[0].metrics.halstead.n1
old: 11.0
new: 20.0
Code
namespace mozilla {
// A template to wrap a type with a mutex so that accesses to the type's
// data are required to take the lock before accessing it. This ensures
// that a mutex is explicitly associated with the data that it protects,
// and makes it impossible to access the data without first taking the
// associated mutex.
//
// This is based on Rust's std::sync::Mutex, which operates under the
// strategy of locking data, rather than code.
//
// Examples:
//
// DataMutex u32DataMutex(1, "u32DataMutex");
// auto x = u32DataMutex.Lock();
// *x = 4;
// assert(*x, 4u);
//
// DataMutex> arrayDataMutex("arrayDataMutex");
// auto a = arrayDataMutex.Lock();
// auto& x = a.ref();
// x.AppendElement(1u);
// assert(x[0], 1u);
//
template
class DataMutexBase {
public:
class MOZ_STACK_CLASS AutoLock {
public:
T* operator->() const& { return &ref(); }
T* operator->() const&& = delete;
T& operator*() const& { return ref(); }
T& operator*() const&& = delete;
// Like RefPtr, make this act like its underlying raw pointer type
// whenever it is used in a context where a raw pointer is expected.
operator T*() const& { return &ref(); }
// Like RefPtr, don't allow implicit conversion of temporary to raw pointer.
operator T*() const&& = delete;
T& ref() const& {
MOZ_ASSERT(mOwner);
return mOwner->mValue;
}
T& ref() const&& = delete;
AutoLock(AutoLock&& aOther) : mOwner(aOther.mOwner) {
aOther.mOwner = nullptr;
}
~AutoLock() {
if (mOwner) {
mOwner->mMutex.Unlock();
mOwner = nullptr;
}
}
private:
friend class DataMutexBase;
AutoLock(const AutoLock& aOther) = delete;
explicit AutoLock(DataMutexBase* aDataMutex)
: mOwner(aDataMutex) {
MOZ_ASSERT(!!mOwner);
mOwner->mMutex.Lock();
}
DataMutexBase* mOwner;
};
explicit DataMutexBase(const char* aName) : mMutex(aName) {}
DataMutexBase(T&& aValue, const char* aName)
: mMutex(aName), mValue(std::move(aValue)) {}
AutoLock Lock() { return AutoLock(this); }
const MutexType& Mutex() const { return mMutex; }
private:
MutexType mMutex;
T mValue;
};
// Craft a version of StaticMutex that takes a const char* in its ctor.
// We need this so it works interchangeably with Mutex which requires a const
// char* aName in its ctor.
class StaticMutexNameless : public StaticMutex {
public:
explicit StaticMutexNameless(const char* aName) : StaticMutex() {}
private:
// Disallow copy construction, `=`, `new`, and `delete` like BaseStaticMutex.
#ifdef DEBUG
StaticMutexNameless(StaticMutexNameless& aOther);
#endif // DEBUG
StaticMutexNameless& operator=(StaticMutexNameless* aRhs);
static void* operator new(size_t) noexcept(true);
static void operator delete(void*);
};
template
using DataMutex = DataMutexBase;
template
using StaticDataMutex = DataMutexBase;
} // namespace mozilla
Minimal test - lines (41, 85)
path: .spaces[0].spaces[0].spaces[0].metrics.mi.mi_original
old: 71.95418488633987
new: 70.16968782314429
path: .spaces[0].spaces[0].spaces[0].metrics.mi.mi_sei
old: 66.10950169086291
new: 46.938103095281505
path: .spaces[0].spaces[0].spaces[0].metrics.mi.mi_visual_studio
old: 42.07847069376601
new: 41.0349051597335
path: .spaces[0].spaces[0].spaces[0].metrics.cyclomatic.sum
old: 2.0
new: 19.0
path: .spaces[0].spaces[0].spaces[0].metrics.cyclomatic.average
old: 1.0
new: 1.4615384615384617
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.bugs
old: 0.14923510764419115
new: 0.30695978917863226
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.estimated_program_length
old: 257.7133799943517
new: 128.36161893476807
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.level
old: 0.09808612440191387
new: 0.02880658436213992
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.n2
old: 41.0
new: 14.0
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.length
old: 163.0
new: 161.0
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.effort
old: 9473.018530629884
new: 27945.0
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.time
old: 526.2788072572157
new: 1552.5
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.n1
old: 11.0
new: 18.0
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.volume
old: 929.171674056998
new: 805.0
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.vocabulary
old: 52.0
new: 32.0
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.purity_ratio
old: 1.5810636809469432
new: 0.7972771362407955
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.N2
old: 76.0
new: 54.0
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.difficulty
old: 10.195121951219512
new: 34.714285714285715
path: .spaces[0].spaces[0].spaces[0].metrics.halstead.N1
old: 87.0
new: 107.0
path: .spaces[0].spaces[0].spaces[0].metrics.nexits.sum
old: 0.0
new: 4.0
path: .spaces[0].spaces[0].spaces[0].metrics.nexits.average
old: 0.0
new: 0.3333333333333333
path: .spaces[0].spaces[0].spaces[0].metrics.nargs.sum
old: 0.0
new: 3.0
path: .spaces[0].spaces[0].spaces[0].metrics.nargs.average
old: 0.0
new: 0.25
path: .spaces[0].spaces[0].spaces[0].metrics.nom.functions
old: 1.0
new: 12.0
path: .spaces[0].spaces[0].spaces[0].metrics.nom.total
old: 1.0
new: 12.0
path: .spaces[0].spaces[0].spaces[0].metrics.loc.cloc
old: 15.0
new: 3.0
path: .spaces[0].spaces[0].spaces[0].metrics.loc.lloc
old: 6.0
new: 11.0
path: .spaces[0].spaces[0].spaces[0].metrics.loc.blank
old: 4.0
new: 10.0
path: .spaces[0].spaces[0].spaces[0].metrics.loc.ploc
old: 30.0
new: 32.0
path: .spaces[0].spaces[0].spaces[0].metrics.loc.sloc
old: 49.0
new: 45.0
path: .spaces[0].spaces[0].spaces[0].metrics.cognitive.sum
old: 0.0
new: 1.0
path: .spaces[0].spaces[0].spaces[0].metrics.cognitive.average
old: 0.0
new: 0.08333333333333333
Code
class MOZ_STACK_CLASS AutoLock {
public:
T* operator->() const& { return &ref(); }
T* operator->() const&& = delete;
T& operator*() const& { return ref(); }
T& operator*() const&& = delete;
// Like RefPtr, make this act like its underlying raw pointer type
// whenever it is used in a context where a raw pointer is expected.
operator T*() const& { return &ref(); }
// Like RefPtr, don't allow implicit conversion of temporary to raw pointer.
operator T*() const&& = delete;
T& ref() const& {
MOZ_ASSERT(mOwner);
return mOwner->mValue;
}
T& ref() const&& = delete;
AutoLock(AutoLock&& aOther) : mOwner(aOther.mOwner) {
aOther.mOwner = nullptr;
}
~AutoLock() {
if (mOwner) {
mOwner->mMutex.Unlock();
mOwner = nullptr;
}
}
private:
friend class DataMutexBase;
AutoLock(const AutoLock& aOther) = delete;
explicit AutoLock(DataMutexBase* aDataMutex)
: mOwner(aDataMutex) {
MOZ_ASSERT(!!mOwner);
mOwner->mMutex.Lock();
}
DataMutexBase* mOwner;
};
Minimal test - lines (39, 99)
path: .spaces[0].spaces[0].metrics.halstead.purity_ratio
old: 1.593560720251315
new: 0.7374301914324605
path: .spaces[0].spaces[0].metrics.halstead.length
old: 166.0
new: 219.0
path: .spaces[0].spaces[0].metrics.halstead.volume
old: 950.8347954574908
new: 1149.2961254441452
path: .spaces[0].spaces[0].metrics.halstead.vocabulary
old: 53.0
new: 38.0
path: .spaces[0].spaces[0].metrics.halstead.N2
old: 77.0
new: 78.0
path: .spaces[0].spaces[0].metrics.halstead.time
old: 532.6435659738722
new: 2766.8240056988684
path: .spaces[0].spaces[0].metrics.halstead.n1
old: 11.0
new: 20.0
path: .spaces[0].spaces[0].metrics.halstead.estimated_program_length
old: 264.53107956171823
new: 161.49721192370885
path: .spaces[0].spaces[0].metrics.halstead.n2
old: 42.0
new: 18.0
path: .spaces[0].spaces[0].metrics.halstead.bugs
old: 0.15043591743468346
new: 0.45121282859473894
path: .spaces[0].spaces[0].metrics.halstead.difficulty
old: 10.083333333333334
new: 43.333333333333336
path: .spaces[0].spaces[0].metrics.halstead.level
old: 0.09917355371900824
new: 0.023076923076923075
path: .spaces[0].spaces[0].metrics.halstead.effort
old: 9587.5841875297
new: 49802.83210257963
path: .spaces[0].spaces[0].metrics.halstead.N1
old: 89.0
new: 141.0
path: .spaces[0].spaces[0].metrics.loc.cloc
old: 15.0
new: 3.0
path: .spaces[0].spaces[0].metrics.loc.ploc
old: 32.0
new: 43.0
path: .spaces[0].spaces[0].metrics.loc.sloc
old: 53.0
new: 61.0
path: .spaces[0].spaces[0].metrics.loc.lloc
old: 7.0
new: 13.0
path: .spaces[0].spaces[0].metrics.loc.blank
old: 6.0
new: 15.0
path: .spaces[0].spaces[0].metrics.nargs.sum
old: 0.0
new: 6.0
path: .spaces[0].spaces[0].metrics.nargs.average
old: 0.0
new: 0.375
path: .spaces[0].spaces[0].metrics.mi.mi_sei
old: 62.77281568488872
new: 33.14808576872802
path: .spaces[0].spaces[0].metrics.mi.mi_visual_studio
old: 41.130468584980015
new: 36.2631213806286
path: .spaces[0].spaces[0].metrics.mi.mi_original
old: 70.33310128031583
new: 62.0099375608749
path: .spaces[0].spaces[0].metrics.cyclomatic.sum
old: 3.0
new: 25.0
path: .spaces[0].spaces[0].metrics.cyclomatic.average
old: 1.0
new: 1.3888888888888888
path: .spaces[0].spaces[0].metrics.nexits.sum
old: 0.0
new: 6.0
path: .spaces[0].spaces[0].metrics.nexits.average
old: 0.0
new: 0.375
path: .spaces[0].spaces[0].metrics.cognitive.average
old: 0.0
new: 0.0625
path: .spaces[0].spaces[0].metrics.cognitive.sum
old: 0.0
new: 1.0
path: .spaces[0].spaces[0].metrics.nom.total
old: 1.0
new: 16.0
path: .spaces[0].spaces[0].metrics.nom.functions
old: 1.0
new: 16.0
Code
class DataMutexBase {
public:
class MOZ_STACK_CLASS AutoLock {
public:
T* operator->() const& { return &ref(); }
T* operator->() const&& = delete;
T& operator*() const& { return ref(); }
T& operator*() const&& = delete;
// Like RefPtr, make this act like its underlying raw pointer type
// whenever it is used in a context where a raw pointer is expected.
operator T*() const& { return &ref(); }
// Like RefPtr, don't allow implicit conversion of temporary to raw pointer.
operator T*() const&& = delete;
T& ref() const& {
MOZ_ASSERT(mOwner);
return mOwner->mValue;
}
T& ref() const&& = delete;
AutoLock(AutoLock&& aOther) : mOwner(aOther.mOwner) {
aOther.mOwner = nullptr;
}
~AutoLock() {
if (mOwner) {
mOwner->mMutex.Unlock();
mOwner = nullptr;
}
}
private:
friend class DataMutexBase;
AutoLock(const AutoLock& aOther) = delete;
explicit AutoLock(DataMutexBase* aDataMutex)
: mOwner(aDataMutex) {
MOZ_ASSERT(!!mOwner);
mOwner->mMutex.Lock();
}
DataMutexBase* mOwner;
};
explicit DataMutexBase(const char* aName) : mMutex(aName) {}
DataMutexBase(T&& aValue, const char* aName)
: mMutex(aName), mValue(std::move(aValue)) {}
AutoLock Lock() { return AutoLock(this); }
const MutexType& Mutex() const { return mMutex; }
private:
MutexType mMutex;
T mValue;
};