Skip to content

Commit

Permalink
Merge pull request #54 from AlwinEsch/change-interface
Browse files Browse the repository at this point in the history
Change to now C++ based addon interface
  • Loading branch information
AlwinEsch authored Oct 26, 2019
2 parents 961f2aa + c894eb4 commit 454457e
Show file tree
Hide file tree
Showing 50 changed files with 595 additions and 712 deletions.
12 changes: 7 additions & 5 deletions CMakeLists.txt
Original file line number Diff line number Diff line change
Expand Up @@ -4,15 +4,19 @@ project(game.libretro)
list(APPEND CMAKE_MODULE_PATH ${PROJECT_SOURCE_DIR})

find_package(Kodi REQUIRED)
find_package(p8-platform REQUIRED)
find_package(TinyXML REQUIRED)

include_directories(${KODI_INCLUDE_DIR}
${p8-platform_INCLUDE_DIRS}
${PROJECT_SOURCE_DIR}/src
${TINYXML_INCLUDE_DIRS})

list(APPEND DEPLIBS ${p8-platform_LIBRARIES} ${TINYXML_LIBRARIES})
list(APPEND DEPLIBS ${TINYXML_LIBRARIES})

if(WIN32)
find_package(dlfcn-win32 REQUIRED)
list(APPEND DEPLIBS ${dlfcn-win32_LIBRARIES})
include_directories(${dlfcn-win32_INCLUDE_DIRS})
endif()

set(LIBRETRO_SOURCES src/client.cpp
src/audio/AudioStream.cpp
Expand Down Expand Up @@ -41,7 +45,6 @@ set(LIBRETRO_SOURCES src/client.cpp
src/settings/LibretroSettings.cpp
src/settings/Settings.cpp
src/settings/SettingsGenerator.cpp
src/utils/PathUtils.cpp
src/utils/Timer.cpp
src/video/VideoGeometry.cpp
src/video/VideoStream.cpp)
Expand Down Expand Up @@ -80,7 +83,6 @@ set(LIBRETRO_HEADERS src/GameInfoLoader.h
src/settings/SettingsGenerator.h
src/settings/Settings.h
src/settings/SettingsTypes.h
src/utils/PathUtils.h
src/utils/Timer.h
src/video/VideoGeometry.h
src/video/VideoStream.h)
Expand Down
24 changes: 1 addition & 23 deletions Readme.md
Original file line number Diff line number Diff line change
Expand Up @@ -80,29 +80,7 @@ When developing, compiling from a git repo is more convenient than repeatedly pu

### Developing on Linux

The add-on requires several dependencies to build properly. Like Kodi's build system, you can perform a system install or a local one (demonstrated here).

First, clone p8-platform and build per standard CMake:

```shell
git clone https://github.com/Pulse-Eight/platform.git
cd platform
mkdir build
cd build
cmake -DCMAKE_BUILD_TYPE=Debug \
-DCMAKE_INSTALL_PREFIX=$HOME/kodi \
..
make
make install
```

The kodi-platform library was split from p8-platform. Do the same as above for this library:

```
git clone https://github.com/xbmc/kodi-platform.git
cd kodi-platform
...
```
The add-on requires several dependencies to build properly. Like Kodi's build system, you can perform a system install or a local one.

With these dependencies in place, the add-on can be built:

Expand Down
26 changes: 26 additions & 0 deletions depends/windows/dlfcn-win32/0001-dlopen_with_widechar.patch
Original file line number Diff line number Diff line change
@@ -0,0 +1,26 @@
diff --git a/dlfcn.c b/dlfcn.c
index 69670d1..8d2dbc0 100644
--- a/dlfcn.c
+++ b/dlfcn.c
@@ -264,8 +264,19 @@ void *dlopen( const char *file, int mode )
* to UNIX's search paths (start with system folders instead of current
* folder).
*/
- hModule = LoadLibraryExA(lpFileName, NULL,
- LOAD_WITH_ALTERED_SEARCH_PATH );
+ int wide_len = MultiByteToWideChar(CP_UTF8, 0, lpFileName, -1, 0, 0);
+ if (wide_len > 0)
+ {
+ wchar_t* lpFileNameW = (wchar_t*)malloc(wide_len * sizeof(wchar_t));
+ MultiByteToWideChar(CP_UTF8, 0, lpFileName, -1, lpFileNameW, wide_len);
+
+ hModule = LoadLibraryExW(lpFileNameW, NULL,
+ LOAD_WITH_ALTERED_SEARCH_PATH );
+
+ free(lpFileNameW);
+ }
+ else
+ hModule = 0;

if( MyEnumProcessModules( hCurrentProc, NULL, 0, &dwProcModsAfter ) == 0 )
dwProcModsAfter = 0;
1 change: 1 addition & 0 deletions depends/windows/dlfcn-win32/dlfcn-win32.sha256
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
f18a412e84d8b701e61a78252411fe8c72587f52417c1ef21ca93604de1b9c55
1 change: 1 addition & 0 deletions depends/windows/dlfcn-win32/dlfcn-win32.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
dlfcn-win32 https://github.com/dlfcn-win32/dlfcn-win32/archive/v1.2.0.tar.gz
1 change: 1 addition & 0 deletions depends/windows/dlfcn-win32/flags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
-DBUILD_SHARED_LIBS=OFF
151 changes: 151 additions & 0 deletions depends/windowsstore/dlfcn-win32/0001-win10-fixed-uwp-build.patch
Original file line number Diff line number Diff line change
@@ -0,0 +1,151 @@
From f85366b1044fff7b4ea9162c3edcd8278c3e06ff Mon Sep 17 00:00:00 2001
From: Alwin Esch <[email protected]>
Date: Thu, 22 Aug 2019 19:30:12 +0100
Subject: [PATCH] [win10] fixed uwp build

---
dlfcn.c | 43 ++++++++++++++++++++++++++++++++++++++-----
1 file changed, 38 insertions(+), 5 deletions(-)

diff --git a/dlfcn.c b/dlfcn.c
index 69670d1..2d77ca8 100644
--- a/dlfcn.c
+++ b/dlfcn.c
@@ -19,6 +19,7 @@
* Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
*/

+#define _CRT_SECURE_NO_WARNINGS
#ifdef _DEBUG
#define _CRTDBG_MAP_ALLOC
#include <stdlib.h>
@@ -193,6 +194,7 @@ static void save_err_ptr_str( const void *ptr )
/* Load Psapi.dll at runtime, this avoids linking caveat */
static BOOL MyEnumProcessModules( HANDLE hProcess, HMODULE *lphModule, DWORD cb, LPDWORD lpcbNeeded )
{
+#if !defined(WINAPI_FAMILY) || (WINAPI_FAMILY != WINAPI_FAMILY_APP)
static BOOL (WINAPI *EnumProcessModulesPtr)(HANDLE, HMODULE *, DWORD, LPDWORD);
HMODULE psapi;

@@ -206,20 +208,26 @@ static BOOL MyEnumProcessModules( HANDLE hProcess, HMODULE *lphModule, DWORD cb,
}

return EnumProcessModulesPtr( hProcess, lphModule, cb, lpcbNeeded );
+#else
+ return 0;
+#endif
}

void *dlopen( const char *file, int mode )
{
- HMODULE hModule;
- UINT uMode;
+ HMODULE hModule = NULL;
+ UINT uMode = 0;

current_error = NULL;

/* Do not let Windows display the critical-error-handler message box */
+#if !defined(WINAPI_FAMILY) || (WINAPI_FAMILY != WINAPI_FAMILY_APP)
uMode = SetErrorMode( SEM_FAILCRITICALERRORS );
+#endif

if( file == 0 )
{
+#if !defined(WINAPI_FAMILY) || (WINAPI_FAMILY != WINAPI_FAMILY_APP) // what is replacement of GMH on UWP?
/* POSIX says that if the value of file is 0, a handle on a global
* symbol object must be provided. That object must be able to access
* all symbols from the original program file, and any objects loaded
@@ -234,6 +242,7 @@ void *dlopen( const char *file, int mode )

if( !hModule )
save_err_ptr_str( file );
+#endif
}
else
{
@@ -264,11 +273,29 @@ void *dlopen( const char *file, int mode )
* to UNIX's search paths (start with system folders instead of current
* folder).
*/
+#if defined(WINAPI_FAMILY) && (WINAPI_FAMILY == WINAPI_FAMILY_APP)
+ int result = MultiByteToWideChar(CP_UTF8, MB_ERR_INVALID_CHARS, lpFileName, strlen(lpFileName), NULL, 0);
+ if (result == 0)
+ return NULL;
+
+ wchar_t* newStr = (wchar_t*)malloc(result*sizeof(wchar_t));
+ result = MultiByteToWideChar( CP_UTF8, MB_ERR_INVALID_CHARS, lpFileName, strlen(lpFileName), newStr, result );
+ if (result == 0)
+ {
+ free( newStr );
+ return NULL;
+ }
+
+ hModule = LoadPackagedLibrary( newStr, 0 );
+ free( newStr );
+ dwProcModsAfter = 0;
+#else // WINAPI_PARTITION_DESKTOP
hModule = LoadLibraryExA(lpFileName, NULL,
LOAD_WITH_ALTERED_SEARCH_PATH );

if( MyEnumProcessModules( hCurrentProc, NULL, 0, &dwProcModsAfter ) == 0 )
dwProcModsAfter = 0;
+#endif

/* If the object was loaded with RTLD_LOCAL, add it to list of local
* objects, so that its symbols cannot be retrieved even if the handle for
@@ -288,7 +315,9 @@ void *dlopen( const char *file, int mode )
}

/* Return to previous state of the error-mode bit flags. */
+#if !defined(WINAPI_FAMILY) || (WINAPI_FAMILY != WINAPI_FAMILY_APP)
SetErrorMode( uMode );
+#endif

return (void *) hModule;
}
@@ -321,12 +350,14 @@ void *dlsym( void *handle, const char *name )
{
FARPROC symbol;
HMODULE hCaller;
- HMODULE hModule;
- HANDLE hCurrentProc;
+ HMODULE hModule = 0;
+ HANDLE hCurrentProc = 0;

current_error = NULL;
symbol = NULL;
hCaller = NULL;
+
+#if !defined(WINAPI_FAMILY) || (WINAPI_FAMILY != WINAPI_FAMILY_APP) // what is replacement of GMH on UWP?
hModule = GetModuleHandle( NULL );
hCurrentProc = GetCurrentProcess( );

@@ -358,6 +389,7 @@ void *dlsym( void *handle, const char *name )
if(!hCaller)
goto end;
}
+#endif

if( handle != RTLD_NEXT )
{
@@ -370,7 +402,7 @@ void *dlsym( void *handle, const char *name )
/* If the handle for the original program file is passed, also search
* in all globally loaded objects.
*/
-
+#if !defined(WINAPI_FAMILY) || (WINAPI_FAMILY != WINAPI_FAMILY_APP)
if( hModule == handle || handle == RTLD_NEXT )
{
HMODULE *modules;
@@ -410,6 +442,7 @@ void *dlsym( void *handle, const char *name )
}
}
}
+#endif

end:
if( symbol == NULL )
--
2.19.2.windows.1

1 change: 1 addition & 0 deletions depends/windowsstore/dlfcn-win32/dlfcn-win32.sha256
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
f18a412e84d8b701e61a78252411fe8c72587f52417c1ef21ca93604de1b9c55
1 change: 1 addition & 0 deletions depends/windowsstore/dlfcn-win32/dlfcn-win32.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
dlfcn-win32 https://github.com/dlfcn-win32/dlfcn-win32/archive/v1.2.0.tar.gz
1 change: 1 addition & 0 deletions depends/windowsstore/dlfcn-win32/flags.txt
Original file line number Diff line number Diff line change
@@ -0,0 +1 @@
-DBUILD_SHARED_LIBS=OFF
2 changes: 1 addition & 1 deletion game.libretro/addon.xml.in
Original file line number Diff line number Diff line change
@@ -1,7 +1,7 @@
<?xml version="1.0" encoding="UTF-8" standalone="yes"?>
<addon id="game.libretro"
name="Libretro Compatibility"
version="1.1.0"
version="2.0.0"
provider-name="Team Kodi">
<backwards-compatibility abi="1.0.0"/>
<requires>@ADDON_DEPENDS@</requires>
Expand Down
23 changes: 10 additions & 13 deletions src/GameInfoLoader.cpp
Original file line number Diff line number Diff line change
Expand Up @@ -21,19 +21,17 @@
#include "GameInfoLoader.h"
#include "log/Log.h"

#include "libXBMC_addon.h"
#include <kodi/Filesystem.h>

#include <stdint.h>

using namespace ADDON;
using namespace LIBRETRO;

#define READ_SIZE (100 * 1024) // Read from VFS 100KB at a time (if file size is unknown)
#define MAX_READ_SIZE (100 * 1024 * 1024) // Read at most 100MB from VFS

CGameInfoLoader::CGameInfoLoader(const char* path, CHelper_libXBMC_addon* XBMC, bool bSupportsVFS)
CGameInfoLoader::CGameInfoLoader(const std::string& path, bool bSupportsVFS)
: m_path(path),
m_xbmc(XBMC),
m_bSupportsVfs(bSupportsVFS)
{
}
Expand All @@ -43,14 +41,13 @@ bool CGameInfoLoader::Load(void)
if (!m_bSupportsVfs)
return false;

struct __stat64 statStruct = { };

bool bExists = (m_xbmc->StatFile(m_path.c_str(), &statStruct) == 0);
STAT_STRUCTURE statStruct = {0};
bool bExists = kodi::vfs::StatFile(m_path, statStruct);

// Not all VFS protocols necessarily support StatFile(), so also check if file exists
if (!bExists)
{
bExists = m_xbmc->FileExists(m_path.c_str(), true);
bExists = kodi::vfs::FileExists(m_path, true);
if (bExists)
{
dsyslog("Failed to stat (but file exists): %s", m_path.c_str());
Expand All @@ -62,21 +59,21 @@ bool CGameInfoLoader::Load(void)
}
}

void* file = m_xbmc->OpenFile(m_path.c_str(), 0);
if (!file)
kodi::vfs::CFile file;
if (!file.OpenFile(m_path))
{
esyslog("Failed to open file: %s", m_path.c_str());
return false;
}

int64_t size = statStruct.st_size;
int64_t size = statStruct.size;
if (size > 0)
{
// Size is known, read entire file at once (unless it is too big)
if (size <= MAX_READ_SIZE)
{
m_dataBuffer.resize((size_t)size);
m_xbmc->ReadFile(file, m_dataBuffer.data(), size);
file.Read(m_dataBuffer.data(), size);
}
else
{
Expand All @@ -90,7 +87,7 @@ bool CGameInfoLoader::Load(void)
// Read file in chunks
unsigned int bytesRead;
uint8_t buffer[READ_SIZE];
while ((bytesRead = m_xbmc->ReadFile(file, buffer, sizeof(buffer))) > 0)
while ((bytesRead = file.Read(buffer, sizeof(buffer))) > 0)
{
m_dataBuffer.insert(m_dataBuffer.end(), buffer, buffer + bytesRead);

Expand Down
5 changes: 1 addition & 4 deletions src/GameInfoLoader.h
Original file line number Diff line number Diff line change
Expand Up @@ -25,8 +25,6 @@
#include <string>
#include <vector>

namespace ADDON { class CHelper_libXBMC_addon; }

namespace LIBRETRO
{
/*!
Expand All @@ -39,7 +37,7 @@ namespace LIBRETRO
class CGameInfoLoader
{
public:
CGameInfoLoader(const char* path, ADDON::CHelper_libXBMC_addon* XBMC, bool bSupportsVFS);
CGameInfoLoader(const std::string& path, bool bSupportsVFS);

bool Load(void);

Expand All @@ -58,7 +56,6 @@ namespace LIBRETRO

private:
const std::string m_path;
ADDON::CHelper_libXBMC_addon* const m_xbmc;
const bool m_bSupportsVfs;
std::vector<uint8_t> m_dataBuffer;
};
Expand Down
Loading

0 comments on commit 454457e

Please sign in to comment.