[Bf-blender-cvs] [9421bf66553] functions: initial body type for lazy input evaluation

Jacques Lucke noreply at git.blender.org
Sun Mar 24 18:40:29 CET 2019


Commit: 9421bf665531ec092ee4d9ffd57f8e9eedc2a746
Author: Jacques Lucke
Date:   Sun Mar 24 18:40:23 2019 +0100
Branches: functions
https://developer.blender.org/rB9421bf665531ec092ee4d9ffd57f8e9eedc2a746

initial body type for lazy input evaluation

===================================================================

M	source/blender/functions/CMakeLists.txt
M	source/blender/functions/FN_tuple_call.hpp
M	source/blender/functions/backends/tuple_call/fgraph_tuple_call.cpp
A	source/blender/functions/backends/tuple_call/lazy_to_normal.cpp
A	source/blender/functions/backends/tuple_call/lazy_to_normal.hpp
M	source/blender/functions/backends/tuple_call/tuple_call.cpp
M	source/blender/functions/backends/tuple_call/tuple_call.hpp
M	source/blender/functions/functions/switch.cpp

===================================================================

diff --git a/source/blender/functions/CMakeLists.txt b/source/blender/functions/CMakeLists.txt
index 144a772f095..64f085170f3 100644
--- a/source/blender/functions/CMakeLists.txt
+++ b/source/blender/functions/CMakeLists.txt
@@ -41,6 +41,8 @@ set(SRC
 	backends/tuple_call/fgraph_tuple_call.cpp
 	backends/tuple_call/tuple.hpp
 	backends/tuple_call/tuple.cpp
+	backends/tuple_call/lazy_to_normal.hpp
+	backends/tuple_call/lazy_to_normal.cpp
 
 	backends/dependencies/dependencies.hpp
 	backends/dependencies/dependencies.cpp
diff --git a/source/blender/functions/FN_tuple_call.hpp b/source/blender/functions/FN_tuple_call.hpp
index ee3da8c3565..24276d0386f 100644
--- a/source/blender/functions/FN_tuple_call.hpp
+++ b/source/blender/functions/FN_tuple_call.hpp
@@ -3,4 +3,5 @@
 #include "backends/tuple_call/cpp_types.hpp"
 #include "backends/tuple_call/tuple.hpp"
 #include "backends/tuple_call/tuple_call.hpp"
-#include "backends/tuple_call/fgraph_tuple_call.hpp"
\ No newline at end of file
+#include "backends/tuple_call/fgraph_tuple_call.hpp"
+#include "backends/tuple_call/lazy_to_normal.hpp"
\ No newline at end of file
diff --git a/source/blender/functions/backends/tuple_call/fgraph_tuple_call.cpp b/source/blender/functions/backends/tuple_call/fgraph_tuple_call.cpp
index 2317ea12fc1..476ae8f2230 100644
--- a/source/blender/functions/backends/tuple_call/fgraph_tuple_call.cpp
+++ b/source/blender/functions/backends/tuple_call/fgraph_tuple_call.cpp
@@ -1,5 +1,5 @@
-#include "fgraph_tuple_call.hpp"
 #include "FN_llvm.hpp"
+#include "FN_tuple_call.hpp"
 
 namespace FN {
 
@@ -98,11 +98,15 @@ namespace FN {
 
 			auto *context = new llvm::LLVMContext();
 			for (Node *node : required_nodes) {
-				if (node->function()->has_body<TupleCallBody>()) {
+				SharedFunction &fn = node->function();
+				if (fn->has_body<TupleCallBody>()) {
 					continue;
 				}
-				else if (node->function()->has_body<LLVMBuildIRBody>()) {
-					derive_TupleCallBody_from_LLVMBuildIRBody(node->function(), *context);
+				else if (fn->has_body<LLVMBuildIRBody>()) {
+					derive_TupleCallBody_from_LLVMBuildIRBody(fn, *context);
+				}
+				else if (fn->has_body<LazyInTupleCallBody>()) {
+					derive_TupleCallBody_from_LazyInTupleCallBody(fn);
 				}
 				else {
 					BLI_assert(false);
diff --git a/source/blender/functions/backends/tuple_call/lazy_to_normal.cpp b/source/blender/functions/backends/tuple_call/lazy_to_normal.cpp
new file mode 100644
index 00000000000..ad5adf1ad07
--- /dev/null
+++ b/source/blender/functions/backends/tuple_call/lazy_to_normal.cpp
@@ -0,0 +1,36 @@
+#include "tuple_call.hpp"
+#include "lazy_to_normal.hpp"
+
+namespace FN {
+
+	class MakeEagerBody : public TupleCallBody {
+	private:
+		LazyInTupleCallBody *m_lazy_body;
+		uint m_user_data_size;
+
+	public:
+		MakeEagerBody(LazyInTupleCallBody *body)
+			: m_lazy_body(body),
+			  m_user_data_size(body->user_data_size()) {}
+
+		void call(Tuple &fn_in, Tuple &fn_out) const override
+		{
+			void *user_data = alloca(m_user_data_size);
+			LazyState state(user_data);
+			while (!state.is_done()) {
+				state.start_next_entry();
+				m_lazy_body->call(fn_in, fn_out, state);
+			}
+		}
+	};
+
+	void derive_TupleCallBody_from_LazyInTupleCallBody(
+		SharedFunction &fn)
+	{
+		BLI_assert(fn->has_body<LazyInTupleCallBody>());
+		BLI_assert(!fn->has_body<TupleCallBody>());
+
+		fn->add_body(new MakeEagerBody(fn->body<LazyInTupleCallBody>()));
+	}
+
+} /* namespace FN */
\ No newline at end of file
diff --git a/source/blender/functions/backends/tuple_call/lazy_to_normal.hpp b/source/blender/functions/backends/tuple_call/lazy_to_normal.hpp
new file mode 100644
index 00000000000..b4fe123cdde
--- /dev/null
+++ b/source/blender/functions/backends/tuple_call/lazy_to_normal.hpp
@@ -0,0 +1,10 @@
+#pragma once
+
+#include "FN_core.hpp"
+
+namespace FN {
+
+	void derive_TupleCallBody_from_LazyInTupleCallBody(
+		SharedFunction &fn);
+
+} /* namespace FN */
\ No newline at end of file
diff --git a/source/blender/functions/backends/tuple_call/tuple_call.cpp b/source/blender/functions/backends/tuple_call/tuple_call.cpp
index 25ea86be90b..07264fba4d9 100644
--- a/source/blender/functions/backends/tuple_call/tuple_call.cpp
+++ b/source/blender/functions/backends/tuple_call/tuple_call.cpp
@@ -3,16 +3,29 @@
 namespace FN {
 
 	BLI_COMPOSITION_IMPLEMENTATION(TupleCallBody);
+	BLI_COMPOSITION_IMPLEMENTATION(LazyInTupleCallBody);
 
-	void TupleCallBody::init_defaults(Tuple &fn_in) const
+	void TupleCallBodyBase::init_defaults(Tuple &fn_in) const
 	{
 		fn_in.init_default_all();
 	}
 
-	void TupleCallBody::owner_init_post()
+	void TupleCallBodyBase::owner_init_post()
 	{
 		m_meta_in = SharedTupleMeta::New(this->owner()->signature().input_types());
 		m_meta_out = SharedTupleMeta::New(this->owner()->signature().output_types());
 	}
 
+
+	uint LazyInTupleCallBody::user_data_size() const
+	{
+		return 0;
+	}
+
+	const SmallVector<uint> &LazyInTupleCallBody::always_required() const
+	{
+		static SmallVector<uint> empty_list = {};
+		return empty_list;
+	}
+
 } /* namespace FN */
\ No newline at end of file
diff --git a/source/blender/functions/backends/tuple_call/tuple_call.hpp b/source/blender/functions/backends/tuple_call/tuple_call.hpp
index c72521e64b9..adab1a12efd 100644
--- a/source/blender/functions/backends/tuple_call/tuple_call.hpp
+++ b/source/blender/functions/backends/tuple_call/tuple_call.hpp
@@ -4,7 +4,7 @@
 
 namespace FN {
 
-	class TupleCallBody : public FunctionBody {
+	class TupleCallBodyBase : public FunctionBody {
 	private:
 		SharedTupleMeta m_meta_in;
 		SharedTupleMeta m_meta_out;
@@ -12,15 +12,9 @@ namespace FN {
 	protected:
 		void owner_init_post() override;
 
-		TupleCallBody()
-			: FunctionBody() {}
-
 	public:
-		BLI_COMPOSITION_DECLARATION(TupleCallBody);
-
-		virtual ~TupleCallBody() {};
+		virtual ~TupleCallBodyBase() {};
 
-		virtual void call(Tuple &fn_in, Tuple &fn_out) const = 0;
 		virtual void init_defaults(Tuple &fn_in) const;
 
 		SharedTupleMeta &meta_in()
@@ -34,4 +28,62 @@ namespace FN {
 		}
 	};
 
+	class TupleCallBody : public TupleCallBodyBase {
+	public:
+		BLI_COMPOSITION_DECLARATION(TupleCallBody);
+
+		virtual void call(Tuple &fn_in, Tuple &fn_out) const = 0;
+	};
+
+	class LazyState {
+	private:
+		uint m_entry_count = 0;
+		bool m_is_done = false;
+		void *m_user_data;
+		SmallVector<uint> m_requested_inputs;
+
+	public:
+		LazyState(void *user_data)
+			: m_user_data(user_data) {}
+
+		void start_next_entry()
+		{
+			m_entry_count++;
+		}
+
+		void request_input(uint index)
+		{
+			m_requested_inputs.append(index);
+		}
+
+		void done()
+		{
+			m_is_done = true;
+		}
+
+		bool is_first_entry() const
+		{
+			return m_entry_count == 1;
+		}
+
+		bool is_done() const
+		{
+			return m_is_done;
+		}
+
+		void *user_data() const
+		{
+			return m_user_data;
+		}
+	};
+
+	class LazyInTupleCallBody : public TupleCallBodyBase {
+	public:
+		BLI_COMPOSITION_DECLARATION(LazyInTupleCallBody);
+
+		virtual uint user_data_size() const;
+		virtual const SmallVector<uint> &always_required() const;
+		virtual void call(Tuple &fn_in, Tuple &fn_out, LazyState &state) const = 0;
+	};
+
 } /* namespace FN */
\ No newline at end of file
diff --git a/source/blender/functions/functions/switch.cpp b/source/blender/functions/functions/switch.cpp
index ae0df818802..0cd64738a4c 100644
--- a/source/blender/functions/functions/switch.cpp
+++ b/source/blender/functions/functions/switch.cpp
@@ -9,29 +9,45 @@ namespace FN { namespace Functions {
 
 	using namespace Types;
 
-	class BoolSwitch : public TupleCallBody {
+	class LazyBoolSwitch : public LazyInTupleCallBody {
 	private:
-		SharedType m_data_type;
-		CPPTypeInfo *m_type_info;
+		SharedType m_type;
+		uint m_type_size;
+		const SmallVector<uint> m_always_required = {0};
 
 	public:
-		BoolSwitch(SharedType data_type)
-			: m_data_type(data_type),
-			  m_type_info(data_type->extension<CPPTypeInfo>()) {}
+		LazyBoolSwitch(SharedType type)
+			: m_type(type),
+			  m_type_size(type->extension<CPPTypeInfo>()->size_of_type()) {}
 
-		void call(Tuple &fn_in, Tuple &fn_out) const override
+		const SmallVector<uint> &always_required() const override
+		{
+			return m_always_required;
+		}
+
+		void call(Tuple &fn_in, Tuple &fn_out, LazyState &state) const override
 		{
 			bool condition = fn_in.get<bool>(0);
-			uint size = m_type_info->size_of_type();
-			void *value = alloca(size);
+
+			if (state.is_first_entry()) {
+				if (condition) {
+					state.request_input(1);
+				}
+				else {
+					state.request_input(2);
+				}
+				return;
+			}
+
+			void *value = alloca(m_type_size);
 			if (condition) {
 				fn_in.relocate_out__dynamic(1, value);
-				fn_out.relocate_in__dynamic(0, value);
 			}
 			else {
 				fn_in.relocate_out__dynamic(2, value);
-				fn_out.relocate_in__dynamic(0, value);
 			}
+			fn_out.relocate_in__dynamic(0, value);
+			state.done();
 		}
 	};
 
@@ -45,7 +61,7 @@ namespace FN { namespace Functions {
 		}, {
 			OutputParameter("Result", data_type),
 		}));
-		fn->add_body(new BoolSwitch(data_type));
+		fn->add_body(new LazyBoolSwitch(data_type));
 		return fn;
 	}



More information about the Bf-blender-cvs mailing list