electrum

Electrum Bitcoin wallet
git clone https://git.parazyd.org/electrum
Log | Files | Refs | Submodules

prepare-wine.sh (5608B)


      1 #!/bin/bash
      2 
      3 # Please update these carefully, some versions won't work under Wine
      4 NSIS_FILENAME=nsis-3.05-setup.exe
      5 NSIS_URL=https://downloads.sourceforge.net/project/nsis/NSIS%203/3.05/$NSIS_FILENAME
      6 NSIS_SHA256=1a3cc9401667547b9b9327a177b13485f7c59c2303d4b6183e7bc9e6c8d6bfdb
      7 
      8 LIBUSB_REPO="https://github.com/libusb/libusb.git"
      9 LIBUSB_COMMIT="c6a35c56016ea2ab2f19115d2ea1e85e0edae155"
     10 # ^ tag v1.0.24
     11 
     12 PYINSTALLER_REPO="https://github.com/SomberNight/pyinstaller.git"
     13 PYINSTALLER_COMMIT="80ee4d613ecf75a1226b960a560ee01459e65ddb"
     14 # ^ tag 4.2, plus a custom commit that fixes cross-compilation with MinGW
     15 
     16 PYTHON_VERSION=3.8.7
     17 
     18 
     19 # Let's begin!
     20 set -e
     21 
     22 here="$(dirname "$(readlink -e "$0")")"
     23 
     24 . "$CONTRIB"/build_tools_util.sh
     25 
     26 info "Booting wine."
     27 wine 'wineboot'
     28 
     29 
     30 cd "$CACHEDIR"
     31 mkdir -p $WINEPREFIX/drive_c/tmp
     32 
     33 info "Installing Python."
     34 # note: you might need "sudo apt-get install dirmngr" for the following
     35 # keys from https://www.python.org/downloads/#pubkeys
     36 KEYRING_PYTHON_DEV="keyring-electrum-build-python-dev.gpg"
     37 gpg --no-default-keyring --keyring $KEYRING_PYTHON_DEV --import "$here"/gpg_keys/7ED10B6531D7C8E1BC296021FC624643487034E5.asc
     38 if [ "$WIN_ARCH" = "win32" ] ; then
     39     PYARCH="win32"
     40 elif [ "$WIN_ARCH" = "win64" ] ; then
     41     PYARCH="amd64"
     42 else
     43     fail "unexpected WIN_ARCH: $WIN_ARCH"
     44 fi
     45 PYTHON_DOWNLOADS="$CACHEDIR/python$PYTHON_VERSION"
     46 mkdir -p "$PYTHON_DOWNLOADS"
     47 for msifile in core dev exe lib pip tools; do
     48     echo "Installing $msifile..."
     49     download_if_not_exist "$PYTHON_DOWNLOADS/${msifile}.msi" "https://www.python.org/ftp/python/$PYTHON_VERSION/$PYARCH/${msifile}.msi"
     50     download_if_not_exist "$PYTHON_DOWNLOADS/${msifile}.msi.asc" "https://www.python.org/ftp/python/$PYTHON_VERSION/$PYARCH/${msifile}.msi.asc"
     51     verify_signature "$PYTHON_DOWNLOADS/${msifile}.msi.asc" $KEYRING_PYTHON_DEV
     52     wine msiexec /i "$PYTHON_DOWNLOADS/${msifile}.msi" /qb TARGETDIR=$WINE_PYHOME
     53 done
     54 
     55 break_legacy_easy_install
     56 
     57 info "Installing build dependencies."
     58 $WINE_PYTHON -m pip install --no-dependencies --no-warn-script-location \
     59     --cache-dir "$WINE_PIP_CACHE_DIR" -r "$CONTRIB"/deterministic-build/requirements-build-wine.txt
     60 
     61 info "Installing NSIS."
     62 download_if_not_exist "$CACHEDIR/$NSIS_FILENAME" "$NSIS_URL"
     63 verify_hash "$CACHEDIR/$NSIS_FILENAME" "$NSIS_SHA256"
     64 wine "$CACHEDIR/$NSIS_FILENAME" /S
     65 
     66 
     67 info "Compiling libusb..."
     68 (
     69     cd "$CACHEDIR"
     70     if [ -f "libusb/libusb/.libs/libusb-1.0.dll" ]; then
     71         info "libusb-1.0.dll already built, skipping"
     72         exit 0
     73     fi
     74     rm -rf libusb
     75     mkdir libusb
     76     cd libusb
     77     # Shallow clone
     78     git init
     79     git remote add origin $LIBUSB_REPO
     80     git fetch --depth 1 origin $LIBUSB_COMMIT
     81     git checkout -b pinned "${LIBUSB_COMMIT}^{commit}"
     82     echo "libusb_1_0_la_LDFLAGS += -Wc,-static" >> libusb/Makefile.am
     83     ./bootstrap.sh || fail "Could not bootstrap libusb"
     84     host="$GCC_TRIPLET_HOST"
     85     LDFLAGS="-Wl,--no-insert-timestamp" ./configure \
     86         --host=$host \
     87         --build=$GCC_TRIPLET_BUILD || fail "Could not run ./configure for libusb"
     88     make -j4 || fail "Could not build libusb"
     89     ${host}-strip libusb/.libs/libusb-1.0.dll
     90 ) || fail "libusb build failed"
     91 cp "$CACHEDIR/libusb/libusb/.libs/libusb-1.0.dll" $WINEPREFIX/drive_c/tmp/  || fail "Could not copy libusb to its destination"
     92 
     93 
     94 # copy already built DLLs
     95 cp "$DLL_TARGET_DIR/libsecp256k1-0.dll" $WINEPREFIX/drive_c/tmp/ || fail "Could not copy libsecp to its destination"
     96 cp "$DLL_TARGET_DIR/libzbar-0.dll" $WINEPREFIX/drive_c/tmp/ || fail "Could not copy libzbar to its destination"
     97 
     98 
     99 info "Building PyInstaller."
    100 # we build our own PyInstaller boot loader as the default one has high
    101 # anti-virus false positives
    102 (
    103     if [ "$WIN_ARCH" = "win32" ] ; then
    104         PYINST_ARCH="32bit"
    105     elif [ "$WIN_ARCH" = "win64" ] ; then
    106         PYINST_ARCH="64bit"
    107     else
    108         fail "unexpected WIN_ARCH: $WIN_ARCH"
    109     fi
    110     if [ -f "$CACHEDIR/pyinstaller/PyInstaller/bootloader/Windows-$PYINST_ARCH/runw.exe" ]; then
    111         info "pyinstaller already built, skipping"
    112         exit 0
    113     fi
    114     cd "$WINEPREFIX/drive_c/electrum"
    115     ELECTRUM_COMMIT_HASH=$(git rev-parse HEAD)
    116     cd "$CACHEDIR"
    117     rm -rf pyinstaller
    118     mkdir pyinstaller
    119     cd pyinstaller
    120     # Shallow clone
    121     git init
    122     git remote add origin $PYINSTALLER_REPO
    123     git fetch --depth 1 origin $PYINSTALLER_COMMIT
    124     git checkout -b pinned "${PYINSTALLER_COMMIT}^{commit}"
    125     rm -fv PyInstaller/bootloader/Windows-*/run*.exe || true
    126     # add reproducible randomness. this ensures we build a different bootloader for each commit.
    127     # if we built the same one for all releases, that might also get anti-virus false positives
    128     echo "const char *electrum_tag = \"tagged by Electrum@$ELECTRUM_COMMIT_HASH\";" >> ./bootloader/src/pyi_main.c
    129     pushd bootloader
    130     # cross-compile to Windows using host python
    131     python3 ./waf all CC="${GCC_TRIPLET_HOST}-gcc" \
    132                       CFLAGS="-static \
    133                               -Wno-dangling-else \
    134                               -Wno-error=unused-value \
    135                               -Wno-error=implicit-function-declaration \
    136                               -Wno-error=int-to-pointer-cast \
    137                               -Wno-error=stringop-truncation"
    138     popd
    139     # sanity check bootloader is there:
    140     [[ -e "PyInstaller/bootloader/Windows-$PYINST_ARCH/runw.exe" ]] || fail "Could not find runw.exe in target dir!"
    141 ) || fail "PyInstaller build failed"
    142 info "Installing PyInstaller."
    143 $WINE_PYTHON -m pip install --no-dependencies --no-warn-script-location ./pyinstaller
    144 
    145 info "Wine is configured."