[Scummvm-git-logs] scummvm master -> 8f9c2359e0e1bbc2f7e42f4a2f8da5d527476c34

bluegr noreply at scummvm.org
Mon Aug 5 06:57:44 UTC 2024


This automated email contains information about 3 new commits which have been
pushed to the 'scummvm' repo located at https://github.com/scummvm/scummvm .

Summary:
915eccfa47 COMMON: Fix forwarding of rvalue refs
179f7ecdc3 COMMON: Add emplace, emplace_back, and rvalue push_back
8f9c2359e0 TEST: Add Array emplace and move semantic push_back tests


Commit: 915eccfa478dd25c55aec69dc9a113a97a66115b
    https://github.com/scummvm/scummvm/commit/915eccfa478dd25c55aec69dc9a113a97a66115b
Author: elasota (1137273+elasota at users.noreply.github.com)
Date: 2024-08-05T09:57:40+03:00

Commit Message:
COMMON: Fix forwarding of rvalue refs

Changed paths:
    common/util.h


diff --git a/common/util.h b/common/util.h
index b4d9be28c70..bf1b99351b6 100644
--- a/common/util.h
+++ b/common/util.h
@@ -210,6 +210,11 @@ constexpr remove_reference_t<T> &&move(T &&t) noexcept {
   return static_cast<remove_reference_t<T> &&>(t);
 }
 
+template<class T>
+constexpr T&& forward(remove_reference_t<T> &&t) noexcept {
+	return static_cast<T &&>(t);
+}
+
 template<class T>
 constexpr T&& forward(remove_reference_t<T> &t) noexcept {
 	return static_cast<T &&>(t);


Commit: 179f7ecdc33f4be06aad427d0d6249444823d508
    https://github.com/scummvm/scummvm/commit/179f7ecdc33f4be06aad427d0d6249444823d508
Author: elasota (1137273+elasota at users.noreply.github.com)
Date: 2024-08-05T09:57:40+03:00

Commit Message:
COMMON: Add emplace, emplace_back, and rvalue push_back

Changed paths:
    common/array.h


diff --git a/common/array.h b/common/array.h
index 83ccb739486..a0808b3668e 100644
--- a/common/array.h
+++ b/common/array.h
@@ -138,12 +138,52 @@ public:
 		_capacity = _size = 0;
 	}
 
+	/** Construct an element into a position in the array. */
+	template<class... TArgs>
+	void emplace(const_iterator pos, TArgs&&... args) {
+		assert(pos >= _storage && pos <= _storage + _size);
+
+		const size_type index = static_cast<size_type>(pos - _storage);
+
+		if (_size != _capacity && index == _size) {
+			// Added at the end in the existing storage
+			new (_storage + index) T(Common::forward<TArgs>(args)...);
+		} else {
+			// Either added in the middle, or ran out of space
+			// In the added-in-the-middle case, the copy is required because the parameters
+			// may contain a const ref to the original storage.
+			T *oldStorage = _storage;
+
+			allocCapacity(roundUpCapacity(_size + 1));
+
+			// Construct the new element first, since it may copy-construct from
+			// the original array
+			new (_storage + index) T(Common::forward<TArgs>(args)...);
+
+			// Move the original data
+			uninitialized_move(oldStorage, oldStorage + index, _storage);
+			uninitialized_move(oldStorage + index, oldStorage + _size, _storage + index + 1);
+
+			freeStorage(oldStorage, _size);
+		}
+
+		_size++;
+	}
+
+	/** Construct an element into a position in the array. */
+	template<class... TArgs>
+	void emplace_back(TArgs &&...args) {
+		emplace(begin() + _size, Common::forward<TArgs>(args)...);
+	}
+
 	/** Append an element to the end of the array. */
 	void push_back(const T &element) {
-		if (_size + 1 <= _capacity)
-			new ((void *)&_storage[_size++]) T(element);
-		else
-			insert_aux(end(), &element, &element + 1);
+		emplace_back(element);
+	}
+
+	/** Append an element to the end of the array. */
+	void push_back(T &&element) {
+		emplace_back(Common::move(element));
 	}
 
 	/** Append an element to the end of the array. */


Commit: 8f9c2359e0e1bbc2f7e42f4a2f8da5d527476c34
    https://github.com/scummvm/scummvm/commit/8f9c2359e0e1bbc2f7e42f4a2f8da5d527476c34
Author: elasota (1137273+elasota at users.noreply.github.com)
Date: 2024-08-05T09:57:40+03:00

Commit Message:
TEST: Add Array emplace and move semantic push_back tests

Changed paths:
    test/common/array.h


diff --git a/test/common/array.h b/test/common/array.h
index eaade76b067..12934d1bb87 100644
--- a/test/common/array.h
+++ b/test/common/array.h
@@ -4,6 +4,40 @@
 #include "common/noncopyable.h"
 #include "common/str.h"
 
+
+struct ArrayTestMovable {
+	ArrayTestMovable() : _value(0), _wasMoveConstructed(false), _wasMovedFrom(false) {}
+
+	explicit ArrayTestMovable(int value) : _value(value), _wasMoveConstructed(false), _wasMovedFrom(false) {}
+
+	ArrayTestMovable(const ArrayTestMovable &other)
+		: _value(other._value), _wasMoveConstructed(false), _wasMovedFrom(false) {
+	}
+
+	ArrayTestMovable(ArrayTestMovable &&other) noexcept
+		: _value(other._value), _wasMoveConstructed(true), _wasMovedFrom(false) {
+		other._wasMovedFrom = true;
+	}
+
+	int _value;
+	bool _wasMoveConstructed;
+	bool _wasMovedFrom;
+};
+
+// Hopefully temporary until Common::Pair can be updated to have move constructor/assign operator
+struct ArrayTestMovablePair {
+	ArrayTestMovablePair(ArrayTestMovable &&pFirst, ArrayTestMovable &&pSecond)
+	: first(Common::move(pFirst)), second(Common::move(pSecond)) {
+	}
+
+	ArrayTestMovablePair(const ArrayTestMovable &&pFirst, const ArrayTestMovable &&pSecond)
+		: first(pFirst), second(pSecond) {
+	}
+
+	ArrayTestMovable first;
+	ArrayTestMovable second;
+};
+
 class ArrayTestSuite : public CxxTest::TestSuite
 {
 	public:
@@ -559,5 +593,25 @@ public:
 			delete *iter;
 		}
 	}
+	
+	void test_emplace() {
+		Common::Array<ArrayTestMovablePair> movablePairArray;
+		movablePairArray.emplace_back(ArrayTestMovable(1), ArrayTestMovable(2));
+
+		TS_ASSERT(movablePairArray[0].first._wasMoveConstructed);
+		TS_ASSERT_EQUALS(movablePairArray[0].first._value, 1);
+		TS_ASSERT(movablePairArray[0].second._wasMoveConstructed);
+		TS_ASSERT_EQUALS(movablePairArray[0].second._value, 2);
+	}
+	
+	void test_push_back_move() {
+		ArrayTestMovable movable(3);
 
+		Common::Array<ArrayTestMovable> movableArray;
+		movableArray.push_back(Common::move(movable));
+
+		TS_ASSERT(movable._wasMovedFrom);
+		TS_ASSERT_EQUALS(movableArray[0]._value, 3);
+		TS_ASSERT(movableArray[0]._wasMoveConstructed);
+	}
 };




More information about the Scummvm-git-logs mailing list