Skip to content

Commit

Permalink
[refactoring]gfx egl.
Browse files Browse the repository at this point in the history
  • Loading branch information
bluesky013 committed Jul 27, 2023
1 parent cd90419 commit b523c5c
Show file tree
Hide file tree
Showing 23 changed files with 919 additions and 11 deletions.
25 changes: 20 additions & 5 deletions native/CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -461,6 +461,8 @@ cocos_source_files(
cocos/base/TypeDef.h
cocos/base/BinaryArchive.cpp
cocos/base/BinaryArchive.h
cocos/base/DynamicLibrary.cpp
cocos/base/DynamicLibrary.h
cocos/base/std/any.h
cocos/base/std/optional.h
cocos/base/std/variant.h
Expand Down Expand Up @@ -1612,14 +1614,27 @@ cocos_source_files(
# )

if(CC_USE_GLES2 OR CC_USE_GLES3)
cocos_source_files(
cocos/renderer/gfx-gles-common/common/GLESQueue.cpp
cocos/renderer/gfx-gles-common/common/GLESQueue.h
cocos/renderer/gfx-gles-common/common/GLESCommandStorage.cpp
cocos/renderer/gfx-gles-common/common/GLESCommandStorage.h
cocos/renderer/gfx-gles-common/egl/Context.cpp
cocos/renderer/gfx-gles-common/egl/Context.h
cocos/renderer/gfx-gles-common/egl/Surface.cpp
cocos/renderer/gfx-gles-common/egl/Surface.h
cocos/renderer/gfx-gles-common/egl/Instance.cpp
cocos/renderer/gfx-gles-common/egl/Instance.h
)

cocos_source_files(
cocos/renderer/gfx-gles-common/GLESCommandPool.h
cocos/renderer/gfx-gles-common/eglw.cpp
cocos/renderer/gfx-gles-common/gles2w.cpp
cocos/renderer/gfx-gles-common/loader/eglw.cpp
cocos/renderer/gfx-gles-common/loader/gles2w.cpp
)
if(CC_USE_GLES3)
cocos_source_files(
cocos/renderer/gfx-gles-common/gles3w.cpp
cocos/renderer/gfx-gles-common/loader/gles3w.cpp
)
endif()
endif()
Expand Down Expand Up @@ -2374,7 +2389,7 @@ if(USE_MIDDLEWARE)
NO_WERROR cocos/editor-support/spine-creator-support/spine-cocos2dx.cpp
cocos/editor-support/spine-creator-support/spine-cocos2dx.h
NO_WERROR cocos/editor-support/spine-creator-support/VertexEffectDelegate.cpp
cocos/editor-support/spine-creator-support/VertexEffectDelegate.h
cocos/editor-support/spine-creator-support/VertexEffectDelegate.h

)
cocos_source_files(
Expand Down Expand Up @@ -3327,7 +3342,7 @@ set(COCOS_SOURCE_LIST_EXCLUDE_GENRATED ${COCOS_SOURCE_LIST})
set(COCOS_GENERATED_LIST)
foreach(src IN LISTS COCOS_SOURCE_LIST_EXCLUDE_GENRATED)
get_source_file_property(IS_GENERATED ${src} GENERATED)
if(IS_GENERATED)
if(IS_GENERATED)
list(REMOVE_ITEM COCOS_SOURCE_LIST_EXCLUDE_GENRATED ${src})
list(APPEND COCOS_GENERATED_LIST ${src})
endif()
Expand Down
50 changes: 50 additions & 0 deletions native/cocos/base/DynamicLibrary.cpp
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
30 changes: 30 additions & 0 deletions native/cocos/base/DynamicLibrary.h
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
2 changes: 1 addition & 1 deletion native/cocos/platform/java/modules/XRInterface.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -45,7 +45,7 @@
#include "gfx-vulkan/VKDevice.h"
#endif
#ifdef CC_USE_GLES3
#include "gfx-gles-common/gles3w.h"
#include "gfx-gles-common/loader/gles3w.h"
#include "gfx-gles3/GLES3Device.h"
#include "renderer/gfx-gles3/GLES3GPUObjects.h"
#endif
Expand Down
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 native/cocos/renderer/gfx-gles-common/common/GLESCommandStorage.h
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 native/cocos/renderer/gfx-gles-common/common/GLESQueue.cpp
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
Loading

0 comments on commit b523c5c

Please sign in to comment.