1//************************************ bs::framework - Copyright 2018 Marko Pintera **************************************//
2//*********** Licensed under the MIT license. See LICENSE.md for full terms. This notice is not to be removed. ***********//
3#pragma once
4
5#include "BsCorePrerequisites.h"
6#include "Threading/BsAsyncOp.h"
7
8namespace bs
9{
10 namespace ct
11 {
12 /** @addtogroup CoreThread
13 * @{
14 */
15
16 /**
17 * Represents counterpart of a CoreObject that is meant to be used specifically on the core thread.
18 *
19 * @note Core thread only.
20 * @note Different CoreObject implementations should implement this class for their own needs.
21 */
22 class BS_CORE_EXPORT CoreObject
23 {
24 protected:
25 /** Values that represent current state of the object */
26 enum Flags
27 {
28 CGCO_INITIALIZED = 0x01, /**< Object has been initialized and can be used. */
29 CGCO_SCHEDULED_FOR_INIT = 0x02 /**< Object has been scheduled for initialization but core thread has not completed it yet. */
30 };
31
32 public:
33 CoreObject();
34 virtual ~CoreObject();
35
36 /** Called on the core thread when the object is first created. */
37 virtual void initialize();
38
39 /** Returns a shared_ptr version of "this" pointer. */
40 SPtr<CoreObject> getThisPtr() const { return mThis.lock(); }
41
42 public: // ***** INTERNAL ******
43 /** @name Internal
44 * @{
45 */
46
47 /**
48 * Sets a shared this pointer to this object. This MUST be called immediately after construction.
49 *
50 * @note Called automatically by the factory creation methods so user should not call this manually.
51 */
52 void _setThisPtr(SPtr<CoreObject> ptrThis);
53
54 /** @} */
55
56 protected:
57 friend class CoreObjectManager;
58 friend class bs::CoreObjectManager;
59 friend class bs::CoreObject;
60
61 /**
62 * Update internal data from provided memory buffer that was populated with data from the sim thread.
63 *
64 * @note
65 * This generally happens at the start of a core thread frame. Data used was recorded on the previous sim thread
66 * frame.
67 */
68 virtual void syncToCore(const CoreSyncData& data) { }
69
70 /**
71 * Blocks the current thread until the resource is fully initialized.
72 *
73 * @note
74 * If you call this without calling initialize first a deadlock will occur. You should not call this from core thread.
75 */
76 void synchronize();
77
78 /**
79 * Returns true if the object has been properly initialized. Methods are not allowed to be called on the object
80 * until it is initialized.
81 */
82 bool isInitialized() const { return (mFlags & CGCO_INITIALIZED) != 0; }
83 bool isScheduledToBeInitialized() const { return (mFlags & CGCO_SCHEDULED_FOR_INIT) != 0; }
84
85 void setIsInitialized(bool initialized) { mFlags = initialized ? mFlags | CGCO_INITIALIZED : mFlags & ~CGCO_INITIALIZED; }
86 void setScheduledToBeInitialized(bool scheduled) { mFlags = scheduled ? mFlags | CGCO_SCHEDULED_FOR_INIT : mFlags & ~CGCO_SCHEDULED_FOR_INIT; }
87
88 volatile UINT8 mFlags;
89 std::weak_ptr<CoreObject> mThis;
90
91 static Signal mCoreGpuObjectLoadedCondition;
92 static Mutex mCoreGpuObjectLoadedMutex;
93 };
94
95 /** @} */
96 }
97}
98
99