From dc2493e7525bb7633f697ef10f72b72b46222249 Mon Sep 17 00:00:00 2001
From: Andy Belle-Isle <drumsetmonkey@gmail.com>
Date: Fri, 30 Aug 2019 00:45:36 -0400
Subject: Forget what I said, I just need to change git attributes to mark for
 vendor

---
 lib/sol2/examples/source/shared_ptr.cpp | 97 +++++++++++++++++++++++++++++++++
 1 file changed, 97 insertions(+)
 create mode 100644 lib/sol2/examples/source/shared_ptr.cpp

(limited to 'lib/sol2/examples/source/shared_ptr.cpp')

diff --git a/lib/sol2/examples/source/shared_ptr.cpp b/lib/sol2/examples/source/shared_ptr.cpp
new file mode 100644
index 0000000..8f1cce6
--- /dev/null
+++ b/lib/sol2/examples/source/shared_ptr.cpp
@@ -0,0 +1,97 @@
+#define SOL_ALL_SAFETIES_ON 1
+#include <sol/sol.hpp>
+
+#include "assert.hpp"
+
+#include <iostream>
+
+struct my_type {
+	int value = 10;
+
+	my_type() {
+		std::cout << "my_type at " << static_cast<void*>(this) << " being default constructed!" << std::endl;
+	}
+
+	my_type(const my_type& other) : value(other.value) {
+		std::cout << "my_type at " << static_cast<void*>(this) << " being copy constructed!" << std::endl;
+	}
+
+	my_type(my_type&& other) : value(other.value) {
+		std::cout << "my_type at " << static_cast<void*>(this) << " being move-constructed!" << std::endl;
+	}
+
+	my_type& operator=(const my_type& other) {
+		value = other.value;
+		std::cout << "my_type at " << static_cast<void*>(this) << " being copy-assigned to!" << std::endl;
+		return *this;
+	}
+
+	my_type& operator=(my_type&& other) {
+		value = other.value;
+		std::cout << "my_type at " << static_cast<void*>(this) << " being move-assigned to!" << std::endl;
+		return *this;
+	}
+
+	~my_type() {
+		std::cout << "my_type at " << static_cast<void*>(this) << " being destructed!" << std::endl;
+	}
+};
+
+int main() {
+
+	std::cout << "=== shared_ptr support ===" << std::endl;
+
+	sol::state lua;
+	lua.new_usertype<my_type>("my_type",
+		"value", &my_type::value
+		);
+	{
+		std::shared_ptr<my_type> shared = std::make_shared<my_type>();
+		lua["shared"] = std::move(shared);
+	}
+	{
+		std::cout << "getting reference to shared_ptr..." << std::endl;
+		std::shared_ptr<my_type>& ref_to_shared_ptr = lua["shared"];
+		std::cout << "\tshared.use_count(): " << ref_to_shared_ptr.use_count() << std::endl;
+		my_type& ref_to_my_type = lua["shared"];
+		std::cout << "\tafter getting reference to my_type: " << ref_to_shared_ptr.use_count() << std::endl;
+		my_type* ptr_to_my_type = lua["shared"];
+		std::cout << "\tafter getting pointer to my_type: " << ref_to_shared_ptr.use_count() << std::endl;
+
+		c_assert(ptr_to_my_type == ref_to_shared_ptr.get());
+		c_assert(&ref_to_my_type == ref_to_shared_ptr.get());
+		c_assert(ref_to_shared_ptr->value == 10);
+
+		// script affects all of them equally
+		lua.script("shared.value = 20");
+
+		c_assert(ptr_to_my_type->value == 20);
+		c_assert(ref_to_my_type.value == 20);
+		c_assert(ref_to_shared_ptr->value == 20);
+	}
+	{
+		std::cout << "getting copy of shared_ptr..." << std::endl;
+		std::shared_ptr<my_type> copy_of_shared_ptr = lua["shared"];
+		std::cout << "\tshared.use_count(): " << copy_of_shared_ptr.use_count() << std::endl;
+		my_type copy_of_value = lua["shared"];
+		std::cout << "\tafter getting value copy of my_type: " << copy_of_shared_ptr.use_count() << std::endl;
+
+		c_assert(copy_of_shared_ptr->value == 20);
+		c_assert(copy_of_value.value == 20);
+
+		// script still affects pointer, but does not affect copy of `my_type`
+		lua.script("shared.value = 30");
+
+		c_assert(copy_of_shared_ptr->value == 30);
+		c_assert(copy_of_value.value == 20);
+	}
+	// set to nil and collect garbage to destroy it
+	lua.script("shared = nil");
+	lua.collect_garbage();
+	lua.collect_garbage();
+
+	std::cout << "garbage has been collected" << std::endl;
+	std::cout << std::endl;
+
+	return 0;
+}
-- 
cgit v1.2.3