-
Notifications
You must be signed in to change notification settings - Fork 2k
Commit
This commit does not belong to any branch on this repository, and may belong to a fork outside of the repository.
- Loading branch information
1 parent
cd90419
commit b523c5c
Showing
23 changed files
with
919 additions
and
11 deletions.
There are no files selected for viewing
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,50 @@ | ||
#include "DynamicLibrary.h" | ||
|
||
namespace cc { | ||
|
||
DynamicLibrary::~DynamicLibrary() { | ||
unload(); | ||
} | ||
|
||
bool DynamicLibrary::load() { | ||
#ifdef _WIN32 | ||
_handle = ::LoadLibraryExA(_libName.c_str(), nullptr, 0); | ||
#elif defined(__EMSCRIPTEN__) | ||
_handle = nullptr; | ||
#else | ||
_handle = dlopen(_libName.c_str(), RTLD_LOCAL | RTLD_LAZY); | ||
#endif | ||
return _handle != nullptr; | ||
} | ||
|
||
void DynamicLibrary::unload() { | ||
if (_handle != nullptr) { | ||
#ifdef _WIN32 | ||
::FreeLibrary(static_cast<HMODULE>(_handle)); | ||
#elif defined(__EMSCRIPTEN__) | ||
// do nothing | ||
#else | ||
dlclose(_handle); | ||
#endif | ||
_handle = nullptr; | ||
} | ||
} | ||
|
||
bool DynamicLibrary::isLoaded() const { | ||
return _handle != nullptr; | ||
} | ||
|
||
void* DynamicLibrary::getProcAddress(const std::string &key) const { | ||
if (_handle == nullptr) { | ||
return nullptr; | ||
} | ||
#ifdef _WIN32 | ||
return reinterpret_cast<void*>(::GetProcAddress(static_cast<HMODULE>(_handle), key.c_str())); | ||
#elif defined(__EMSCRIPTEN__) | ||
return nullptr; | ||
#else | ||
return dlsym(_handle, key.c_str()); | ||
#endif | ||
} | ||
|
||
} // namespace cc |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,30 @@ | ||
#pragma once | ||
|
||
#include "base/std/container/string.h" | ||
|
||
#ifdef _WIN32 | ||
#include <windows.h> | ||
#else | ||
#include <dlfcn.h> | ||
#endif | ||
|
||
|
||
namespace cc { | ||
|
||
class DynamicLibrary { | ||
public: | ||
explicit DynamicLibrary(ccstd::string name) : _libName(std::move(name)) {} | ||
~DynamicLibrary(); | ||
|
||
bool load(); | ||
void unload(); | ||
bool isLoaded() const; | ||
|
||
void* getProcAddress(const std::string &key) const; | ||
|
||
private: | ||
std::string _libName; | ||
void *_handle = nullptr; | ||
}; | ||
|
||
} // namespace cc |
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
61 changes: 61 additions & 0 deletions
61
native/cocos/renderer/gfx-gles-common/common/GLESCommandStorage.cpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,61 @@ | ||
#include "GLESCommandStorage.h" | ||
#include "base/Utils.h" | ||
|
||
namespace cc::gfx { | ||
|
||
uint8_t *GLESCommandStorage::BlockStorage::allocate(uint32_t size, uint32_t alignment) { | ||
auto alignSize = utils::alignTo(size, alignment); | ||
if (!storage) { | ||
storage = std::make_unique<uint8_t[]>(blockSize); | ||
} | ||
|
||
if (offset + alignSize > blockSize) { | ||
return nullptr; | ||
} | ||
uint8_t *res = storage.get() + offset; | ||
offset += size; | ||
return res; | ||
} | ||
|
||
void GLESCommandStorage::BlockStorage::reset() { | ||
offset = 0; | ||
} | ||
|
||
void GLESCommandStorage::allocateStorage() { | ||
auto storage = std::make_unique<BlockStorage>(); | ||
storage->offset = 0; | ||
storage->blockSize = DEFAULT_BLOCK_SIZE; | ||
_iterator = _storages.emplace(_iterator, std::move(storage)); | ||
} | ||
|
||
void GLESCommandStorage::reset() { | ||
for (auto &storage : _storages) { | ||
storage->reset(); | ||
} | ||
_iterator = _storages.begin(); | ||
_head = nullptr; | ||
_current = &_head; | ||
} | ||
|
||
void GLESCommandStorage::execute() { | ||
while (_head != nullptr) { | ||
auto *ptr = _head->next; | ||
_head->execute(); | ||
_head->~CmdBase(); | ||
_head = ptr; | ||
} | ||
} | ||
|
||
uint8_t* GLESCommandStorage::allocate(uint32_t size, uint32_t alignment) { | ||
uint8_t *ptr = (*_iterator)->allocate(size, alignment); | ||
if (ptr == nullptr) { | ||
_iterator++; | ||
if (_iterator == _storages.end()) { | ||
allocateStorage(); | ||
} | ||
ptr = (*_iterator)->allocate(size, alignment); | ||
} | ||
return ptr; | ||
} | ||
|
||
} // namespace cc::gfx |
76 changes: 76 additions & 0 deletions
76
native/cocos/renderer/gfx-gles-common/common/GLESCommandStorage.h
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,76 @@ | ||
#pragma once | ||
|
||
#include <memory> | ||
#include <tuple> | ||
#include <base/std/container/list.h> | ||
|
||
namespace cc::gfx { | ||
|
||
struct CmdBase { | ||
CmdBase() = default; | ||
virtual ~CmdBase() = default; | ||
virtual void execute() {}; | ||
CmdBase* next = nullptr; | ||
}; | ||
|
||
template <typename Func, typename ...Args> | ||
struct Cmd : public CmdBase { | ||
using Parameters = std::tuple<std::remove_reference_t<Args>...>; | ||
using FuncType = Func; | ||
|
||
explicit Cmd(Func &&f, Args &&...args) : func(f), params(std::forward<Args>(args)...) {} | ||
|
||
FuncType func; | ||
Parameters params; | ||
|
||
void execute() override { | ||
std::apply(func, params); | ||
} | ||
}; | ||
|
||
|
||
class GLESCommandStorage { | ||
public: | ||
GLESCommandStorage() = default; | ||
~GLESCommandStorage() = default; | ||
|
||
static constexpr uint32_t DEFAULT_ALIGNMENT = 4; | ||
static constexpr uint32_t DEFAULT_BLOCK_SIZE = 1 * 1024 * 1024; // 1M | ||
|
||
uint8_t* allocate(uint32_t size, uint32_t alignment = DEFAULT_ALIGNMENT); | ||
void reset(); | ||
void execute(); | ||
|
||
template <typename Func, typename ...Args> | ||
void enqueueCmd(Func &&func, Args &&...args) | ||
{ | ||
using CmdType = Cmd<Func, Args...>; | ||
uint8_t *ptr = allocate(sizeof(CmdType)); | ||
auto *cmd = new (ptr) CmdType(std::forward<Func>(func), std::forward<Args>(args)...); | ||
|
||
(*_current) = cmd; | ||
_current = &(cmd->next); | ||
} | ||
|
||
struct BlockStorage { | ||
uint32_t blockSize = 0; | ||
uint32_t offset = 0; | ||
std::unique_ptr<uint8_t[]> storage; | ||
|
||
uint8_t *allocate(uint32_t size, uint32_t alignment); | ||
void reset(); | ||
}; | ||
|
||
private: | ||
void allocateStorage(); | ||
|
||
using StoragePtr = std::unique_ptr<BlockStorage>; | ||
using Iterator = std::list<StoragePtr>::iterator; | ||
|
||
ccstd::list<StoragePtr> _storages; | ||
Iterator _iterator = _storages.end(); | ||
CmdBase* _head = nullptr; | ||
CmdBase** _current = &_head; | ||
}; | ||
|
||
} // namespace cc::gfx |
56 changes: 56 additions & 0 deletions
56
native/cocos/renderer/gfx-gles-common/common/GLESQueue.cpp
This file contains bidirectional Unicode text that may be interpreted or compiled differently than what appears below. To review, open the file in an editor that reveals hidden Unicode characters.
Learn more about bidirectional Unicode characters
Original file line number | Diff line number | Diff line change |
---|---|---|
@@ -0,0 +1,56 @@ | ||
#include "GLESQueue.h" | ||
|
||
namespace cc::gfx { | ||
|
||
bool GLESQueue::hasComplete(TaskHandle taskId) { | ||
return _lastTaskId.load() >= taskId; | ||
} | ||
|
||
void GLESQueue::wait(TaskHandle taskId) { | ||
std::unique_lock<std::mutex> lock(_mutex); | ||
_taskCv.wait(lock, [=]() {return hasComplete(taskId); }); | ||
} | ||
|
||
void GLESQueue::waitIdle() { | ||
auto task = queueTask([](){}); | ||
wait(task); | ||
} | ||
|
||
void GLESQueue::threadMain() { | ||
while (!_exit.load()) { | ||
if (!runTask()) { | ||
std::unique_lock<std::mutex> lock(_mutex); | ||
while (!_exit.load() && !hasTask()) { | ||
_cv.wait(lock); | ||
} | ||
} | ||
} | ||
} | ||
|
||
bool GLESQueue::runTask() { | ||
ccstd::vector<Task> tasks; | ||
{ | ||
std::lock_guard<std::mutex> const lock(_taskMutex); | ||
if (_taskQueue.empty()) { | ||
return false; | ||
} | ||
tasks.swap(_taskQueue); | ||
} | ||
for (auto &task : tasks) { | ||
task.func(); | ||
_lastTaskId.store(task.taskId); | ||
{ | ||
std::unique_lock<std::mutex> const lock(_mutex); | ||
_taskCv.notify_all(); | ||
} | ||
} | ||
|
||
return true; | ||
} | ||
|
||
bool GLESQueue::hasTask() { | ||
std::lock_guard<std::mutex> const lock(_taskMutex); | ||
return !_taskQueue.empty(); | ||
} | ||
|
||
} // namespace cc::gfx |
Oops, something went wrong.