diff --git a/CMakeLists.txt b/CMakeLists.txt index 624bec17..7fef0f12 100644 --- a/CMakeLists.txt +++ b/CMakeLists.txt @@ -193,9 +193,21 @@ SET(VBAMCORE_LIBS ) if(ENABLE_FFMPEG) - FIND_PACKAGE ( PkgConfig REQUIRED ) + FIND_PACKAGE(PkgConfig REQUIRED) PKG_CHECK_MODULES(FFMPEG REQUIRED libavcodec libavformat libswscale libavutil) + + if(FFMPEG_STATIC) + set(FFMPEG_LIBRARIES ${FFMPEG_STATIC_LIBRARIES}) + set(FFMPEG_LDFLAGS ${FFMPEG_STATIC_LDFLAGS} ${FFMPEG_STATIC_OTHER_LDFLAGS}) + + if(APPLE) + set(FFMPEG_LDFLAGS ${FFMPEG_LDFLAGS} -framework CoreText -framework ApplicationServices) + endif() + else() + set(FFMPEG_LIBRARIES ${FFMPEG_LIBRARIES}) + set(FFMPEG_LDFLAGS ${FFMPEG_LDFLAGS} ${FFMPEG_OTHER_LDFLAGS}) + endif() endif(ENABLE_FFMPEG) if(NOT ENABLE_FFMPEG) diff --git a/README.md b/README.md index 48f07c72..fe76aeb3 100644 --- a/README.md +++ b/README.md @@ -118,24 +118,26 @@ cmake .. -DCMAKE_BUILD_TYPE=Debug Here is the complete list: -| **CMake Option** | **What it Does** | **Defaults** | -|----------------------|----------------------------------------------------------------------|-----------------------| -| ENABLE_SDL | Build the SDL port | OFF | -| ENABLE_WX | Build the wxWidgets port | ON | -| ENABLE_DEBUGGER | Enable the debugger | ON | -| ENABLE_NLS | Enable translations | ON | -| ENABLE_ASM_CORE | Enable x86 ASM CPU cores (**BUGGY AND DANGEROUS**) | OFF | -| ENABLE_ASM | Enable the following two ASM options | ON for 32 bit builds | -| ENABLE_ASM_SCALERS | Enable x86 ASM graphic filters | ON for 32 bit builds | -| ENABLE_MMX | Enable MMX | ON for 32 bit builds | -| ENABLE_LINK | Enable GBA linking functionality (requires SFML) | ON | -| ENABLE_LIRC | Enable LIRC support | OFF | -| ENABLE_FFMPEG | Enable ffmpeg A/V recording | ON on Linux and MSys2 | -| ENABLE_LTO | Compile with Link Time Optimization (gcc and clang only) | ON for release build | -| ENABLE_GBA_LOGGING | Enable extended GBA logging | ON | -| ENABLE_DIRECT3D | Direct3D rendering for wxWidgets (Windows, **NOT IMPLEMENTED!!!**) | ON | -| ENABLE_XAUDIO2 | Enable xaudio2 sound output for wxWidgets (Windows only) | ON | -| ENABLE_OPENAL | Enable OpenAL for the wxWidgets port | ON | +| **CMake Option** | **What it Does** | **Defaults** | +|-----------------------|----------------------------------------------------------------------|-----------------------| +| ENABLE_SDL | Build the SDL port | OFF | +| ENABLE_WX | Build the wxWidgets port | ON | +| ENABLE_DEBUGGER | Enable the debugger | ON | +| ENABLE_NLS | Enable translations | ON | +| ENABLE_ASM_CORE | Enable x86 ASM CPU cores (**BUGGY AND DANGEROUS**) | OFF | +| ENABLE_ASM | Enable the following two ASM options | ON for 32 bit builds | +| ENABLE_ASM_SCALERS | Enable x86 ASM graphic filters | ON for 32 bit builds | +| ENABLE_MMX | Enable MMX | ON for 32 bit builds | +| ENABLE_LINK | Enable GBA linking functionality (requires SFML) | ON | +| ENABLE_LIRC | Enable LIRC support | OFF | +| ENABLE_FFMPEG | Enable ffmpeg A/V recording | ON on Linux and MSys2 | +| ENABLE_LTO | Compile with Link Time Optimization (gcc and clang only) | ON for release build | +| ENABLE_GBA_LOGGING | Enable extended GBA logging | ON | +| ENABLE_DIRECT3D | Direct3D rendering for wxWidgets (Windows, **NOT IMPLEMENTED!!!**) | ON | +| ENABLE_XAUDIO2 | Enable xaudio2 sound output for wxWidgets (Windows only) | ON | +| ENABLE_OPENAL | Enable OpenAL for the wxWidgets port | ON | +| SFML_STATIC_LIBRARIES | Set this to ON if linking static SFML libraries | OFF | +| FFMPEG_STATIC | Set this to ON if linking static ffmpeg librariesl | OFF | Note for distro packagers, we use the CMake module [GNUInstallDirs](https://cmake.org/cmake/help/v2.8.12/cmake.html#module:GNUInstallDirs) diff --git a/cmake/VbamFunctions.cmake b/cmake/VbamFunctions.cmake new file mode 100644 index 00000000..522aa59f --- /dev/null +++ b/cmake/VbamFunctions.cmake @@ -0,0 +1,6 @@ +# From: https://stackoverflow.com/a/7216542 +function(JOIN VALUES GLUE OUTPUT) + string (REGEX REPLACE "([^\\]|^);" "\\1${GLUE}" _TMP_STR "${VALUES}") + string (REGEX REPLACE "[\\](.)" "\\1" _TMP_STR "${_TMP_STR}") #fixes escaping + set (${OUTPUT} "${_TMP_STR}" PARENT_SCOPE) +endfunction() diff --git a/src/wx/CMakeLists.txt b/src/wx/CMakeLists.txt index a78a06a5..1fe94750 100644 --- a/src/wx/CMakeLists.txt +++ b/src/wx/CMakeLists.txt @@ -5,6 +5,8 @@ IF(NOT CMAKE_VERSION VERSION_LESS 3.0) cmake_policy(SET CMP0043 NEW) # for wxWidgets ENDIF() +include(VbamFunctions) + if( WIN32 ) # not yet implemented option( ENABLE_DIRECT3D "Enable Direct3D rendering for the wxWidgets port" ON ) @@ -511,6 +513,13 @@ TARGET_LINK_LIBRARIES ( ${OPENAL_LIBRARY} ) +join("${FFMPEG_LDFLAGS}" " " FFMPEG_LDFLAGS_STR) + +set_target_properties( + visualboyadvance-m + PROPERTIES LINK_FLAGS ${FFMPEG_LDFLAGS_STR} +) + # Build a console app in debug mode on Windows IF(WIN32 AND CMAKE_BUILD_TYPE STREQUAL Debug) SET(CMAKE_CXX_LINK_EXECUTABLE "${CMAKE_CXX_LINK_EXECUTABLE} -Wl,--subsystem,console") @@ -535,14 +544,6 @@ if(APPLE) ADD_CUSTOM_COMMAND(TARGET visualboyadvance-m POST_BUILD COMMAND ${CMAKE_SOURCE_DIR}/tools/osx/third_party_libs_tool ./visualboyadvance-m.app WORKING_DIRECTORY "${CMAKE_BINARY_DIR}") - - ADD_CUSTOM_COMMAND(TARGET visualboyadvance-m POST_BUILD - COMMAND codesign -s "Developer ID Application" --deep ./visualboyadvance-m.app - WORKING_DIRECTORY "${CMAKE_BINARY_DIR}") - - ADD_CUSTOM_COMMAND(TARGET visualboyadvance-m POST_BUILD - COMMAND zip -9r ./visualboyadvance-m-Mac.zip ./visualboyadvance-m.app - WORKING_DIRECTORY "${CMAKE_BINARY_DIR}") ENDIF() endif(APPLE) diff --git a/tools/osx/builder b/tools/osx/builder index f2b324dc..750feebd 100755 --- a/tools/osx/builder +++ b/tools/osx/builder @@ -4,43 +4,140 @@ set -e BUILD_ROOT=$HOME/vbam-build -# build env +build_env() { + cat </dev/null; then - glibtoolize - else - libtoolize - fi - - autoheader - autoconf - [ -e Makefile.am ] && automake --add-missing - fi - - ./configure $(dist_args "$dist" autoconf) - make -j$NUM_CPUS - make install prefix=$BUILD_ROOT/root - - echo "\nDone!!!\n" - elif [ -e CMakeLists.txt ]; then - echo "\nBuilding $dist\n" - - mkdir -p build - cd build - - cmake .. $(dist_args "$dist" cmake) - make -j$NUM_CPUS - rm -rf destdir - mkdir destdir - make install DESTDIR="$PWD/destdir" - - cd "$PWD/destdir/$BUILD_ROOT/root" - find . ! -type d | (cd "$BUILD_ROOT/root"; IFS=' -'; while read f; do - mkdir -p "${f%/*}" - cp -a "$BUILD_ROOT/libs/$dist/build/destdir/$BUILD_ROOT/root/$f" "$f" - done) - - cd "$BUILD_ROOT/libs/$dist" - - echo "\nDone!!!\n" - fi - - cd .. + if [ ! -e "$install_artifact" ]; then + build_dist $(list_get $i $DIST_NAMES) fi i=$((i + 1)) done } +build_dist() { + dist=$1 + [ -n "$1" ] || error 'build_dist: dist name required' + shift + extra_dist_args=$@ + + cd "$BUILD_ROOT/dists/$dist" + + echo "\nBuilding $dist\n" + + ORIG_LDFLAGS=$LDFLAGS + + # have to make sure C++ flags are passed when linking, but only for C++ and **NOT** C + # this fails if there are any .c files in the project + if [ "$(find . -name '*.cpp' -o -name '*.cc' | wc -l)" -ne 0 -a "$(find . -name '*.c' | wc -l)" -eq 0 ]; then + export LDFLAGS="$CXXFLAGS $LDFLAGS" + fi + + dist_patch "$dist" + dist_pre_build "$dist" + + if [ -e configure -o -e configure.ac -o -e configure.in -o -e Makefile.am ]; then + if [ ! -e configure ]; then + if [ -e autogen.sh ]; then + sh autogen.sh + elif [ -e buildconf.sh ]; then + sh buildconf.sh + else + if [ -d m4 ]; then + aclocal -I m4 + else + aclocal + fi + + if command -v glibtoolize >/dev/null; then + glibtoolize + else + libtoolize + fi + + autoheader || : + autoconf + [ -e Makefile.am ] && automake --add-missing + fi + fi + + eval "set -- $(dist_args "$dist" autoconf) $extra_dist_args" + ./configure "$@" + eval "set -- $(dist_make_args "$dist")" + make -j$NUM_CPUS "$@" + make install prefix=$BUILD_ROOT/root + elif [ -e CMakeLists.txt ]; then + mkdir -p build + cd build + + eval "set -- $(dist_args "$dist" cmake) $extra_dist_args" + cmake .. "$@" + eval "set -- $(dist_make_args "$dist")" + make -j$NUM_CPUS "$@" + rm -rf destdir + mkdir destdir + make install DESTDIR="$PWD/destdir" + + cd "destdir/$BUILD_ROOT/root" + OLDPWD=$PWD + find . ! -type d | (cd "$BUILD_ROOT/root";IFS=' +'; while read f; do + mkdir -p "${f%/*}" + cp -a "$OLDPWD/$f" "$f" + done) + elif [ -e Makefile.PL ]; then + eval "set -- $(dist_args "$dist" perl) $extra_dist_args" + perl Makefile.PL "$@" + eval "set -- $(dist_make_args "$dist")" + make -j$NUM_CPUS "$@" + make install + elif [ -e Makefile ]; then + eval "set -- $(dist_make_args "$dist")" + make -j$NUM_CPUS "$@" + make install PREFIX="$BUILD_ROOT/root" INSTALL_ROOT="$BUILD_ROOT/root" + else + error "don't know how to build $dist" + fi + + dist_post_build "$dist" + + export LDFLAGS=$ORIG_LDFLAGS + + echo "\nDone!!!\n" +} + list_get() { i=0 n=${1:=0} @@ -213,10 +377,15 @@ list_get() { dist_args() { dist=$1 - [ -n "$dist" ] || error 'dist name required' + [ -n "$dist" ] || error 'dist_args: dist name required' buildsys=$2 - [ "$buildsys" = autoconf -o "$buildsys" = cmake ] || \ - error "buildsystem type required, must be 'autoconf' or 'cmake'" + case "$buildsys" in + autoconf|cmake|perl) + ;; + *) + error "dist_args: buildsystem type required, must be 'autoconf', 'cmake' or 'perl'" + ;; + esac args=$(table_line "$dist" "$DIST_OVERRIDES") @@ -228,6 +397,9 @@ dist_args() { cmake) args="$CMAKE_ARGS $(table_line "$dist" "$DIST_ARGS")" ;; + perl) + args="$(table_line "$dist" "$DIST_ARGS")" + ;; esac fi @@ -236,12 +408,66 @@ dist_args() { return 0 } +dist_make_args() { + dist=$1 + [ -n "$dist" ] || error 'dist_make_args: dist name required' + + echo "$(table_line "$dist" "$DIST_MAKE_ARGS")" + + return 0 +} + +dist_patch() { + [ -n "$1" ] || error 'dist_patch: dist name required' + + _patch_url="$(table_line "$1" "$DIST_PATCHES")" + + [ -n "$_patch_url" ] || return 0 + + echo "\nApplying patch $_patch_url to $1\n" + + curl -LO "$_patch_url" + patch -p1 < "${_patch_url##*/}" + + echo "\nDone!!!\n" +} + +dist_pre_build() { + [ -n "$1" ] || error 'dist_pre_build: dist name required' + + _cmd=$(table_line "$1" "$DIST_PRE_BUILD") + [ -n "$_cmd" ] || return 0 + + echo "\nRunning pre-build for: $dist:\n$_cmd\n" + + eval "$_cmd" +} + +dist_post_build() { + [ -n "$1" ] || error 'dist_post_build: dist name required' + + _cmd=$(table_line "$1" "$DIST_POST_BUILD") + [ -n "$_cmd" ] || return 0 + + if [ -z "$IN_DIST_POST_BUILD" ]; then + IN_DIST_POST_BUILD=1 + + echo "\nRunning post-build for: $dist:\n$_cmd\n" + + eval "$_cmd" + + IN_DIST_POST_BUILD= + fi +} + table_line() { name=$1 [ -n "$name" ] || error 'item name required' table=$2 [ -n "$table" ] || error 'table string required' + table=$(echo "$table" | grep -Ev '^ *#') + OLDIFS=$IFS IFS=' ' @@ -274,7 +500,7 @@ find_checkout() { } error() { - printf >&2 '\nERROR: %s.\n\n' "$1" + printf >&2 '\nERROR: %s\n\n' "$1" [ -z "$2" ] && exit 1 } @@ -284,9 +510,14 @@ build_project() { mkdir -p "$BUILD_ROOT/project" cd "$BUILD_ROOT/project" - cmake "$CHECKOUT" -DCMAKE_PREFIX_PATH="$BUILD_ROOT/root" -DENABLE_FFMPEG=OFF -DSFML_STATIC_LIBRARIES=TRUE + cmake "$CHECKOUT" -DCMAKE_PREFIX_PATH="$BUILD_ROOT/root" -DCMAKE_BUILD_TYPE=Release -DSFML_STATIC_LIBRARIES=TRUE -DENABLE_FFMPEG=ON -DFFMPEG_STATIC=TRUE make -j$NUM_CPUS + codesign -s "Developer ID Application" --deep ./visualboyadvance-m.app || : + + rm -f ./visualboyadvance-m-Mac.zip + zip -9r ./visualboyadvance-m-Mac.zip ./visualboyadvance-m.app + echo "\nBuild Successful!!!\n\nBuild results can be found in: $BUILD_ROOT/project\n" } @@ -298,6 +529,8 @@ table_column() { table=$3 [ -n "$table" ] || error 'table_column: table required' + table=$(echo "$table" | grep -Ev '^ *#') + i=0 res= for item in $table; do @@ -316,6 +549,8 @@ table_rows() { table=$1 [ -n "$table" ] || error 'table_rows: table required' + table=$(echo "$table" | grep -Ev '^ *#') + i=0 OLDIFS=$IFS IFS='