1f25ce65dSSergey Makeev // The MIT License (MIT) 2f25ce65dSSergey Makeev // 3f25ce65dSSergey Makeev // Copyright (c) 2015 Sergey Makeev, Vadim Slyusarev 4f25ce65dSSergey Makeev // 5f25ce65dSSergey Makeev // Permission is hereby granted, free of charge, to any person obtaining a copy 6f25ce65dSSergey Makeev // of this software and associated documentation files (the "Software"), to deal 7f25ce65dSSergey Makeev // in the Software without restriction, including without limitation the rights 8f25ce65dSSergey Makeev // to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9f25ce65dSSergey Makeev // copies of the Software, and to permit persons to whom the Software is 10f25ce65dSSergey Makeev // furnished to do so, subject to the following conditions: 11f25ce65dSSergey Makeev // 12f25ce65dSSergey Makeev // The above copyright notice and this permission notice shall be included in 13f25ce65dSSergey Makeev // all copies or substantial portions of the Software. 14f25ce65dSSergey Makeev // 15f25ce65dSSergey Makeev // THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16f25ce65dSSergey Makeev // IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17f25ce65dSSergey Makeev // FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18f25ce65dSSergey Makeev // AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19f25ce65dSSergey Makeev // LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20f25ce65dSSergey Makeev // OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN 21f25ce65dSSergey Makeev // THE SOFTWARE. 22f25ce65dSSergey Makeev 2358964d0bSSergey Makeev #pragma once 2458964d0bSSergey Makeev 2558964d0bSSergey Makeev #include <MTTools.h> 2658964d0bSSergey Makeev #include <MTPlatform.h> 2758964d0bSSergey Makeev #include <MTTaskBucket.h> 2858964d0bSSergey Makeev 293a3d248dSs.makeev_local #ifdef Yield 303a3d248dSs.makeev_local #undef Yield 313a3d248dSs.makeev_local #endif 323a3d248dSs.makeev_local 3358964d0bSSergey Makeev 3458964d0bSSergey Makeev namespace MT 3558964d0bSSergey Makeev { 3658d12dadSSergey Makeev class TaskHandle; 3758d12dadSSergey Makeev 3858964d0bSSergey Makeev //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 3958964d0bSSergey Makeev // Fiber task status 4058964d0bSSergey Makeev //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 4158964d0bSSergey Makeev // Task can be completed for several reasons. 4258964d0bSSergey Makeev // For example task was done or someone call Yield from the Task body. 4358964d0bSSergey Makeev namespace FiberTaskStatus 4458964d0bSSergey Makeev { 4558964d0bSSergey Makeev enum Type 4658964d0bSSergey Makeev { 4758964d0bSSergey Makeev UNKNOWN = 0, 4858964d0bSSergey Makeev RUNNED = 1, 4958964d0bSSergey Makeev FINISHED = 2, 503a3d248dSs.makeev_local YIELDED = 3, 5158964d0bSSergey Makeev AWAITING_CHILD = 4, 5258964d0bSSergey Makeev }; 5358964d0bSSergey Makeev } 5458964d0bSSergey Makeev 5558964d0bSSergey Makeev //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 5658964d0bSSergey Makeev // Fiber context 5758964d0bSSergey Makeev //////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////////// 5858964d0bSSergey Makeev // Context passed to fiber main function 5958964d0bSSergey Makeev class FiberContext 6058964d0bSSergey Makeev { 6158964d0bSSergey Makeev private: 6258964d0bSSergey Makeev 6356aa031bSSergey Makeev void RunSubtasksAndYieldImpl(ArrayView<internal::TaskBucket>& buckets); 6458964d0bSSergey Makeev 6558964d0bSSergey Makeev public: 6658964d0bSSergey Makeev 6758964d0bSSergey Makeev FiberContext(); 6858964d0bSSergey Makeev 6958964d0bSSergey Makeev template<class TTask> 70806ef292SSergey Makeev void RunSubtasksAndYield(TaskGroup taskGroup, const TTask* taskArray, size_t taskCount); 7158964d0bSSergey Makeev 7258964d0bSSergey Makeev template<class TTask> 73f4db079dSs.makeev void RunAsync(TaskGroup taskGroup, const TTask* taskArray, size_t taskCount); 7458964d0bSSergey Makeev 7558d12dadSSergey Makeev // 76f4db079dSs.makeev void RunAsync(TaskGroup taskGroup, const TaskHandle* taskHandleArray, uint32 taskHandleCount); 77f4db079dSs.makeev void RunSubtasksAndYield(TaskGroup taskGroup, const TaskHandle* taskHandleArray, uint32 taskHandleCount); 7858d12dadSSergey Makeev 793a3d248dSs.makeev_local // 803a3d248dSs.makeev_local void Yield(); 813a3d248dSs.makeev_local 8258964d0bSSergey Makeev void Reset(); 8358964d0bSSergey Makeev 8458964d0bSSergey Makeev void SetThreadContext(internal::ThreadContext * _threadContext); 8558964d0bSSergey Makeev internal::ThreadContext* GetThreadContext(); 8658964d0bSSergey Makeev 8758964d0bSSergey Makeev void SetStatus(FiberTaskStatus::Type _taskStatus); 8858964d0bSSergey Makeev FiberTaskStatus::Type GetStatus() const; 8958964d0bSSergey Makeev 9058964d0bSSergey Makeev private: 9158964d0bSSergey Makeev 9258964d0bSSergey Makeev // Active thread context (null if fiber context is not executing now) 9358964d0bSSergey Makeev internal::ThreadContext * threadContext; 9458964d0bSSergey Makeev 9558964d0bSSergey Makeev // Active task status 9658964d0bSSergey Makeev FiberTaskStatus::Type taskStatus; 9758964d0bSSergey Makeev 9858964d0bSSergey Makeev public: 9958964d0bSSergey Makeev 10058964d0bSSergey Makeev // Active task attached to this fiber 10158964d0bSSergey Makeev internal::TaskDesc currentTask; 10258964d0bSSergey Makeev 10358964d0bSSergey Makeev // Active task group 104806ef292SSergey Makeev TaskGroup currentGroup; 10558964d0bSSergey Makeev 106f4db079dSs.makeev // Requirements for stack 107f4db079dSs.makeev StackRequirements::Type stackRequirements; 108f4db079dSs.makeev 10958964d0bSSergey Makeev // Number of children fibers 110721f8c0bSs.makeev_local Atomic32<int32> childrenFibersCount; 11158964d0bSSergey Makeev 11258964d0bSSergey Makeev // Parent fiber 11358964d0bSSergey Makeev FiberContext* parentFiber; 11458964d0bSSergey Makeev 11558964d0bSSergey Makeev // System fiber 11658964d0bSSergey Makeev Fiber fiber; 11758964d0bSSergey Makeev 118*9c716f68Ss.makeev_local //Fiber index in pool 119*9c716f68Ss.makeev_local uint32 fiberIndex; 120*9c716f68Ss.makeev_local 12158964d0bSSergey Makeev // Prevent false sharing between threads 12258964d0bSSergey Makeev uint8 cacheline[64]; 12358964d0bSSergey Makeev }; 12458964d0bSSergey Makeev 12558964d0bSSergey Makeev 12658964d0bSSergey Makeev } 127