diff options
33 files changed, 70 insertions, 1627 deletions
diff --git a/.ci/yuzu-mainline-step1.yml b/.ci/yuzu-mainline-step1.yml index 3fd33d75a..6b6acb5c6 100644 --- a/.ci/yuzu-mainline-step1.yml +++ b/.ci/yuzu-mainline-step1.yml @@ -1,6 +1,9 @@ trigger: - master +pool: + vmImage: 'ubuntu-latest' + stages: - stage: merge displayName: 'merge' diff --git a/.ci/yuzu-patreon-step1.yml b/.ci/yuzu-patreon-step1.yml index cf30397cd..c63d7a066 100644 --- a/.ci/yuzu-patreon-step1.yml +++ b/.ci/yuzu-patreon-step1.yml @@ -1,6 +1,9 @@ trigger: - master +pool: + vmImage: 'ubuntu-latest' + stages: - stage: merge displayName: 'merge' diff --git a/.gitmodules b/.gitmodules index 749cd0408..dc6ed500f 100644 --- a/.gitmodules +++ b/.gitmodules @@ -28,9 +28,6 @@ [submodule "mbedtls"] path = externals/mbedtls url = https://github.com/yuzu-emu/mbedtls -[submodule "libzip"] - path = externals/libzip/libzip - url = https://github.com/nih-at/libzip.git [submodule "xbyak"] path = externals/xbyak url = https://github.com/herumi/xbyak.git diff --git a/CMakeLists.txt b/CMakeLists.txt index b7ea86d8a..bd0f6b978 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -29,16 +29,10 @@ option(YUZU_USE_BUNDLED_FFMPEG "Download/Build bundled FFmpeg" "${WIN32}") option(YUZU_USE_QT_WEB_ENGINE "Use QtWebEngine for web applet implementation" OFF) -option(YUZU_ENABLE_BOXCAT "Enable the Boxcat service, a yuzu high-level implementation of BCAT" ON) - option(ENABLE_CUBEB "Enables the cubeb audio backend" ON) option(USE_DISCORD_PRESENCE "Enables Discord Rich Presence" OFF) -if (NOT ENABLE_WEB_SERVICE) - set(YUZU_ENABLE_BOXCAT OFF) -endif() - # Default to a Release build get_property(IS_MULTI_CONFIG GLOBAL PROPERTY GENERATOR_IS_MULTI_CONFIG) if (NOT IS_MULTI_CONFIG AND NOT CMAKE_BUILD_TYPE) @@ -422,11 +416,6 @@ if (CONAN_REQUIRED_LIBS) endif() include(${CMAKE_BINARY_DIR}/conan.cmake) - set(CONAN_LIB_OPTIONS - libzip:with_openssl=False - libzip:enable_windows_crypto=False - ) - conan_check(VERSION 1.24.0 REQUIRED) # Manually add iconv to fix a dep conflict between qt and sdl2 diff --git a/externals/CMakeLists.txt b/externals/CMakeLists.txt index 0c2c059a9..a76a3d800 100644 --- a/externals/CMakeLists.txt +++ b/externals/CMakeLists.txt @@ -93,13 +93,6 @@ endif() # Sirit add_subdirectory(sirit) -# libzip -find_package(libzip 1.5) -if (NOT libzip_FOUND) - message(STATUS "libzip 1.5 or newer not found, falling back to externals") - add_subdirectory(libzip EXCLUDE_FROM_ALL) -endif() - if (ENABLE_WEB_SERVICE) find_package(OpenSSL 1.1) if (OPENSSL_FOUND) diff --git a/externals/find-modules/Findlibzip.cmake b/externals/find-modules/Findlibzip.cmake deleted file mode 100644 index 8934de3b8..000000000 --- a/externals/find-modules/Findlibzip.cmake +++ /dev/null @@ -1,72 +0,0 @@ - -find_package(PkgConfig QUIET) -pkg_check_modules(PC_libzip QUIET libzip) - -find_path(libzip_INCLUDE_DIR - NAMES zip.h - PATHS ${PC_libzip_INCLUDE_DIRS} - "$ENV{LIB_DIR}/include" - "$ENV{INCLUDE}" - /usr/local/include - /usr/include -) -find_path(libzip_INCLUDE_DIR_ZIPCONF - NAMES zipconf.h - HINTS ${PC_libzip_INCLUDE_DIRS} - "$ENV{LIB_DIR}/include" - "$ENV{LIB_DIR}/lib/libzip/include" - "$ENV{LIB}/lib/libzip/include" - /usr/local/lib/libzip/include - /usr/lib/libzip/include - /usr/local/include - /usr/include - "$ENV{INCLUDE}" -) -find_library(libzip_LIBRARY - NAMES zip - PATHS ${PC_libzip_LIBRARY_DIRS} - "$ENV{LIB_DIR}/lib" "$ENV{LIB}" /usr/local/lib /usr/lib -) - -if (libzip_INCLUDE_DIR_ZIPCONF) - FILE(READ "${libzip_INCLUDE_DIR_ZIPCONF}/zipconf.h" _libzip_VERSION_CONTENTS) - if (_libzip_VERSION_CONTENTS) - STRING(REGEX REPLACE ".*#define LIBZIP_VERSION \"([0-9.]+)\".*" "\\1" libzip_VERSION "${_libzip_VERSION_CONTENTS}") - endif() - unset(_libzip_VERSION_CONTENTS) -endif() - -set(libzip_VERSION ${libzip_VERSION} CACHE STRING "Version number of libzip") - -include(FindPackageHandleStandardArgs) -find_package_handle_standard_args(libzip - FOUND_VAR libzip_FOUND - REQUIRED_VARS - libzip_LIBRARY - libzip_INCLUDE_DIR - libzip_INCLUDE_DIR_ZIPCONF - libzip_VERSION - VERSION_VAR libzip_VERSION -) - -if(libzip_FOUND) - set(libzip_LIBRARIES ${libzip_LIBRARY}) - set(libzip_INCLUDE_DIRS ${libzip_INCLUDE_DIR}) - set(libzip_DEFINITIONS ${PC_libzip_CFLAGS_OTHER}) -endif() - -if(libzip_FOUND AND NOT TARGET libzip::libzip) - add_library(libzip::libzip UNKNOWN IMPORTED) - set_target_properties(libzip::libzip PROPERTIES - IMPORTED_LOCATION "${libzip_LIBRARY}" - INTERFACE_COMPILE_OPTIONS "${PC_libzip_CFLAGS_OTHER}" - INTERFACE_INCLUDE_DIRECTORIES "${libzip_INCLUDE_DIR}" - ) -endif() - -mark_as_advanced( - libzip_INCLUDE_DIR - libzip_INCLUDE_DIR_ZIPCONF - libzip_LIBRARY - libzip_VERSION -) diff --git a/externals/libzip/CMakeLists.txt b/externals/libzip/CMakeLists.txt deleted file mode 100644 index ea5329fa0..000000000 --- a/externals/libzip/CMakeLists.txt +++ /dev/null @@ -1,564 +0,0 @@ -# TODO: -# create usable libtool .la file - -CMAKE_MINIMUM_REQUIRED(VERSION 3.0.2) - -LIST(APPEND CMAKE_MODULE_PATH "${CMAKE_CURRENT_SOURCE_DIR}/libzip") - -PROJECT(libzip C) - -OPTION(ENABLE_COMMONCRYPTO "Enable use of CommonCrypto" ON) -OPTION(ENABLE_GNUTLS "Enable use of GnuTLS" ON) -OPTION(ENABLE_MBEDTLS "Enable use of mbed TLS" ON) -OPTION(ENABLE_OPENSSL "Enable use of OpenSSL" ON) -OPTION(ENABLE_WINDOWS_CRYPTO "Enable use of Windows cryptography libraries" ON) - -OPTION(ENABLE_BZIP2 "Enable use of BZip2" OFF) -OPTION(ENABLE_LZMA "Enable use of LZMA" OFF) - -INCLUDE(CheckFunctionExists) -INCLUDE(CheckIncludeFiles) -INCLUDE(CheckSymbolExists) -INCLUDE(CheckTypeSize) -INCLUDE(CheckCSourceRuns) -INCLUDE(CheckCSourceCompiles) -INCLUDE(CheckStructHasMember) -INCLUDE(TestBigEndian) -INCLUDE(GNUInstallDirs) -IF(ENABLE_COMMONCRYPTO) - CHECK_INCLUDE_FILES(CommonCrypto/CommonCrypto.h COMMONCRYPTO_FOUND) -ELSE() - SET(COMMONCRYPTO_FOUND FALSE) -ENDIF() -IF(ENABLE_GNUTLS) - INCLUDE(FindNettle) - INCLUDE(FindGnuTLS) -ELSE() - SET(GNUTLS_FOUND FALSE) -ENDIF() -IF(ENABLE_MBEDTLS) - FIND_PATH(MBEDTLS_INCLUDE_DIR mbedtls/aes.h) - FIND_LIBRARY(MBEDTLS_LIBRARIES NAMES mbedcrypto) -ELSE() - SET(MBEDTLS_LIBRARIES FALSE) -ENDIF() -IF(ENABLE_OPENSSL) - INCLUDE(FindOpenSSL) -ELSE() - SET(OPENSSL_FOUND FALSE) -ENDIF() -IF(WIN32) - IF(ENABLE_WINDOWS_CRYPTO) - SET(WINDOWS_CRYPTO_FOUND TRUE) - ENDIF() -ELSE() - SET(WINDOWS_CRYPTO_FOUND FALSE) -ENDIF() - -OPTION(BUILD_SHARED_LIBS "Build shared libraries" ON) -OPTION(SHARED_LIB_VERSIONNING "Add SO version in .so build" ON) - -SET(PACKAGE "libzip") -SET(PACKAGE_NAME ${PACKAGE}) -SET(PACKAGE_VERSION_MAJOR "1") -SET(PACKAGE_VERSION_MINOR "5") -SET(PACKAGE_VERSION_MICRO "2a") -#SET(VERSION "${PACKAGE_VERSION_MAJOR}.${PACKAGE_VERSION_MINOR}") -SET(VERSION "${PACKAGE_VERSION_MAJOR}.${PACKAGE_VERSION_MINOR}.${PACKAGE_VERSION_MICRO}") -SET(PACKAGE_VERSION ${VERSION}) -SET(LIBZIP_VERSION ${PACKAGE_VERSION}) -SET(LIBZIP_VERSION_MAJOR ${PACKAGE_VERSION_MAJOR}) -SET(LIBZIP_VERSION_MINOR ${PACKAGE_VERSION_MINOR}) -SET(LIBZIP_VERSION_MICRO ${PACKAGE_VERSION_MICRO}) -SET(PACKAGE_STRING "${PACKAGE_NAME} ${PACKAGE_VERSION}") - -SET(ARCHIVE_NAME ${PACKAGE_NAME}-${PACKAGE_VERSION}) -IF(NOT TARGET dist) -ADD_CUSTOM_TARGET(dist - COMMAND git config tar.tar.xz.command "xz -c" - COMMAND git archive --prefix=${ARCHIVE_NAME}/ -o ${ARCHIVE_NAME}.tar.gz HEAD - COMMAND git archive --prefix=${ARCHIVE_NAME}/ -o ${ARCHIVE_NAME}.tar.xz HEAD - WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} - ) -ADD_CUSTOM_TARGET(distcheck - COMMAND chmod -R u+w ${ARCHIVE_NAME} ${ARCHIVE_NAME}-build ${ARCHIVE_NAME}-dest 2>/dev/null || true - COMMAND rm -rf ${ARCHIVE_NAME} ${ARCHIVE_NAME}-build ${ARCHIVE_NAME}-dest - COMMAND cmake -E tar xf ${ARCHIVE_NAME}.tar.gz - COMMAND chmod -R u-w ${ARCHIVE_NAME} - COMMAND mkdir ${ARCHIVE_NAME}-build - COMMAND mkdir ${ARCHIVE_NAME}-dest - COMMAND cd ${ARCHIVE_NAME}-build && cmake -DCMAKE_INSTALL_PREFIX=../${ARCHIVE_NAME}-dest ../${ARCHIVE_NAME} - COMMAND cd ${ARCHIVE_NAME}-build && make -j4 - COMMAND cd ${ARCHIVE_NAME}-build && make test - COMMAND cd ${ARCHIVE_NAME}-build && make install -# COMMAND cd ${ARCHIVE_NAME}-build && make uninstall -# COMMAND if [ `find ${ARCHIVE_NAME}-dest ! -type d | wc -l` -ne 0 ]; then echo leftover files in ${ARCHIVE_NAME}-dest; false; fi - COMMAND cd ${ARCHIVE_NAME}-build && make clean - COMMAND chmod -R u+w ${ARCHIVE_NAME} ${ARCHIVE_NAME}-build ${ARCHIVE_NAME}-dest - COMMAND rm -rf ${ARCHIVE_NAME} ${ARCHIVE_NAME}-build ${ARCHIVE_NAME}-dest - COMMAND echo "${ARCHIVE_NAME}.tar.gz is ready for distribution." - WORKING_DIRECTORY ${CMAKE_SOURCE_DIR} - ) -ADD_DEPENDENCIES(distcheck dist) -ENDIF(NOT TARGET dist) - -IF(BUILD_SHARED_LIBS) - SET(HAVE_SHARED TRUE) -ELSE() - SET(ZIP_STATIC TRUE) -ENDIF() - -# Checks - -CHECK_FUNCTION_EXISTS(_chmod HAVE__CHMOD) -CHECK_FUNCTION_EXISTS(_close HAVE__CLOSE) -CHECK_FUNCTION_EXISTS(_dup HAVE__DUP) -CHECK_FUNCTION_EXISTS(_fdopen HAVE__FDOPEN) -CHECK_FUNCTION_EXISTS(_fileno HAVE__FILENO) -CHECK_FUNCTION_EXISTS(_open HAVE__OPEN) -CHECK_FUNCTION_EXISTS(_setmode HAVE__SETMODE) -CHECK_FUNCTION_EXISTS(_snprintf HAVE__SNPRINTF) -CHECK_FUNCTION_EXISTS(_strdup HAVE__STRDUP) -CHECK_FUNCTION_EXISTS(_stricmp HAVE__STRICMP) -CHECK_FUNCTION_EXISTS(_strtoi64 HAVE__STRTOI64) -CHECK_FUNCTION_EXISTS(_strtoui64 HAVE__STRTOUI64) -CHECK_FUNCTION_EXISTS(_unlink HAVE__UNLINK) -CHECK_FUNCTION_EXISTS(arc4random HAVE_ARC4RANDOM) -CHECK_FUNCTION_EXISTS(clonefile HAVE_CLONEFILE) -CHECK_FUNCTION_EXISTS(explicit_bzero HAVE_EXPLICIT_BZERO) -CHECK_FUNCTION_EXISTS(explicit_memset HAVE_EXPLICIT_MEMSET) -CHECK_FUNCTION_EXISTS(fileno HAVE_FILENO) -CHECK_FUNCTION_EXISTS(fseeko HAVE_FSEEKO) -CHECK_FUNCTION_EXISTS(ftello HAVE_FTELLO) -CHECK_FUNCTION_EXISTS(getprogname HAVE_GETPROGNAME) -CHECK_FUNCTION_EXISTS(localtime_r HAVE_LOCALTIME_R) -CHECK_FUNCTION_EXISTS(open HAVE_OPEN) -CHECK_FUNCTION_EXISTS(setmode HAVE_SETMODE) -CHECK_FUNCTION_EXISTS(snprintf HAVE_SNPRINTF) -CHECK_FUNCTION_EXISTS(strcasecmp HAVE_STRCASECMP) -CHECK_FUNCTION_EXISTS(strdup HAVE_STRDUP) -CHECK_FUNCTION_EXISTS(stricmp HAVE_STRICMP) -CHECK_FUNCTION_EXISTS(strtoll HAVE_STRTOLL) -CHECK_FUNCTION_EXISTS(strtoull HAVE_STRTOULL) - -CHECK_INCLUDE_FILES("sys/types.h;sys/stat.h;fts.h" HAVE_FTS_H) -CHECK_INCLUDE_FILES(stdbool.h HAVE_STDBOOL_H) -CHECK_INCLUDE_FILES(strings.h HAVE_STRINGS_H) -CHECK_INCLUDE_FILES(unistd.h HAVE_UNISTD_H) - -CHECK_INCLUDE_FILES(inttypes.h HAVE_INTTYPES_H_LIBZIP) -CHECK_INCLUDE_FILES(stdint.h HAVE_STDINT_H_LIBZIP) -CHECK_INCLUDE_FILES(sys/types.h HAVE_SYS_TYPES_H_LIBZIP) - -# TODO: fix test -# this test does not find __progname even when it exists -#CHECK_SYMBOL_EXISTS(__progname stdlib.h HAVE___PROGNAME) - -CHECK_TYPE_SIZE(__int8 __INT8_LIBZIP) -CHECK_TYPE_SIZE(int8_t INT8_T_LIBZIP) -CHECK_TYPE_SIZE(uint8_t UINT8_T_LIBZIP) -CHECK_TYPE_SIZE(__int16 __INT16_LIBZIP) -CHECK_TYPE_SIZE(int16_t INT16_T_LIBZIP) -CHECK_TYPE_SIZE(uint16_t UINT16_T_LIBZIP) -CHECK_TYPE_SIZE(__int32 __INT32_LIBZIP) -CHECK_TYPE_SIZE(int32_t INT32_T_LIBZIP) -CHECK_TYPE_SIZE(uint32_t UINT32_T_LIBZIP) -CHECK_TYPE_SIZE(__int64 __INT64_LIBZIP) -CHECK_TYPE_SIZE(int64_t INT64_T_LIBZIP) -CHECK_TYPE_SIZE(uint64_t UINT64_T_LIBZIP) -CHECK_TYPE_SIZE("short" SHORT_LIBZIP) -CHECK_TYPE_SIZE("int" INT_LIBZIP) -CHECK_TYPE_SIZE("long" LONG_LIBZIP) -CHECK_TYPE_SIZE("long long" LONG_LONG_LIBZIP) -CHECK_TYPE_SIZE("off_t" SIZEOF_OFF_T) -CHECK_TYPE_SIZE("size_t" SIZE_T_LIBZIP) -CHECK_TYPE_SIZE("ssize_t" SSIZE_T_LIBZIP) - -CHECK_C_SOURCE_COMPILES("#include <sys/ioctl.h> -#include <linux/fs.h> -int main(int argc, char *argv[]) { unsigned long x = FICLONERANGE; }" HAVE_FICLONERANGE) - -CHECK_C_SOURCE_COMPILES(" -int foo(char * _Nullable bar); -int main(int argc, char *argv[]) { }" HAVE_NULLABLE) - -TEST_BIG_ENDIAN(WORDS_BIGENDIAN) - -#FIND_PACKAGE(ZLIB 1.1.2 REQUIRED) -INCLUDE_DIRECTORIES(../zlib/zlib) -SET(CMAKE_REQUIRED_INCLUDES ../zlib/zlib) - -IF(ENABLE_BZIP2) - FIND_PACKAGE(BZip2) - IF(BZIP2_FOUND) - SET (HAVE_LIBBZ2 1) - - INCLUDE_DIRECTORIES(${BZIP2_INCLUDE_DIR}) - SET (OPTIONAL_LIBRARY ${OPTIONAL_LIBRARY} ${BZIP2_LIBRARIES}) - ELSE() - MESSAGE(WARNING "-- bzip2 library not found; bzip2 support disabled") - ENDIF(BZIP2_FOUND) -ENDIF(ENABLE_BZIP2) - -IF(ENABLE_LZMA) - FIND_PACKAGE(LibLZMA) - IF(LIBLZMA_FOUND) - SET (HAVE_LIBLZMA 1) - - INCLUDE_DIRECTORIES(${LIBLZMA_INCLUDE_DIR}) - SET (OPTIONAL_LIBRARY ${OPTIONAL_LIBRARY} ${LIBLZMA_LIBRARY}) - ELSE() - MESSAGE(WARNING "-- lzma library not found; lzma support disabled") - ENDIF(LIBLZMA_FOUND) -ENDIF(ENABLE_LZMA) - - -IF (COMMONCRYPTO_FOUND) - SET (HAVE_CRYPTO 1) - SET (HAVE_COMMONCRYPTO 1) -ELSEIF (WINDOWS_CRYPTO_FOUND) - SET (HAVE_CRYPTO 1) - SET (HAVE_WINDOWS_CRYPTO 1) -ELSEIF (GNUTLS_FOUND AND NETTLE_FOUND) - SET (HAVE_CRYPTO 1) - SET (HAVE_GNUTLS 1) - INCLUDE_DIRECTORIES(${GNUTLS_INCLUDE_DIR} ${NETTLE_INCLUDE_DIR}) - SET (OPTIONAL_LIBRARY ${OPTIONAL_LIBRARY} ${GNUTLS_LIBRARY} ${NETTLE_LIBRARY}) -ELSEIF (OPENSSL_FOUND) - SET (HAVE_CRYPTO 1) - SET (HAVE_OPENSSL 1) - INCLUDE_DIRECTORIES(${OPENSSL_INCLUDE_DIR}) - SET (OPTIONAL_LIBRARY ${OPTIONAL_LIBRARY} ${OPENSSL_LIBRARIES}) -ELSEIF (MBEDTLS_LIBRARIES) - SET (HAVE_CRYPTO 1) - SET (HAVE_MBEDTLS 1) - INCLUDE_DIRECTORIES(${MBEDTLS_INCLUDE_DIR}) - SET (OPTIONAL_LIBRARY ${OPTIONAL_LIBRARY} ${MBEDTLS_LIBRARIES}) -ENDIF() - -IF (NOT HAVE_CRYPTO) - MESSAGE(WARNING "-- neither Common Crypto, GnuTLS, mbed TLS, OpenSSL, nor Windows Cryptography found; AES support disabled") -ENDIF() - -IF(MSVC) -ADD_DEFINITIONS("-D_CRT_SECURE_NO_WARNINGS") -ADD_DEFINITIONS("-D_CRT_NONSTDC_NO_DEPRECATE") -ENDIF(MSVC) - -if(WIN32) - if(HAVE_WINDOWS_CRYPTO) - SET (OPTIONAL_LIBRARY ${OPTIONAL_LIBRARY} bcrypt) - endif() - if(CMAKE_SYSTEM_NAME MATCHES WindowsPhone OR CMAKE_SYSTEM_NAME MATCHES WindowsStore) - ADD_DEFINITIONS(-DMS_UWP) - else(CMAKE_SYSTEM_NAME MATCHES WindowsPhone OR CMAKE_SYSTEM_NAME MATCHES WindowsStore) - SET (OPTIONAL_LIBRARY ${OPTIONAL_LIBRARY} advapi32) - endif(CMAKE_SYSTEM_NAME MATCHES WindowsPhone OR CMAKE_SYSTEM_NAME MATCHES WindowsStore) -endif(WIN32) - -ADD_DEFINITIONS("-DHAVE_CONFIG_H") - -# rpath handling: use rpath in installed binaries -IF(NOT CMAKE_SYSTEM_NAME MATCHES Linux) - SET(CMAKE_INSTALL_RPATH "${CMAKE_INSTALL_PREFIX}/${CMAKE_INSTALL_LIBDIR}") - SET(CMAKE_INSTALL_RPATH_USE_LINK_PATH TRUE) -ENDIF() - -# fixed size integral types - -IF(HAVE_INTTYPES_H_LIBZIP) - SET(LIBZIP_TYPES_INCLUDE "#define __STDC_FORMAT_MACROS 1 -#include <inttypes.h>") -ELSEIF(HAVE_STDINT_H_LIBZIP) - SET(LIBZIP_TYPES_INCLUDE "#include <stdint.h>") -ELSEIF(HAVE_SYS_TYPES_H_LIBZIP) - SET(LIBZIP_TYPES_INCLUDE "#include <sys/types.h>") -ENDIF() - -IF(HAVE_INT8_T_LIBZIP) - SET(ZIP_INT8_T int8_t) -ELSEIF(HAVE___INT8_LIBZIP) - SET(ZIP_INT8_T __int8) -ELSE() - SET(ZIP_INT8_T "signed char") -ENDIF() - -IF(HAVE_UINT8_T_LIBZIP) - SET(ZIP_UINT8_T uint8_t) -ELSEIF(HAVE___INT8_LIBZIP) - SET(ZIP_UINT8_T "unsigned __int8") -ELSE() - SET(ZIP_UINT8_T "unsigned char") -ENDIF() - -IF(HAVE_INT16_T_LIBZIP) - SET(ZIP_INT16_T int16_t) -ELSEIF(HAVE___INT16_LIBZIP) - SET(INT16_T_LIBZIP __int16) -ELSEIF(SHORT_LIBZIP EQUAL 2) - SET(INT16_T_LIBZIP short) -ENDIF() - -IF(HAVE_UINT16_T_LIBZIP) - SET(ZIP_UINT16_T uint16_t) -ELSEIF(HAVE___INT16_LIBZIP) - SET(UINT16_T_LIBZIP "unsigned __int16") -ELSEIF(SHORT_LIBZIP EQUAL 2) - SET(UINT16_T_LIBZIP "unsigned short") -ENDIF() - -IF(HAVE_INT32_T_LIBZIP) - SET(ZIP_INT32_T int32_t) -ELSEIF(HAVE___INT32_LIBZIP) - SET(ZIP_INT32_T __int32) -ELSEIF(INT_LIBZIP EQUAL 4) - SET(ZIP_INT32_T int) -ELSEIF(LONG_LIBZIP EQUAL 4) - SET(ZIP_INT32_T long) -ENDIF() - -IF(HAVE_UINT32_T_LIBZIP) -SET(ZIP_UINT32_T uint32_t) -ELSEIF(HAVE___INT32_LIBZIP) -SET(ZIP_UINT32_T "unsigned __int32") -ELSEIF(INT_LIBZIP EQUAL 4) -SET(ZIP_UINT32_T "unsigned int") -ELSEIF(LONG_LIBZIP EQUAL 4) -SET(ZIP_UINT32_T "unsigned long") -ENDIF() - -IF(HAVE_INT64_T_LIBZIP) - SET(ZIP_INT64_T int64_t) -ELSEIF(HAVE___INT64_LIBZIP) - SET(ZIP_INT64_T __int64) -ELSEIF(LONG_LIBZIP EQUAL 8) - SET(ZIP_INT64_T long) -ELSEIF(LONG_LONG_LIBZIP EQUAL 8) - SET(ZIP_INT64_T "long long") -ENDIF() - -IF(HAVE_UINT64_T_LIBZIP) - SET(ZIP_UINT64_T uint64_t) -ELSEIF(HAVE___INT64_LIBZIP) - SET(ZIP_UINT64_T "unsigned __int64") -ELSEIF(LONG_LIBZIP EQUAL 8) - SET(ZIP_UINT64_T "unsigned long") -ELSEIF(LONG_LONG_LIBZIP EQUAL 8) - SET(ZIP_UINT64_T "unsigned long long") -ENDIF() - -IF(HAVE_NULLABLE) - SET(ZIP_NULLABLE_DEFINES) -ELSE() - SET(ZIP_NULLABLE_DEFINES "#define _Nullable -#define _Nonnull") -ENDIF() - -# write out config file -CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/libzip/cmake-config.h.in ${CMAKE_CURRENT_BINARY_DIR}/libzip/config.h) -CONFIGURE_FILE(${CMAKE_CURRENT_SOURCE_DIR}/libzip/cmake-zipconf.h.in ${CMAKE_CURRENT_BINARY_DIR}/libzip/zipconf.h) - -# installation -INSTALL(FILES ${CMAKE_CURRENT_BINARY_DIR}/libzip/zipconf.h DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}) -INSTALL(FILES libzip/lib/zip.h DESTINATION ${CMAKE_INSTALL_INCLUDEDIR}) - -SET(CMAKE_C_VISIBILITY_PRESET hidden) - -ADD_LIBRARY(zip - libzip/lib/zip_add.c - libzip/lib/zip_add_dir.c - libzip/lib/zip_add_entry.c - libzip/lib/zip_algorithm_deflate.c - libzip/lib/zip_buffer.c - libzip/lib/zip_close.c - libzip/lib/zip_delete.c - libzip/lib/zip_dir_add.c - libzip/lib/zip_dirent.c - libzip/lib/zip_discard.c - libzip/lib/zip_entry.c - libzip/lib/zip_err_str.c - libzip/lib/zip_error.c - libzip/lib/zip_error_clear.c - libzip/lib/zip_error_get.c - libzip/lib/zip_error_get_sys_type.c - libzip/lib/zip_error_strerror.c - libzip/lib/zip_error_to_str.c - libzip/lib/zip_extra_field.c - libzip/lib/zip_extra_field_api.c - libzip/lib/zip_fclose.c - libzip/lib/zip_fdopen.c - libzip/lib/zip_file_add.c - libzip/lib/zip_file_error_clear.c - libzip/lib/zip_file_error_get.c - libzip/lib/zip_file_get_comment.c - libzip/lib/zip_file_get_external_attributes.c - libzip/lib/zip_file_get_offset.c - libzip/lib/zip_file_rename.c - libzip/lib/zip_file_replace.c - libzip/lib/zip_file_set_comment.c - libzip/lib/zip_file_set_encryption.c - libzip/lib/zip_file_set_external_attributes.c - libzip/lib/zip_file_set_mtime.c - libzip/lib/zip_file_strerror.c - libzip/lib/zip_filerange_crc.c - libzip/lib/zip_fopen.c - libzip/lib/zip_fopen_encrypted.c - libzip/lib/zip_fopen_index.c - libzip/lib/zip_fopen_index_encrypted.c - libzip/lib/zip_fread.c - libzip/lib/zip_fseek.c - libzip/lib/zip_ftell.c - libzip/lib/zip_get_archive_comment.c - libzip/lib/zip_get_archive_flag.c - libzip/lib/zip_get_encryption_implementation.c - libzip/lib/zip_get_file_comment.c - libzip/lib/zip_get_name.c - libzip/lib/zip_get_num_entries.c - libzip/lib/zip_get_num_files.c - libzip/lib/zip_hash.c - libzip/lib/zip_io_util.c - libzip/lib/zip_libzip_version.c - libzip/lib/zip_memdup.c - libzip/lib/zip_name_locate.c - libzip/lib/zip_new.c - libzip/lib/zip_open.c - libzip/lib/zip_progress.c - libzip/lib/zip_rename.c - libzip/lib/zip_replace.c - libzip/lib/zip_set_archive_comment.c - libzip/lib/zip_set_archive_flag.c - libzip/lib/zip_set_default_password.c - libzip/lib/zip_set_file_comment.c - libzip/lib/zip_set_file_compression.c - libzip/lib/zip_set_name.c - libzip/lib/zip_source_accept_empty.c - libzip/lib/zip_source_begin_write.c - libzip/lib/zip_source_begin_write_cloning.c - libzip/lib/zip_source_buffer.c - libzip/lib/zip_source_call.c - libzip/lib/zip_source_close.c - libzip/lib/zip_source_commit_write.c - libzip/lib/zip_source_compress.c - libzip/lib/zip_source_crc.c - libzip/lib/zip_source_error.c - libzip/lib/zip_source_filep.c - libzip/lib/zip_source_free.c - libzip/lib/zip_source_function.c - libzip/lib/zip_source_get_compression_flags.c - libzip/lib/zip_source_is_deleted.c - libzip/lib/zip_source_layered.c - libzip/lib/zip_source_open.c - libzip/lib/zip_source_pkware.c - libzip/lib/zip_source_read.c - libzip/lib/zip_source_remove.c - libzip/lib/zip_source_rollback_write.c - libzip/lib/zip_source_seek.c - libzip/lib/zip_source_seek_write.c - libzip/lib/zip_source_stat.c - libzip/lib/zip_source_supports.c - libzip/lib/zip_source_tell.c - libzip/lib/zip_source_tell_write.c - libzip/lib/zip_source_window.c - libzip/lib/zip_source_write.c - libzip/lib/zip_source_zip.c - libzip/lib/zip_source_zip_new.c - libzip/lib/zip_stat.c - libzip/lib/zip_stat_index.c - libzip/lib/zip_stat_init.c - libzip/lib/zip_strerror.c - libzip/lib/zip_string.c - libzip/lib/zip_unchange.c - libzip/lib/zip_unchange_all.c - libzip/lib/zip_unchange_archive.c - libzip/lib/zip_unchange_data.c - libzip/lib/zip_utf-8.c -) - -IF(WIN32) - target_sources(zip PRIVATE - libzip/lib/zip_source_win32handle.c - libzip/lib/zip_source_win32utf8.c - libzip/lib/zip_source_win32w.c - ) - IF(CMAKE_SYSTEM_NAME MATCHES WindowsPhone OR CMAKE_SYSTEM_NAME MATCHES WindowsStore) - ELSE() - target_sources(zip PRIVATE libzip/lib/zip_source_win32a.c) - ENDIF() -ELSE() - target_sources(zip PRIVATE - libzip/lib/zip_mkstempm.c - libzip/lib/zip_source_file.c - libzip/lib/zip_random_unix.c - ) -ENDIF() - -IF(HAVE_LIBBZ2) - target_sources(zip PRIVATE libzip/lib/zip_algorithm_bzip2.c) -ENDIF() - -IF(HAVE_LIBLZMA) - target_sources(zip PRIVATE libzip/lib/zip_algorithm_xz.c) -ENDIF() - -IF(HAVE_COMMONCRYPTO) - target_sources(zip PRIVATE libzip/lib/zip_crypto_commoncrypto.c) -ELSEIF(HAVE_WINDOWS_CRYPTO) - target_sources(zip PRIVATE libzip/lib/zip_crypto_win.c) -ELSEIF(HAVE_GNUTLS) - target_sources(zip PRIVATE libzip/lib/zip_crypto_gnutls.c) -ELSEIF(HAVE_OPENSSL) - target_sources(zip PRIVATE libzip/lib/zip_crypto_openssl.c) -ELSEIF(HAVE_MBEDTLS) - target_sources(zip PRIVATE libzip/lib/zip_crypto_mbedtls.c) -ENDIF() - -IF(HAVE_CRYPTO) - target_sources(zip PRIVATE - libzip/lib/zip_winzip_aes.c - libzip/lib/zip_source_winzip_aes_decode.c - libzip/lib/zip_source_winzip_aes_encode.c - ) -ENDIF() - -target_include_directories(zip -PUBLIC - libzip/lib - ${CMAKE_CURRENT_BINARY_DIR}/libzip -) - -# pkgconfig file -SET(prefix ${CMAKE_INSTALL_PREFIX}) -SET(exec_prefix \${prefix}) -SET(bindir \${exec_prefix}/${CMAKE_INSTALL_BINDIR}) -SET(libdir \${exec_prefix}/${CMAKE_INSTALL_LIBDIR}) -SET(includedir \${prefix}/${CMAKE_INSTALL_INCLUDEDIR}) -IF(CMAKE_SYSTEM_NAME MATCHES BSD) - SET(PKG_CONFIG_RPATH "-Wl,-R\${libdir}") -ENDIF(CMAKE_SYSTEM_NAME MATCHES BSD) -get_target_property(LIBS_PRIVATE zip LINK_LIBRARIES) -foreach(LIB ${LIBS_PRIVATE}) - if(LIB MATCHES "^/") - get_filename_component(LIB ${LIB} NAME_WE) - string(REGEX REPLACE "^lib" "" LIB ${LIB}) - endif() - set(LIBS "${LIBS} -l${LIB}") -endforeach() -CONFIGURE_FILE(libzip/libzip.pc.in libzip/libzip.pc @ONLY) -INSTALL(FILES ${CMAKE_CURRENT_BINARY_DIR}/libzip.pc DESTINATION ${CMAKE_INSTALL_LIBDIR}/pkgconfig) - -ADD_CUSTOM_TARGET(update_zip_err_str - COMMAND sh ${CMAKE_CURRENT_SOURCE_DIR}/libzip/lib/make_zip_err_str.sh ${CMAKE_CURRENT_SOURCE_DIR}/libzip/lib/zip.h ${CMAKE_CURRENT_SOURCE_DIR}/libzip/lib/zip_err_str.c - DEPENDS ${CMAKE_CURRENT_SOURCE_DIR}/libzip/lib/zip.h ${CMAKE_CURRENT_SOURCE_DIR}/libzip/lib/make_zip_err_str.sh -) - -IF(SHARED_LIB_VERSIONNING) -SET_TARGET_PROPERTIES(zip PROPERTIES VERSION 5.0 SOVERSION 5) -ENDIF() - -TARGET_LINK_LIBRARIES(zip ${ZLIB_LIBRARIES} ${OPTIONAL_LIBRARY}) -INSTALL(TARGETS zip - RUNTIME DESTINATION ${CMAKE_INSTALL_BINDIR} - ARCHIVE DESTINATION ${CMAKE_INSTALL_LIBDIR} - LIBRARY DESTINATION ${CMAKE_INSTALL_LIBDIR} -) - diff --git a/externals/libzip/libzip b/externals/libzip/libzip deleted file mode 160000 -Subproject 89bd6d63bdea9da7627695f6c82e54f16d368b5 diff --git a/src/common/settings.cpp b/src/common/settings.cpp index 69f0bd8c0..9dd5e3efb 100644 --- a/src/common/settings.cpp +++ b/src/common/settings.cpp @@ -69,8 +69,6 @@ void LogSettings() { log_path("DataStorage_NANDDir", Common::FS::GetYuzuPath(Common::FS::YuzuPath::NANDDir)); log_path("DataStorage_SDMCDir", Common::FS::GetYuzuPath(Common::FS::YuzuPath::SDMCDir)); log_setting("Debugging_ProgramArgs", values.program_args.GetValue()); - log_setting("Services_BCATBackend", values.bcat_backend.GetValue()); - log_setting("Services_BCATBoxcatLocal", values.bcat_boxcat_local.GetValue()); log_setting("Input_EnableMotion", values.motion_enabled.GetValue()); log_setting("Input_EnableVibration", values.vibration_enabled.GetValue()); log_setting("Input_EnableRawInput", values.enable_raw_input.GetValue()); diff --git a/src/common/settings.h b/src/common/settings.h index c53d5acc3..402339443 100644 --- a/src/common/settings.h +++ b/src/common/settings.h @@ -568,8 +568,6 @@ struct Values { BasicSetting<bool> use_dev_keys{false, "use_dev_keys"}; // Network - BasicSetting<std::string> bcat_backend{"none", "bcat_backend"}; - BasicSetting<bool> bcat_boxcat_local{false, "bcat_boxcat_local"}; BasicSetting<std::string> network_interface{std::string(), "network_interface"}; // WebService diff --git a/src/core/CMakeLists.txt b/src/core/CMakeLists.txt index 7140d0db8..aa3b26628 100644 --- a/src/core/CMakeLists.txt +++ b/src/core/CMakeLists.txt @@ -106,8 +106,6 @@ add_library(core STATIC file_sys/vfs_concat.h file_sys/vfs_layered.cpp file_sys/vfs_layered.h - file_sys/vfs_libzip.cpp - file_sys/vfs_libzip.h file_sys/vfs_offset.cpp file_sys/vfs_offset.h file_sys/vfs_real.cpp @@ -653,13 +651,6 @@ add_library(core STATIC tools/freezer.h ) -if (YUZU_ENABLE_BOXCAT) - target_sources(core PRIVATE - hle/service/bcat/backend/boxcat.cpp - hle/service/bcat/backend/boxcat.h - ) -endif() - if (MSVC) target_compile_options(core PRIVATE /we4242 # 'identifier': conversion from 'type1' to 'type2', possible loss of data @@ -690,12 +681,7 @@ endif() create_target_directory_groups(core) target_link_libraries(core PUBLIC common PRIVATE audio_core video_core) -target_link_libraries(core PUBLIC Boost::boost PRIVATE fmt::fmt nlohmann_json::nlohmann_json mbedtls Opus::Opus zip) - -if (YUZU_ENABLE_BOXCAT) - target_compile_definitions(core PRIVATE -DYUZU_ENABLE_BOXCAT) - target_link_libraries(core PRIVATE httplib nlohmann_json::nlohmann_json) -endif() +target_link_libraries(core PUBLIC Boost::boost PRIVATE fmt::fmt nlohmann_json::nlohmann_json mbedtls Opus::Opus) if (ENABLE_WEB_SERVICE) target_compile_definitions(core PRIVATE -DENABLE_WEB_SERVICE) diff --git a/src/core/core.cpp b/src/core/core.cpp index 50d5dab4b..bb268a319 100644 --- a/src/core/core.cpp +++ b/src/core/core.cpp @@ -421,6 +421,7 @@ struct System::Impl { bool is_async_gpu{}; ExecuteProgramCallback execute_program_callback; + ExitCallback exit_callback; std::array<u64, Core::Hardware::NUM_CPU_CORES> dynarmic_ticks{}; std::array<MicroProfileToken, Core::Hardware::NUM_CPU_CORES> microprofile_dynarmic{}; @@ -798,6 +799,18 @@ void System::ExecuteProgram(std::size_t program_index) { } } +void System::RegisterExitCallback(ExitCallback&& callback) { + impl->exit_callback = std::move(callback); +} + +void System::Exit() { + if (impl->exit_callback) { + impl->exit_callback(); + } else { + LOG_CRITICAL(Core, "exit_callback must be initialized by the frontend"); + } +} + void System::ApplySettings() { if (IsPoweredOn()) { Renderer().RefreshBaseSettings(); diff --git a/src/core/core.h b/src/core/core.h index 715ab88e7..a796472b2 100644 --- a/src/core/core.h +++ b/src/core/core.h @@ -387,6 +387,18 @@ public: */ void ExecuteProgram(std::size_t program_index); + /// Type used for the frontend to designate a callback for System to exit the application. + using ExitCallback = std::function<void()>; + + /** + * Registers a callback from the frontend for System to exit the application. + * @param callback Callback from the frontend to exit the application. + */ + void RegisterExitCallback(ExitCallback&& callback); + + /// Instructs the frontend to exit the application. + void Exit(); + /// Applies any changes to settings to this core instance. void ApplySettings(); diff --git a/src/core/file_sys/vfs_libzip.cpp b/src/core/file_sys/vfs_libzip.cpp deleted file mode 100644 index 00e256779..000000000 --- a/src/core/file_sys/vfs_libzip.cpp +++ /dev/null @@ -1,88 +0,0 @@ -// Copyright 2019 yuzu emulator team -// Licensed under GPLv2 or any later version -// Refer to the license.txt file included. - -#include <string> - -#ifdef __GNUC__ -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wshadow" -#endif -#include <zip.h> -#ifdef __GNUC__ -#pragma GCC diagnostic pop -#endif - -#include "common/fs/path_util.h" -#include "core/file_sys/vfs.h" -#include "core/file_sys/vfs_libzip.h" -#include "core/file_sys/vfs_vector.h" - -namespace FileSys { - -VirtualDir ExtractZIP(VirtualFile file) { - zip_error_t error{}; - - const auto data = file->ReadAllBytes(); - std::unique_ptr<zip_source_t, decltype(&zip_source_close)> src{ - zip_source_buffer_create(data.data(), data.size(), 0, &error), zip_source_close}; - if (src == nullptr) - return nullptr; - - std::unique_ptr<zip_t, decltype(&zip_close)> zip{zip_open_from_source(src.get(), 0, &error), - zip_close}; - if (zip == nullptr) - return nullptr; - - std::shared_ptr<VectorVfsDirectory> out = std::make_shared<VectorVfsDirectory>(); - - const auto num_entries = static_cast<std::size_t>(zip_get_num_entries(zip.get(), 0)); - - zip_stat_t stat{}; - zip_stat_init(&stat); - - for (std::size_t i = 0; i < num_entries; ++i) { - const auto stat_res = zip_stat_index(zip.get(), i, 0, &stat); - if (stat_res == -1) - return nullptr; - - const std::string name(stat.name); - if (name.empty()) - continue; - - if (name.back() != '/') { - std::unique_ptr<zip_file_t, decltype(&zip_fclose)> file2{ - zip_fopen_index(zip.get(), i, 0), zip_fclose}; - - std::vector<u8> buf(stat.size); - if (zip_fread(file2.get(), buf.data(), buf.size()) != s64(buf.size())) - return nullptr; - - const auto parts = Common::FS::SplitPathComponents(stat.name); - const auto new_file = std::make_shared<VectorVfsFile>(buf, parts.back()); - - std::shared_ptr<VectorVfsDirectory> dtrv = out; - for (std::size_t j = 0; j < parts.size() - 1; ++j) { - if (dtrv == nullptr) - return nullptr; - const auto subdir = dtrv->GetSubdirectory(parts[j]); - if (subdir == nullptr) { - const auto temp = std::make_shared<VectorVfsDirectory>( - std::vector<VirtualFile>{}, std::vector<VirtualDir>{}, parts[j]); - dtrv->AddDirectory(temp); - dtrv = temp; - } else { - dtrv = std::dynamic_pointer_cast<VectorVfsDirectory>(subdir); - } - } - - if (dtrv == nullptr) - return nullptr; - dtrv->AddFile(new_file); - } - } - - return out; -} - -} // namespace FileSys diff --git a/src/core/file_sys/vfs_libzip.h b/src/core/file_sys/vfs_libzip.h deleted file mode 100644 index f68af576a..000000000 --- a/src/core/file_sys/vfs_libzip.h +++ /dev/null @@ -1,13 +0,0 @@ -// Copyright 2019 yuzu emulator team -// Licensed under GPLv2 or any later version -// Refer to the license.txt file included. - -#pragma once - -#include "core/file_sys/vfs_types.h" - -namespace FileSys { - -VirtualDir ExtractZIP(VirtualFile zip); - -} // namespace FileSys diff --git a/src/core/hle/service/am/am.cpp b/src/core/hle/service/am/am.cpp index 8c2e2f920..49e9787a4 100644 --- a/src/core/hle/service/am/am.cpp +++ b/src/core/hle/service/am/am.cpp @@ -332,10 +332,10 @@ ISelfController::~ISelfController() = default; void ISelfController::Exit(Kernel::HLERequestContext& ctx) { LOG_DEBUG(Service_AM, "called"); - system.Shutdown(); - IPC::ResponseBuilder rb{ctx, 2}; rb.Push(ResultSuccess); + + system.Exit(); } void ISelfController::LockExit(Kernel::HLERequestContext& ctx) { diff --git a/src/core/hle/service/bcat/backend/boxcat.cpp b/src/core/hle/service/bcat/backend/boxcat.cpp deleted file mode 100644 index 7ca7f2aac..000000000 --- a/src/core/hle/service/bcat/backend/boxcat.cpp +++ /dev/null @@ -1,548 +0,0 @@ -// Copyright 2019 yuzu emulator team -// Licensed under GPLv2 or any later version -// Refer to the license.txt file included. - -#include <fmt/ostream.h> - -#ifdef __GNUC__ -#pragma GCC diagnostic push -#pragma GCC diagnostic ignored "-Wshadow" -#ifndef __clang__ -#pragma GCC diagnostic ignored "-Wmaybe-uninitialized" -#endif -#endif -#include <httplib.h> -#include <mbedtls/sha256.h> -#include <nlohmann/json.hpp> -#ifdef __GNUC__ -#pragma GCC diagnostic pop -#endif - -#include "common/fs/file.h" -#include "common/fs/fs.h" -#include "common/fs/path_util.h" -#include "common/hex_util.h" -#include "common/logging/log.h" -#include "common/settings.h" -#include "core/core.h" -#include "core/file_sys/vfs.h" -#include "core/file_sys/vfs_libzip.h" -#include "core/file_sys/vfs_vector.h" -#include "core/frontend/applets/error.h" -#include "core/hle/service/am/applets/applets.h" -#include "core/hle/service/bcat/backend/boxcat.h" - -namespace Service::BCAT { -namespace { - -// Prevents conflicts with windows macro called CreateFile -FileSys::VirtualFile VfsCreateFileWrap(FileSys::VirtualDir dir, std::string_view name) { - return dir->CreateFile(name); -} - -// Prevents conflicts with windows macro called DeleteFile -bool VfsDeleteFileWrap(FileSys::VirtualDir dir, std::string_view name) { - return dir->DeleteFile(name); -} - -constexpr ResultCode ERROR_GENERAL_BCAT_FAILURE{ErrorModule::BCAT, 1}; - -constexpr char BOXCAT_HOSTNAME[] = "api.yuzu-emu.org"; - -// Formatted using fmt with arg[0] = hex title id -constexpr char BOXCAT_PATHNAME_DATA[] = "/game-assets/{:016X}/boxcat"; -constexpr char BOXCAT_PATHNAME_LAUNCHPARAM[] = "/game-assets/{:016X}/launchparam"; - -constexpr char BOXCAT_PATHNAME_EVENTS[] = "/game-assets/boxcat/events"; - -constexpr char BOXCAT_API_VERSION[] = "1"; -constexpr char BOXCAT_CLIENT_TYPE[] = "yuzu"; - -// HTTP status codes for Boxcat -enum class ResponseStatus { - Ok = 200, ///< Operation completed successfully. - BadClientVersion = 301, ///< The Boxcat-Client-Version doesn't match the server. - NoUpdate = 304, ///< The digest provided would match the new data, no need to update. - NoMatchTitleId = 404, ///< The title ID provided doesn't have a boxcat implementation. - NoMatchBuildId = 406, ///< The build ID provided is blacklisted (potentially because of format - ///< issues or whatnot) and has no data. -}; - -enum class DownloadResult { - Success = 0, - NoResponse, - GeneralWebError, - NoMatchTitleId, - NoMatchBuildId, - InvalidContentType, - GeneralFSError, - BadClientVersion, -}; - -constexpr std::array<const char*, 8> DOWNLOAD_RESULT_LOG_MESSAGES{ - "Success", - "There was no response from the server.", - "There was a general web error code returned from the server.", - "The title ID of the current game doesn't have a boxcat implementation. If you believe an " - "implementation should be added, contact yuzu support.", - "The build ID of the current version of the game is marked as incompatible with the current " - "BCAT distribution. Try upgrading or downgrading your game version or contacting yuzu support.", - "The content type of the web response was invalid.", - "There was a general filesystem error while saving the zip file.", - "The server is either too new or too old to serve the request. Try using the latest version of " - "an official release of yuzu.", -}; - -std::ostream& operator<<(std::ostream& os, DownloadResult result) { - return os << DOWNLOAD_RESULT_LOG_MESSAGES.at(static_cast<std::size_t>(result)); -} - -constexpr u32 PORT = 443; -constexpr u32 TIMEOUT_SECONDS = 30; -[[maybe_unused]] constexpr u64 VFS_COPY_BLOCK_SIZE = 1ULL << 24; // 4MB - -std::filesystem::path GetBINFilePath(u64 title_id) { - return Common::FS::GetYuzuPath(Common::FS::YuzuPath::CacheDir) / "bcat" / - fmt::format("{:016X}/launchparam.bin", title_id); -} - -std::filesystem::path GetZIPFilePath(u64 title_id) { - return Common::FS::GetYuzuPath(Common::FS::YuzuPath::CacheDir) / "bcat" / - fmt::format("{:016X}/data.zip", title_id); -} - -// If the error is something the user should know about (build ID mismatch, bad client version), -// display an error. -void HandleDownloadDisplayResult(const AM::Applets::AppletManager& applet_manager, - DownloadResult res) { - if (res == DownloadResult::Success || res == DownloadResult::NoResponse || - res == DownloadResult::GeneralWebError || res == DownloadResult::GeneralFSError || - res == DownloadResult::NoMatchTitleId || res == DownloadResult::InvalidContentType) { - return; - } - - const auto& frontend{applet_manager.GetAppletFrontendSet()}; - frontend.error->ShowCustomErrorText( - ResultUnknown, "There was an error while attempting to use Boxcat.", - DOWNLOAD_RESULT_LOG_MESSAGES[static_cast<std::size_t>(res)], [] {}); -} - -bool VfsRawCopyProgress(FileSys::VirtualFile src, FileSys::VirtualFile dest, - std::string_view dir_name, ProgressServiceBackend& progress, - std::size_t block_size = 0x1000) { - if (src == nullptr || dest == nullptr || !src->IsReadable() || !dest->IsWritable()) - return false; - if (!dest->Resize(src->GetSize())) - return false; - - progress.StartDownloadingFile(dir_name, src->GetName(), src->GetSize()); - - std::vector<u8> temp(std::min(block_size, src->GetSize())); - for (std::size_t i = 0; i < src->GetSize(); i += block_size) { - const auto read = std::min(block_size, src->GetSize() - i); - - if (src->Read(temp.data(), read, i) != read) { - return false; - } - - if (dest->Write(temp.data(), read, i) != read) { - return false; - } - - progress.UpdateFileProgress(i); - } - - progress.FinishDownloadingFile(); - - return true; -} - -bool VfsRawCopyDProgressSingle(FileSys::VirtualDir src, FileSys::VirtualDir dest, - ProgressServiceBackend& progress, std::size_t block_size = 0x1000) { - if (src == nullptr || dest == nullptr || !src->IsReadable() || !dest->IsWritable()) - return false; - - for (const auto& file : src->GetFiles()) { - const auto out_file = VfsCreateFileWrap(dest, file->GetName()); - if (!VfsRawCopyProgress(file, out_file, src->GetName(), progress, block_size)) { - return false; - } - } - progress.CommitDirectory(src->GetName()); - - return true; -} - -bool VfsRawCopyDProgress(FileSys::VirtualDir src, FileSys::VirtualDir dest, - ProgressServiceBackend& progress, std::size_t block_size = 0x1000) { - if (src == nullptr || dest == nullptr || !src->IsReadable() || !dest->IsWritable()) - return false; - - for (const auto& dir : src->GetSubdirectories()) { - const auto out = dest->CreateSubdirectory(dir->GetName()); - if (!VfsRawCopyDProgressSingle(dir, out, progress, block_size)) { - return false; - } - } - - return true; -} - -} // Anonymous namespace - -class Boxcat::Client { -public: - Client(std::filesystem::path path_, u64 title_id_, u64 build_id_) - : path(std::move(path_)), title_id(title_id_), build_id(build_id_) {} - - DownloadResult DownloadDataZip() { - return DownloadInternal(fmt::format(BOXCAT_PATHNAME_DATA, title_id), TIMEOUT_SECONDS, - "application/zip"); - } - - DownloadResult DownloadLaunchParam() { - return DownloadInternal(fmt::format(BOXCAT_PATHNAME_LAUNCHPARAM, title_id), - TIMEOUT_SECONDS / 3, "application/octet-stream"); - } - -private: - DownloadResult DownloadInternal(const std::string& resolved_path, u32 timeout_seconds, - const std::string& content_type_name) { - if (client == nullptr) { - client = std::make_unique<httplib::SSLClient>(BOXCAT_HOSTNAME, PORT); - client->set_connection_timeout(timeout_seconds); - client->set_read_timeout(timeout_seconds); - client->set_write_timeout(timeout_seconds); - } - - httplib::Headers headers{ - {std::string("Game-Assets-API-Version"), std::string(BOXCAT_API_VERSION)}, - {std::string("Boxcat-Client-Type"), std::string(BOXCAT_CLIENT_TYPE)}, - {std::string("Game-Build-Id"), fmt::format("{:016X}", build_id)}, - }; - - if (Common::FS::Exists(path)) { - Common::FS::IOFile file{path, Common::FS::FileAccessMode::Read, - Common::FS::FileType::BinaryFile}; - if (file.IsOpen()) { - std::vector<u8> bytes(file.GetSize()); - void(file.Read(bytes)); - const auto digest = DigestFile(bytes); - headers.insert({std::string("If-None-Match"), Common::HexToString(digest, false)}); - } - } - - const auto response = client->Get(resolved_path.c_str(), headers); - if (response == nullptr) - return DownloadResult::NoResponse; - - if (response->status == static_cast<int>(ResponseStatus::NoUpdate)) - return DownloadResult::Success; - if (response->status == static_cast<int>(ResponseStatus::BadClientVersion)) - return DownloadResult::BadClientVersion; - if (response->status == static_cast<int>(ResponseStatus::NoMatchTitleId)) - return DownloadResult::NoMatchTitleId; - if (response->status == static_cast<int>(ResponseStatus::NoMatchBuildId)) - return DownloadResult::NoMatchBuildId; - if (response->status != static_cast<int>(ResponseStatus::Ok)) - return DownloadResult::GeneralWebError; - - const auto content_type = response->headers.find("content-type"); - if (content_type == response->headers.end() || - content_type->second.find(content_type_name) == std::string::npos) { - return DownloadResult::InvalidContentType; - } - - if (!Common::FS::CreateDirs(path)) { - return DownloadResult::GeneralFSError; - } - - Common::FS::IOFile file{path, Common::FS::FileAccessMode::Append, - Common::FS::FileType::BinaryFile}; - if (!file.IsOpen()) { - return DownloadResult::GeneralFSError; - } - - if (!file.SetSize(response->body.size())) { - return DownloadResult::GeneralFSError; - } - - if (file.Write(response->body) != response->body.size()) { - return DownloadResult::GeneralFSError; - } - - return DownloadResult::Success; - } - - using Digest = std::array<u8, 0x20>; - static Digest DigestFile(std::vector<u8> bytes) { - Digest out{}; - mbedtls_sha256_ret(bytes.data(), bytes.size(), out.data(), 0); - return out; - } - - std::unique_ptr<httplib::SSLClient> client; - std::filesystem::path path; - u64 title_id; - u64 build_id; -}; - -Boxcat::Boxcat(AM::Applets::AppletManager& applet_manager_, DirectoryGetter getter) - : Backend(std::move(getter)), applet_manager{applet_manager_} {} - -Boxcat::~Boxcat() = default; - -void SynchronizeInternal(AM::Applets::AppletManager& applet_manager, DirectoryGetter dir_getter, - TitleIDVersion title, ProgressServiceBackend& progress, - std::optional<std::string> dir_name = {}) { - progress.SetNeedHLELock(true); - - if (Settings::values.bcat_boxcat_local) { - LOG_INFO(Service_BCAT, "Boxcat using local data by override, skipping download."); - const auto dir = dir_getter(title.title_id); - if (dir) - progress.SetTotalSize(dir->GetSize()); - progress.FinishDownload(ResultSuccess); - return; - } - - const auto zip_path = GetZIPFilePath(title.title_id); - Boxcat::Client client{zip_path, title.title_id, title.build_id}; - - progress.StartConnecting(); - - const auto res = client.DownloadDataZip(); - if (res != DownloadResult::Success) { - LOG_ERROR(Service_BCAT, "Boxcat synchronization failed with error '{}'!", res); - - if (res == DownloadResult::NoMatchBuildId || res == DownloadResult::NoMatchTitleId) { - Common::FS::RemoveFile(zip_path); - } - - HandleDownloadDisplayResult(applet_manager, res); - progress.FinishDownload(ERROR_GENERAL_BCAT_FAILURE); - return; - } - - progress.StartProcessingDataList(); - - Common::FS::IOFile zip{zip_path, Common::FS::FileAccessMode::Read, - Common::FS::FileType::BinaryFile}; - const auto size = zip.GetSize(); - std::vector<u8> bytes(size); - if (!zip.IsOpen() || size == 0 || zip.Read(bytes) != bytes.size()) { - LOG_ERROR(Service_BCAT, "Boxcat failed to read ZIP file at path '{}'!", - Common::FS::PathToUTF8String(zip_path)); - progress.FinishDownload(ERROR_GENERAL_BCAT_FAILURE); - return; - } - - const auto extracted = FileSys::ExtractZIP(std::make_shared<FileSys::VectorVfsFile>(bytes)); - if (extracted == nullptr) { - LOG_ERROR(Service_BCAT, "Boxcat failed to extract ZIP file!"); - progress.FinishDownload(ERROR_GENERAL_BCAT_FAILURE); - return; - } - - if (dir_name == std::nullopt) { - progress.SetTotalSize(extracted->GetSize()); - - const auto target_dir = dir_getter(title.title_id); - if (target_dir == nullptr || !VfsRawCopyDProgress(extracted, target_dir, progress)) { - LOG_ERROR(Service_BCAT, "Boxcat failed to copy extracted ZIP to target directory!"); - progress.FinishDownload(ERROR_GENERAL_BCAT_FAILURE); - return; - } - } else { - const auto target_dir = dir_getter(title.title_id); - if (target_dir == nullptr) { - LOG_ERROR(Service_BCAT, "Boxcat failed to get directory for title ID!"); - progress.FinishDownload(ERROR_GENERAL_BCAT_FAILURE); - return; - } - - const auto target_sub = target_dir->GetSubdirectory(*dir_name); - const auto source_sub = extracted->GetSubdirectory(*dir_name); - - progress.SetTotalSize(source_sub->GetSize()); - - std::vector<std::string> filenames; - { - const auto files = target_sub->GetFiles(); - std::transform(files.begin(), files.end(), std::back_inserter(filenames), - [](const auto& vfile) { return vfile->GetName(); }); - } - - for (const auto& filename : filenames) { - VfsDeleteFileWrap(target_sub, filename); - } - - if (target_sub == nullptr || source_sub == nullptr || - !VfsRawCopyDProgressSingle(source_sub, target_sub, progress)) { - LOG_ERROR(Service_BCAT, "Boxcat failed to copy extracted ZIP to target directory!"); - progress.FinishDownload(ERROR_GENERAL_BCAT_FAILURE); - return; - } - } - - progress.FinishDownload(ResultSuccess); -} - -bool Boxcat::Synchronize(TitleIDVersion title, ProgressServiceBackend& progress) { - is_syncing.exchange(true); - - std::thread([this, title, &progress] { - SynchronizeInternal(applet_manager, dir_getter, title, progress); - }).detach(); - - return true; -} - -bool Boxcat::SynchronizeDirectory(TitleIDVersion title, std::string name, - ProgressServiceBackend& progress) { - is_syncing.exchange(true); - - std::thread([this, title, name, &progress] { - SynchronizeInternal(applet_manager, dir_getter, title, progress, name); - }).detach(); - - return true; -} - -bool Boxcat::Clear(u64 title_id) { - if (Settings::values.bcat_boxcat_local) { - LOG_INFO(Service_BCAT, "Boxcat using local data by override, skipping clear."); - return true; - } - - const auto dir = dir_getter(title_id); - - std::vector<std::string> dirnames; - - for (const auto& subdir : dir->GetSubdirectories()) - dirnames.push_back(subdir->GetName()); - - for (const auto& subdir : dirnames) { - if (!dir->DeleteSubdirectoryRecursive(subdir)) - return false; - } - - return true; -} - -void Boxcat::SetPassphrase(u64 title_id, const Passphrase& passphrase) { - LOG_DEBUG(Service_BCAT, "called, title_id={:016X}, passphrase={}", title_id, - Common::HexToString(passphrase)); -} - -std::optional<std::vector<u8>> Boxcat::GetLaunchParameter(TitleIDVersion title) { - const auto bin_file_path = GetBINFilePath(title.title_id); - - if (Settings::values.bcat_boxcat_local) { - LOG_INFO(Service_BCAT, "Boxcat using local data by override, skipping download."); - } else { - Client launch_client{bin_file_path, title.title_id, title.build_id}; - - const auto res = launch_client.DownloadLaunchParam(); - if (res != DownloadResult::Success) { - LOG_ERROR(Service_BCAT, "Boxcat synchronization failed with error '{}'!", res); - - if (res == DownloadResult::NoMatchBuildId || res == DownloadResult::NoMatchTitleId) { - Common::FS::RemoveFile(bin_file_path); - } - - HandleDownloadDisplayResult(applet_manager, res); - return std::nullopt; - } - } - - Common::FS::IOFile bin{bin_file_path, Common::FS::FileAccessMode::Read, - Common::FS::FileType::BinaryFile}; - const auto size = bin.GetSize(); - std::vector<u8> bytes(size); - if (!bin.IsOpen() || size == 0 || bin.Read(bytes) != bytes.size()) { - LOG_ERROR(Service_BCAT, "Boxcat failed to read launch parameter binary at path '{}'!", - Common::FS::PathToUTF8String(bin_file_path)); - return std::nullopt; - } - - return bytes; -} - -Boxcat::StatusResult Boxcat::GetStatus(std::optional<std::string>& global, - std::map<std::string, EventStatus>& games) { - httplib::SSLClient client{BOXCAT_HOSTNAME, static_cast<int>(PORT)}; - client.set_connection_timeout(static_cast<int>(TIMEOUT_SECONDS)); - client.set_read_timeout(static_cast<int>(TIMEOUT_SECONDS)); - client.set_write_timeout(static_cast<int>(TIMEOUT_SECONDS)); - - httplib::Headers headers{ - {std::string("Game-Assets-API-Version"), std::string(BOXCAT_API_VERSION)}, - {std::string("Boxcat-Client-Type"), std::string(BOXCAT_CLIENT_TYPE)}, - }; - - if (!client.is_valid()) { - LOG_ERROR(Service_BCAT, "Client is invalid, going offline!"); - return StatusResult::Offline; - } - - if (!client.is_socket_open()) { - LOG_ERROR(Service_BCAT, "Failed to open socket, going offline!"); - return StatusResult::Offline; - } - - const auto response = client.Get(BOXCAT_PATHNAME_EVENTS, headers); - if (response == nullptr) - return StatusResult::Offline; - - if (response->status == static_cast<int>(ResponseStatus::BadClientVersion)) - return StatusResult::BadClientVersion; - - try { - nlohmann::json json = nlohmann::json::parse(response->body); - - if (!json["online"].get<bool>()) - return StatusResult::Offline; - - if (json["global"].is_null()) - global = std::nullopt; - else - global = json["global"].get<std::string>(); - - if (json["games"].is_array()) { - for (const auto& object : json["games"]) { - if (object.is_object() && object.find("name") != object.end()) { - EventStatus detail{}; - if (object["header"].is_string()) { - detail.header = object["header"].get<std::string>(); - } else { - detail.header = std::nullopt; - } - - if (object["footer"].is_string()) { - detail.footer = object["footer"].get<std::string>(); - } else { - detail.footer = std::nullopt; - } - - if (object["events"].is_array()) { - for (const auto& event : object["events"]) { - if (!event.is_string()) - continue; - detail.events.push_back(event.get<std::string>()); - } - } - - games.insert_or_assign(object["name"], std::move(detail)); - } - } - } - - return StatusResult::Success; - } catch (const nlohmann::json::parse_error& error) { - LOG_ERROR(Service_BCAT, "{}", error.what()); - return StatusResult::ParseError; - } -} - -} // namespace Service::BCAT diff --git a/src/core/hle/service/bcat/backend/boxcat.h b/src/core/hle/service/bcat/backend/boxcat.h deleted file mode 100644 index d65b42e58..000000000 --- a/src/core/hle/service/bcat/backend/boxcat.h +++ /dev/null @@ -1,64 +0,0 @@ -// Copyright 2019 yuzu emulator team -// Licensed under GPLv2 or any later version -// Refer to the license.txt file included. - -#pragma once - -#include <atomic> -#include <map> -#include <optional> -#include "core/hle/service/bcat/backend/backend.h" - -namespace Service::AM::Applets { -class AppletManager; -} - -namespace Service::BCAT { - -struct EventStatus { - std::optional<std::string> header; - std::optional<std::string> footer; - std::vector<std::string> events; -}; - -/// Boxcat is yuzu's custom backend implementation of Nintendo's BCAT service. It is free to use and -/// doesn't require a switch or nintendo account. The content is controlled by the yuzu team. -class Boxcat final : public Backend { - friend void SynchronizeInternal(AM::Applets::AppletManager& applet_manager, - DirectoryGetter dir_getter, TitleIDVersion title, - ProgressServiceBackend& progress, - std::optional<std::string> dir_name); - -public: - explicit Boxcat(AM::Applets::AppletManager& applet_manager_, DirectoryGetter getter); - ~Boxcat() override; - - bool Synchronize(TitleIDVersion title, ProgressServiceBackend& progress) override; - bool SynchronizeDirectory(TitleIDVersion title, std::string name, - ProgressServiceBackend& progress) override; - - bool Clear(u64 title_id) override; - - void SetPassphrase(u64 title_id, const Passphrase& passphrase) override; - - std::optional<std::vector<u8>> GetLaunchParameter(TitleIDVersion title) override; - - enum class StatusResult { - Success, - Offline, - ParseError, - BadClientVersion, - }; - - static StatusResult GetStatus(std::optional<std::string>& global, - std::map<std::string, EventStatus>& games); - -private: - std::atomic_bool is_syncing{false}; - - class Client; - std::unique_ptr<Client> client; - AM::Applets::AppletManager& applet_manager; -}; - -} // namespace Service::BCAT diff --git a/src/core/hle/service/bcat/bcat_module.cpp b/src/core/hle/service/bcat/bcat_module.cpp index 72294eb2e..701f634f8 100644 --- a/src/core/hle/service/bcat/bcat_module.cpp +++ b/src/core/hle/service/bcat/bcat_module.cpp @@ -4,7 +4,6 @@ #include <cctype> #include <mbedtls/md5.h> -#include "backend/boxcat.h" #include "common/hex_util.h" #include "common/logging/log.h" #include "common/settings.h" @@ -578,12 +577,6 @@ void Module::Interface::CreateDeliveryCacheStorageServiceWithApplicationId( std::unique_ptr<Backend> CreateBackendFromSettings([[maybe_unused]] Core::System& system, DirectoryGetter getter) { -#ifdef YUZU_ENABLE_BOXCAT - if (Settings::values.bcat_backend.GetValue() == "boxcat") { - return std::make_unique<Boxcat>(system.GetAppletManager(), std::move(getter)); - } -#endif - return std::make_unique<NullBackend>(std::move(getter)); } diff --git a/src/core/network/network.cpp b/src/core/network/network.cpp index 72eea52f0..a3e0664b9 100644 --- a/src/core/network/network.cpp +++ b/src/core/network/network.cpp @@ -366,8 +366,6 @@ std::optional<IPv4Address> GetHostIPv4Address() { if (res != network_interfaces.end()) { char ip_addr[16] = {}; ASSERT(inet_ntop(AF_INET, &res->ip_address, ip_addr, sizeof(ip_addr)) != nullptr); - LOG_INFO(Network, "IP address: {}", ip_addr); - return TranslateIPv4(res->ip_address); } else { LOG_ERROR(Network, "Couldn't find selected interface \"{}\"", selected_network_interface); diff --git a/src/input_common/sdl/sdl_impl.cpp b/src/input_common/sdl/sdl_impl.cpp index 03888b7cb..ab6211b29 100644 --- a/src/input_common/sdl/sdl_impl.cpp +++ b/src/input_common/sdl/sdl_impl.cpp @@ -254,11 +254,25 @@ public: } bool IsJoyconLeft() const { - return std::strstr(GetControllerName().c_str(), "Joy-Con Left") != nullptr; + const std::string controller_name = GetControllerName(); + if (std::strstr(controller_name.c_str(), "Joy-Con Left") != nullptr) { + return true; + } + if (std::strstr(controller_name.c_str(), "Joy-Con (L)") != nullptr) { + return true; + } + return false; } bool IsJoyconRight() const { - return std::strstr(GetControllerName().c_str(), "Joy-Con Right") != nullptr; + const std::string controller_name = GetControllerName(); + if (std::strstr(controller_name.c_str(), "Joy-Con Right") != nullptr) { + return true; + } + if (std::strstr(controller_name.c_str(), "Joy-Con (R)") != nullptr) { + return true; + } + return false; } std::string GetControllerName() const { diff --git a/src/yuzu/CMakeLists.txt b/src/yuzu/CMakeLists.txt index b6dda283d..402be6a78 100644 --- a/src/yuzu/CMakeLists.txt +++ b/src/yuzu/CMakeLists.txt @@ -290,10 +290,6 @@ if (YUZU_USE_QT_WEB_ENGINE) target_compile_definitions(yuzu PRIVATE -DYUZU_USE_QT_WEB_ENGINE) endif () -if (YUZU_ENABLE_BOXCAT) - target_compile_definitions(yuzu PRIVATE -DYUZU_ENABLE_BOXCAT) -endif () - if(UNIX AND NOT APPLE) install(TARGETS yuzu RUNTIME DESTINATION "${CMAKE_INSTALL_PREFIX}/bin") endif() diff --git a/src/yuzu/applets/qt_web_browser.cpp b/src/yuzu/applets/qt_web_browser.cpp index 652d99570..7d433ca50 100644 --- a/src/yuzu/applets/qt_web_browser.cpp +++ b/src/yuzu/applets/qt_web_browser.cpp @@ -54,6 +54,9 @@ QtNXWebEngineView::QtNXWebEngineView(QWidget* parent, Core::System& system, input_interpreter(std::make_unique<InputInterpreter>(system)), default_profile{QWebEngineProfile::defaultProfile()}, global_settings{QWebEngineSettings::globalSettings()} { + default_profile->setPersistentStoragePath(QString::fromStdString(Common::FS::PathToUTF8String( + Common::FS::GetYuzuPath(Common::FS::YuzuPath::YuzuDir) / "qtwebengine"))); + QWebEngineScript gamepad; QWebEngineScript window_nx; diff --git a/src/yuzu/bootmanager.cpp b/src/yuzu/bootmanager.cpp index 1519a46ed..8b9e186b0 100644 --- a/src/yuzu/bootmanager.cpp +++ b/src/yuzu/bootmanager.cpp @@ -302,12 +302,17 @@ GRenderWindow::GRenderWindow(GMainWindow* parent, EmuThread* emu_thread_, connect(this, &GRenderWindow::FirstFrameDisplayed, parent, &GMainWindow::OnLoadComplete); connect(this, &GRenderWindow::ExecuteProgramSignal, parent, &GMainWindow::OnExecuteProgram, Qt::QueuedConnection); + connect(this, &GRenderWindow::ExitSignal, parent, &GMainWindow::OnExit, Qt::QueuedConnection); } void GRenderWindow::ExecuteProgram(std::size_t program_index) { emit ExecuteProgramSignal(program_index); } +void GRenderWindow::Exit() { + emit ExitSignal(); +} + GRenderWindow::~GRenderWindow() { input_subsystem->Shutdown(); } diff --git a/src/yuzu/bootmanager.h b/src/yuzu/bootmanager.h index 402dd2ee1..54c4e2142 100644 --- a/src/yuzu/bootmanager.h +++ b/src/yuzu/bootmanager.h @@ -181,6 +181,9 @@ public: */ void ExecuteProgram(std::size_t program_index); + /// Instructs the window to exit the application. + void Exit(); + public slots: void OnEmulationStarting(EmuThread* emu_thread); void OnEmulationStopping(); @@ -191,6 +194,7 @@ signals: void Closed(); void FirstFrameDisplayed(); void ExecuteProgramSignal(std::size_t program_index); + void ExitSignal(); void MouseActivity(); private: diff --git a/src/yuzu/configuration/config.cpp b/src/yuzu/configuration/config.cpp index b5796a8fc..eb941ce02 100644 --- a/src/yuzu/configuration/config.cpp +++ b/src/yuzu/configuration/config.cpp @@ -709,8 +709,6 @@ void Config::ReadDebuggingValues() { void Config::ReadServiceValues() { qt_config->beginGroup(QStringLiteral("Services")); - ReadBasicSetting(Settings::values.bcat_backend); - ReadBasicSetting(Settings::values.bcat_boxcat_local); ReadBasicSetting(Settings::values.network_interface); qt_config->endGroup(); } @@ -1269,8 +1267,6 @@ void Config::SaveDebuggingValues() { void Config::SaveNetworkValues() { qt_config->beginGroup(QStringLiteral("Services")); - WriteBasicSetting(Settings::values.bcat_backend); - WriteBasicSetting(Settings::values.bcat_boxcat_local); WriteBasicSetting(Settings::values.network_interface); qt_config->endGroup(); diff --git a/src/yuzu/configuration/configure_network.cpp b/src/yuzu/configuration/configure_network.cpp index ae22f1018..cc15d36c2 100644 --- a/src/yuzu/configuration/configure_network.cpp +++ b/src/yuzu/configuration/configure_network.cpp @@ -6,64 +6,25 @@ #include <QtConcurrent/QtConcurrent> #include "common/settings.h" #include "core/core.h" -#include "core/hle/service/bcat/backend/boxcat.h" #include "core/network/network_interface.h" #include "ui_configure_network.h" #include "yuzu/configuration/configure_network.h" -#ifdef YUZU_ENABLE_BOXCAT -namespace { -QString FormatEventStatusString(const Service::BCAT::EventStatus& status) { - QString out; - - if (status.header.has_value()) { - out += QStringLiteral("<i>%1</i><br>").arg(QString::fromStdString(*status.header)); - } - - if (status.events.size() == 1) { - out += QStringLiteral("%1<br>").arg(QString::fromStdString(status.events.front())); - } else { - for (const auto& event : status.events) { - out += QStringLiteral("- %1<br>").arg(QString::fromStdString(event)); - } - } - - if (status.footer.has_value()) { - out += QStringLiteral("<i>%1</i><br>").arg(QString::fromStdString(*status.footer)); - } - - return out; -} -} // Anonymous namespace -#endif - ConfigureNetwork::ConfigureNetwork(QWidget* parent) : QWidget(parent), ui(std::make_unique<Ui::ConfigureNetwork>()) { ui->setupUi(this); - ui->bcat_source->addItem(QStringLiteral("None")); - ui->bcat_empty_label->setHidden(true); - ui->bcat_empty_header->setHidden(true); - -#ifdef YUZU_ENABLE_BOXCAT - ui->bcat_source->addItem(QStringLiteral("Boxcat"), QStringLiteral("boxcat")); -#endif - ui->network_interface->addItem(tr("None")); for (const auto& iface : Network::GetAvailableNetworkInterfaces()) { ui->network_interface->addItem(QString::fromStdString(iface.name)); } - connect(ui->bcat_source, QOverload<int>::of(&QComboBox::currentIndexChanged), this, - &ConfigureNetwork::OnBCATImplChanged); - this->SetConfiguration(); } ConfigureNetwork::~ConfigureNetwork() = default; void ConfigureNetwork::ApplyConfiguration() { - Settings::values.bcat_backend = ui->bcat_source->currentText().toLower().toStdString(); Settings::values.network_interface = ui->network_interface->currentText().toStdString(); } @@ -74,86 +35,8 @@ void ConfigureNetwork::RetranslateUi() { void ConfigureNetwork::SetConfiguration() { const bool runtime_lock = !Core::System::GetInstance().IsPoweredOn(); - const int index = - ui->bcat_source->findData(QString::fromStdString(Settings::values.bcat_backend.GetValue())); - ui->bcat_source->setCurrentIndex(index == -1 ? 0 : index); - const std::string& network_interface = Settings::values.network_interface.GetValue(); ui->network_interface->setCurrentText(QString::fromStdString(network_interface)); ui->network_interface->setEnabled(runtime_lock); } - -std::pair<QString, QString> ConfigureNetwork::BCATDownloadEvents() { -#ifdef YUZU_ENABLE_BOXCAT - std::optional<std::string> global; - std::map<std::string, Service::BCAT::EventStatus> map; - const auto res = Service::BCAT::Boxcat::GetStatus(global, map); - - switch (res) { - case Service::BCAT::Boxcat::StatusResult::Success: - break; - case Service::BCAT::Boxcat::StatusResult::Offline: - return {QString{}, - tr("The boxcat service is offline or you are not connected to the internet.")}; - case Service::BCAT::Boxcat::StatusResult::ParseError: - return {QString{}, - tr("There was an error while processing the boxcat event data. Contact the yuzu " - "developers.")}; - case Service::BCAT::Boxcat::StatusResult::BadClientVersion: - return {QString{}, - tr("The version of yuzu you are using is either too new or too old for the server. " - "Try updating to the latest official release of yuzu.")}; - } - - if (map.empty()) { - return {QStringLiteral("Current Boxcat Events"), - tr("There are currently no events on boxcat.")}; - } - - QString out; - - if (global.has_value()) { - out += QStringLiteral("%1<br>").arg(QString::fromStdString(*global)); - } - - for (const auto& [key, value] : map) { - out += QStringLiteral("%1<b>%2</b><br>%3") - .arg(out.isEmpty() ? QString{} : QStringLiteral("<br>")) - .arg(QString::fromStdString(key)) - .arg(FormatEventStatusString(value)); - } - return {tr("Current Boxcat Events"), std::move(out)}; -#else - return {tr("Current Boxcat Events"), tr("There are currently no events on boxcat.")}; -#endif -} - -void ConfigureNetwork::OnBCATImplChanged() { -#ifdef YUZU_ENABLE_BOXCAT - const auto boxcat = ui->bcat_source->currentText() == QStringLiteral("Boxcat"); - ui->bcat_empty_header->setHidden(!boxcat); - ui->bcat_empty_label->setHidden(!boxcat); - ui->bcat_empty_header->setText(QString{}); - ui->bcat_empty_label->setText(tr("Yuzu is retrieving the latest boxcat status...")); - - if (!boxcat) - return; - - const auto future = QtConcurrent::run([this] { return BCATDownloadEvents(); }); - - watcher.setFuture(future); - connect(&watcher, &QFutureWatcher<std::pair<QString, QString>>::finished, this, - [this] { OnUpdateBCATEmptyLabel(watcher.result()); }); -#endif -} - -void ConfigureNetwork::OnUpdateBCATEmptyLabel(std::pair<QString, QString> string) { -#ifdef YUZU_ENABLE_BOXCAT - const auto boxcat = ui->bcat_source->currentText() == QStringLiteral("Boxcat"); - if (boxcat) { - ui->bcat_empty_header->setText(string.first); - ui->bcat_empty_label->setText(string.second); - } -#endif -} diff --git a/src/yuzu/configuration/configure_network.h b/src/yuzu/configuration/configure_network.h index 442b68e6b..028fd4acc 100644 --- a/src/yuzu/configuration/configure_network.h +++ b/src/yuzu/configuration/configure_network.h @@ -25,10 +25,5 @@ public: private: void SetConfiguration(); - std::pair<QString, QString> BCATDownloadEvents(); - void OnBCATImplChanged(); - void OnUpdateBCATEmptyLabel(std::pair<QString, QString> string); - std::unique_ptr<Ui::ConfigureNetwork> ui; - QFutureWatcher<std::pair<QString, QString>> watcher{this}; }; diff --git a/src/yuzu/configuration/configure_network.ui b/src/yuzu/configuration/configure_network.ui index 5f9b7e97b..9a79262f0 100644 --- a/src/yuzu/configuration/configure_network.ui +++ b/src/yuzu/configuration/configure_network.ui @@ -35,92 +35,6 @@ </layout> </widget> </item> - <item> - <widget class="QGroupBox" name="groupBox"> - <property name="title"> - <string>BCAT</string> - </property> - <layout class="QGridLayout" name="gridLayout"> - <item row="3" column="0"> - <widget class="QLabel" name="bcat_empty_header"> - <property name="text"> - <string/> - </property> - <property name="alignment"> - <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> - </property> - <property name="wordWrap"> - <bool>true</bool> - </property> - </widget> - </item> - <item row="0" column="0"> - <widget class="QLabel" name="label"> - <property name="maximumSize"> - <size> - <width>16777215</width> - <height>16777215</height> - </size> - </property> - <property name="text"> - <string>BCAT Backend</string> - </property> - </widget> - </item> - <item row="1" column="1" colspan="2"> - <widget class="QLabel" name="label_2"> - <property name="maximumSize"> - <size> - <width>260</width> - <height>16777215</height> - </size> - </property> - <property name="text"> - <string>BCAT is Nintendo's way of sending data to games to engage its community and unlock additional content.</string> - </property> - <property name="wordWrap"> - <bool>true</bool> - </property> - </widget> - </item> - <item row="2" column="1" colspan="2"> - <widget class="QLabel" name="label_3"> - <property name="text"> - <string><html><head/><body><p><a href="https://yuzu-emu.org/help/feature/boxcat"><span style=" text-decoration: underline; color:#0000ff;">Learn more about BCAT, Boxcat, and Current Events</span></a></p></body></html></string> - </property> - <property name="openExternalLinks"> - <bool>true</bool> - </property> - </widget> - </item> - <item row="0" column="1" colspan="2"> - <widget class="QComboBox" name="bcat_source"/> - </item> - <item row="3" column="1" colspan="2"> - <widget class="QLabel" name="bcat_empty_label"> - <property name="enabled"> - <bool>true</bool> - </property> - <property name="maximumSize"> - <size> - <width>260</width> - <height>16777215</height> - </size> - </property> - <property name="text"> - <string/> - </property> - <property name="alignment"> - <set>Qt::AlignLeading|Qt::AlignLeft|Qt::AlignTop</set> - </property> - <property name="wordWrap"> - <bool>true</bool> - </property> - </widget> - </item> - </layout> - </widget> - </item> </layout> </item> <item> diff --git a/src/yuzu/main.cpp b/src/yuzu/main.cpp index 7eec8f5bb..552c2cc63 100644 --- a/src/yuzu/main.cpp +++ b/src/yuzu/main.cpp @@ -1384,6 +1384,9 @@ void GMainWindow::BootGame(const QString& filename, u64 program_id, std::size_t system.RegisterExecuteProgramCallback( [this](std::size_t program_index) { render_window->ExecuteProgram(program_index); }); + // Register an Exit callback such that Core can exit the currently running application. + system.RegisterExitCallback([this]() { render_window->Exit(); }); + connect(render_window, &GRenderWindow::Closed, this, &GMainWindow::OnStopGame); connect(render_window, &GRenderWindow::MouseActivity, this, &GMainWindow::OnMouseActivity); // BlockingQueuedConnection is important here, it makes sure we've finished refreshing our views @@ -2469,6 +2472,10 @@ void GMainWindow::OnExecuteProgram(std::size_t program_index) { BootGame(last_filename_booted, 0, program_index); } +void GMainWindow::OnExit() { + OnStopGame(); +} + void GMainWindow::ErrorDisplayDisplayError(QString error_code, QString error_text) { OverlayDialog dialog(render_window, Core::System::GetInstance(), error_code, error_text, QString{}, tr("OK"), Qt::AlignLeft | Qt::AlignVCenter); diff --git a/src/yuzu/main.h b/src/yuzu/main.h index 36eed6103..60ce01471 100644 --- a/src/yuzu/main.h +++ b/src/yuzu/main.h @@ -153,6 +153,7 @@ signals: public slots: void OnLoadComplete(); void OnExecuteProgram(std::size_t program_index); + void OnExit(); void ControllerSelectorReconfigureControllers( const Core::Frontend::ControllerParameters& parameters); void SoftwareKeyboardInitialize( diff --git a/src/yuzu_cmd/config.cpp b/src/yuzu_cmd/config.cpp index d74eb7e2b..434518d53 100644 --- a/src/yuzu_cmd/config.cpp +++ b/src/yuzu_cmd/config.cpp @@ -518,10 +518,6 @@ void Config::ReadValues() { ReadSetting("WebService", Settings::values.web_api_url); ReadSetting("WebService", Settings::values.yuzu_username); ReadSetting("WebService", Settings::values.yuzu_token); - - // Services - ReadSetting("Services", Settings::values.bcat_backend); - ReadSetting("Services", Settings::values.bcat_boxcat_local); } void Config::Reload() { diff --git a/src/yuzu_cmd/default_ini.h b/src/yuzu_cmd/default_ini.h index 72f3213fb..8119a50d8 100644 --- a/src/yuzu_cmd/default_ini.h +++ b/src/yuzu_cmd/default_ini.h @@ -428,11 +428,6 @@ web_api_url = https://api.yuzu-emu.org yuzu_username = yuzu_token = -[Services] -# The name of the backend to use for BCAT -# If this is set to 'boxcat' boxcat will be used, otherwise a null implementation will be used -bcat_backend = - [AddOns] # Used to disable add-ons # List of title IDs of games that will have add-ons disabled (separated by '|'): |