mirror of
https://github.com/python-pillow/Pillow.git
synced 2024-12-25 17:36:18 +03:00
Merge remote-tracking branch 'upstream/master' into gha-msys
# Conflicts: # .appveyor.yml # .github/workflows/test-windows.yml
This commit is contained in:
commit
21325b8ce3
|
@ -1,4 +1,5 @@
|
|||
version: '{build}'
|
||||
image: Visual Studio 2017
|
||||
clone_folder: c:\pillow
|
||||
init:
|
||||
- ECHO %PYTHON%
|
||||
|
@ -6,46 +7,36 @@ init:
|
|||
# Uncomment previous line to get RDP access during the build.
|
||||
|
||||
environment:
|
||||
X64_EXT: -x64
|
||||
EXECUTABLE: python.exe
|
||||
PIP_DIR: Scripts
|
||||
VENV: NO
|
||||
TEST_OPTIONS:
|
||||
DEPLOY: YES
|
||||
matrix:
|
||||
- PYTHON: C:/Python38
|
||||
- PYTHON: C:/Python38-x64
|
||||
- PYTHON: C:/Python35
|
||||
ARCHITECTURE: x86
|
||||
- PYTHON: C:/Python35-x64
|
||||
- PYTHON: C:/vp/pypy3
|
||||
EXECUTABLE: bin/pypy.exe
|
||||
VENV: YES
|
||||
ARCHITECTURE: x64
|
||||
|
||||
|
||||
install:
|
||||
- curl -fsSL -o pillow-depends.zip https://github.com/python-pillow/pillow-depends/archive/master.zip
|
||||
- 7z x pillow-depends.zip -oc:\
|
||||
- mv c:\pillow-depends-master c:\pillow-depends
|
||||
- xcopy c:\pillow-depends\*.zip c:\pillow\winbuild\
|
||||
- xcopy c:\pillow-depends\*.tar.gz c:\pillow\winbuild\
|
||||
- xcopy /s c:\pillow-depends\test_images\* c:\pillow\tests\images
|
||||
- cd c:\pillow\winbuild\
|
||||
- ps: |
|
||||
if ($env:PYTHON -eq "c:/vp/pypy3")
|
||||
{
|
||||
c:\pillow\winbuild\appveyor_install_pypy3.cmd
|
||||
}
|
||||
- ps: |
|
||||
c:\python37\python.exe c:\pillow\winbuild\build_dep.py
|
||||
c:\pillow\winbuild\build_deps.cmd
|
||||
$host.SetShouldExit(0)
|
||||
- 7z x ..\pillow-depends\nasm-2.14.02-win64.zip -oc:\
|
||||
- curl -fsSL -o gs952.exe https://github.com/ArtifexSoftware/ghostpdl-downloads/releases/download/gs952/gs952w32.exe
|
||||
- gs952.exe /S
|
||||
- path %path%;C:\Program Files (x86)\gs\gs9.52\bin
|
||||
- path c:\nasm-2.14.02;C:\Program Files (x86)\gs\gs9.52\bin;%PATH%
|
||||
- cd c:\pillow\winbuild\
|
||||
- ps: |
|
||||
c:\python37\python.exe c:\pillow\winbuild\build_prepare.py -v --depends=C:\pillow-depends\
|
||||
c:\pillow\winbuild\build\build_dep_all.cmd
|
||||
$host.SetShouldExit(0)
|
||||
- path C:\pillow\winbuild\build\bin;%PATH%
|
||||
|
||||
build_script:
|
||||
- ps: |
|
||||
& $env:PYTHON/$env:EXECUTABLE c:\pillow\winbuild\build.py
|
||||
c:\pillow\winbuild\build\build_pillow.cmd install
|
||||
$host.SetShouldExit(0)
|
||||
- cd c:\pillow
|
||||
- '%PYTHON%\%EXECUTABLE% selftest.py --installed'
|
||||
|
@ -77,7 +68,7 @@ before_deploy:
|
|||
- cd c:\pillow
|
||||
- '%PYTHON%\%PIP_DIR%\pip.exe install wheel'
|
||||
- cd c:\pillow\winbuild\
|
||||
- '%PYTHON%\%EXECUTABLE% c:\pillow\winbuild\build.py --wheel'
|
||||
- c:\pillow\winbuild\build\build_pillow.cmd bdist_wheel
|
||||
- cd c:\pillow
|
||||
- ps: Get-ChildItem .\dist\*.* | % { Push-AppveyorArtifact $_.FullName -FileName $_.Name }
|
||||
|
||||
|
|
2
.github/workflows/lint.yml
vendored
2
.github/workflows/lint.yml
vendored
|
@ -13,7 +13,7 @@ jobs:
|
|||
name: Python ${{ matrix.python-version }}
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v1
|
||||
- uses: actions/checkout@v2
|
||||
|
||||
- name: pip cache
|
||||
uses: actions/cache@v1
|
||||
|
|
2
.github/workflows/test-docker.yml
vendored
2
.github/workflows/test-docker.yml
vendored
|
@ -30,7 +30,7 @@ jobs:
|
|||
name: ${{ matrix.docker }}
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v1
|
||||
- uses: actions/checkout@v2
|
||||
|
||||
- name: Build system information
|
||||
run: python .github/workflows/system-info.py
|
||||
|
|
311
.github/workflows/test-windows.yml
vendored
311
.github/workflows/test-windows.yml
vendored
|
@ -4,7 +4,6 @@ on: [push, pull_request]
|
|||
|
||||
jobs:
|
||||
build:
|
||||
|
||||
runs-on: windows-2019
|
||||
strategy:
|
||||
fail-fast: false
|
||||
|
@ -27,14 +26,16 @@ jobs:
|
|||
name: Python ${{ matrix.python-version }} ${{ matrix.architecture }}
|
||||
|
||||
steps:
|
||||
- uses: actions/checkout@v1
|
||||
- name: Checkout Pillow
|
||||
uses: actions/checkout@v2
|
||||
|
||||
- uses: actions/checkout@v1
|
||||
- name: Checkout cached dependencies
|
||||
uses: actions/checkout@v2
|
||||
with:
|
||||
repository: python-pillow/pillow-depends
|
||||
ref: master
|
||||
path: winbuild\depends
|
||||
|
||||
- name: Cache
|
||||
- name: Cache pip
|
||||
uses: actions/cache@v1
|
||||
with:
|
||||
path: ~\AppData\Local\pip\Cache
|
||||
|
@ -51,291 +52,68 @@ jobs:
|
|||
python-version: ${{ matrix.python-version }}
|
||||
architecture: ${{ matrix.architecture }}
|
||||
|
||||
- name: Build system information
|
||||
- name: Print build system information
|
||||
run: python .github/workflows/system-info.py
|
||||
|
||||
- name: pip install wheel pytest pytest-cov
|
||||
run: |
|
||||
"%pythonLocation%\python.exe" -m pip install wheel pytest pytest-cov
|
||||
shell: cmd
|
||||
run: python -m pip install wheel pytest pytest-cov
|
||||
|
||||
- name: Fetch dependencies
|
||||
- name: Prepare dependencies
|
||||
run: |
|
||||
7z x ..\pillow-depends\nasm-2.14.02-win64.zip "-o$env:RUNNER_WORKSPACE\"
|
||||
Write-Host "`#`#[add-path]$env:RUNNER_WORKSPACE\nasm-2.14.02"
|
||||
7z x winbuild\depends\nasm-2.14.02-win64.zip "-o$env:RUNNER_WORKSPACE\"
|
||||
Write-Host "::add-path::$env:RUNNER_WORKSPACE\nasm-2.14.02"
|
||||
|
||||
..\pillow-depends\gs950w32.exe /S
|
||||
Write-Host "`#`#[add-path]C:\Program Files (x86)\gs\gs9.50\bin"
|
||||
winbuild\depends\gs950w32.exe /S
|
||||
Write-Host "::add-path::C:\Program Files (x86)\gs\gs9.50\bin"
|
||||
|
||||
$env:PYTHON=$env:pythonLocation
|
||||
xcopy ..\pillow-depends\*.zip $env:GITHUB_WORKSPACE\winbuild\
|
||||
xcopy ..\pillow-depends\*.tar.gz $env:GITHUB_WORKSPACE\winbuild\
|
||||
xcopy /s ..\pillow-depends\test_images\* $env:GITHUB_WORKSPACE\tests\images\
|
||||
cd $env:GITHUB_WORKSPACE/winbuild/
|
||||
python.exe $env:GITHUB_WORKSPACE\winbuild\build_dep.py
|
||||
env:
|
||||
EXECUTABLE: bin\python.exe
|
||||
xcopy /s winbuild\depends\test_images\* Tests\images\
|
||||
|
||||
& python.exe winbuild\build_prepare.py -v --python=$env:pythonLocation
|
||||
shell: pwsh
|
||||
|
||||
- name: Build dependencies / libjpeg
|
||||
if: false
|
||||
run: |
|
||||
REM FIXME uses /MT not /MD, see makefile.vc and win32.mak for more info
|
||||
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
cd /D %BUILD%\jpeg-9d
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
nmake -nologo -f makefile.vc setup-vc6
|
||||
nmake -nologo -f makefile.vc clean
|
||||
nmake -nologo -f makefile.vc nodebug=1 libjpeg.lib cjpeg.exe djpeg.exe
|
||||
copy /Y /B j*.h %INCLIB%
|
||||
copy /Y /B *.lib %INCLIB%
|
||||
copy /Y /B *.exe %INCLIB%
|
||||
shell: cmd
|
||||
|
||||
- name: Build dependencies / libjpeg-turbo
|
||||
run: |
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
cd /D %BUILD%\libjpeg-turbo-2.0.3
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
set CMAKE=cmake.exe -DCMAKE_VERBOSE_MAKEFILE=ON -DCMAKE_RULE_MESSAGES:BOOL=OFF
|
||||
set CMAKE=%CMAKE% -DENABLE_SHARED:BOOL=OFF -DWITH_JPEG8:BOOL=TRUE -DWITH_CRT_DLL:BOOL=TRUE -DCMAKE_BUILD_TYPE=Release
|
||||
%CMAKE% -G "NMake Makefiles" .
|
||||
nmake -nologo -f Makefile clean
|
||||
nmake -nologo -f Makefile jpeg-static cjpeg-static djpeg-static
|
||||
copy /Y /B j*.h %INCLIB%
|
||||
copy /Y /B jpeg-static.lib %INCLIB%\libjpeg.lib
|
||||
copy /Y /B cjpeg-static.exe %INCLIB%\cjpeg.exe
|
||||
copy /Y /B djpeg-static.exe %INCLIB%\djpeg.exe
|
||||
shell: cmd
|
||||
|
||||
run: "& winbuild\\build\\build_dep_libjpeg.cmd"
|
||||
- name: Build dependencies / zlib
|
||||
run: |
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
cd /D %BUILD%\zlib-1.2.11
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
nmake -nologo -f win32\Makefile.msc clean
|
||||
nmake -nologo -f win32\Makefile.msc zlib.lib
|
||||
copy /Y /B z*.h %INCLIB%
|
||||
copy /Y /B *.lib %INCLIB%
|
||||
copy /Y /B zlib.lib %INCLIB%\z.lib
|
||||
shell: cmd
|
||||
|
||||
- name: Build dependencies / LibTIFF
|
||||
run: |
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
cd /D %BUILD%\tiff-4.1.0
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
copy %GITHUB_WORKSPACE%\winbuild\tiff.opt nmake.opt
|
||||
nmake -nologo -f makefile.vc clean
|
||||
nmake -nologo -f makefile.vc lib
|
||||
copy /Y /B libtiff\tiff*.h %INCLIB%
|
||||
copy /Y /B libtiff\*.dll %INCLIB%
|
||||
copy /Y /B libtiff\*.lib %INCLIB%
|
||||
shell: cmd
|
||||
|
||||
run: "& winbuild\\build\\build_dep_zlib.cmd"
|
||||
- name: Build dependencies / LibTiff
|
||||
run: "& winbuild\\build\\build_dep_libtiff.cmd"
|
||||
- name: Build dependencies / WebP
|
||||
run: |
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
cd /D %BUILD%\libwebp-1.1.0
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
rmdir /S /Q output\release-static
|
||||
nmake -nologo -f Makefile.vc CFG=release-static OBJDIR=output ARCH=${{ matrix.architecture }} all
|
||||
mkdir %INCLIB%\webp
|
||||
copy /Y /B src\webp\*.h %INCLIB%\webp
|
||||
copy /Y /B output\release-static\${{ matrix.architecture }}\lib\* %INCLIB%
|
||||
shell: cmd
|
||||
|
||||
run: "& winbuild\\build\\build_dep_libwebp.cmd"
|
||||
- name: Build dependencies / FreeType
|
||||
run: |
|
||||
REM Toolkit v100 not available; missing VCTargetsPath; Clean fails
|
||||
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
cd /D %BUILD%\freetype-2.10.2
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
rmdir /S /Q objs
|
||||
set DefaultPlatformToolset=v142
|
||||
set VCTargetsPath=C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\MSBuild\Microsoft\VC\v160\
|
||||
set MSBUILD="C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\MSBuild\Current\Bin\MSBuild.exe"
|
||||
powershell -Command "(gc builds\windows\vc2010\freetype.vcxproj) -replace 'MultiThreaded<', 'MultiThreadedDLL<' | Out-File -encoding ASCII builds\windows\vc2010\freetype.vcxproj"
|
||||
%MSBUILD% builds\windows\vc2010\freetype.sln /t:Build /p:Configuration="Release Static" /p:Platform=${{ matrix.platform-msbuild }} /m
|
||||
xcopy /Y /E /Q include %INCLIB%
|
||||
copy /Y /B "objs\${{ matrix.platform-msbuild }}\Release Static\freetype.lib" %INCLIB%
|
||||
shell: cmd
|
||||
|
||||
run: "& winbuild\\build\\build_dep_freetype.cmd"
|
||||
- name: Build dependencies / LCMS2
|
||||
run: |
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
cd /D %BUILD%\lcms2-2.8
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
rmdir /S /Q Lib
|
||||
rmdir /S /Q Projects\VC2015\Release
|
||||
set VCTargetsPath=C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\MSBuild\Microsoft\VC\v160\
|
||||
set MSBUILD="C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\MSBuild\Current\Bin\MSBuild.exe"
|
||||
powershell %GITHUB_WORKSPACE%\winbuild\lcms2_patch.ps1
|
||||
%MSBUILD% Projects\VC2015\lcms2.sln /t:Clean;lcms2_static /p:Configuration="Release" /p:Platform=${{ matrix.platform-msbuild }} /m
|
||||
xcopy /Y /E /Q include %INCLIB%
|
||||
copy /Y /B Lib\MS\*.lib %INCLIB%
|
||||
shell: cmd
|
||||
|
||||
run: "& winbuild\\build\\build_dep_lcms2.cmd"
|
||||
- name: Build dependencies / OpenJPEG
|
||||
run: |
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
cd /D %BUILD%\openjpeg-2.3.1msvcr10-x32
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
set CMAKE=cmake.exe -DCMAKE_VERBOSE_MAKEFILE=ON -DCMAKE_RULE_MESSAGES:BOOL=OFF
|
||||
set CMAKE=%CMAKE% -DBUILD_THIRDPARTY:BOOL=OFF -DBUILD_SHARED_LIBS:BOOL=OFF
|
||||
set CMAKE=%CMAKE% -DCMAKE_BUILD_TYPE=Release
|
||||
%CMAKE% -G "NMake Makefiles" .
|
||||
nmake -nologo -f Makefile clean
|
||||
nmake -nologo -f Makefile
|
||||
mkdir %INCLIB%\openjpeg-2.3.1
|
||||
copy /Y /B src\lib\openjp2\*.h %INCLIB%\openjpeg-2.3.1
|
||||
copy /Y /B bin\*.lib %INCLIB%
|
||||
shell: cmd
|
||||
run: "& winbuild\\build\\build_dep_openjpeg.cmd"
|
||||
|
||||
# GPL licensed; skip if building wheels
|
||||
- name: Build dependencies / libimagequant
|
||||
if: "github.event_name != 'push' || contains(matrix.python-version, 'pypy')"
|
||||
run: |
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
rem e5d454b: Merge tag '2.12.6' into msvc
|
||||
cd /D %BUILD%\libimagequant-e5d454bc7f5eb63ee50c84a83a7fa5ac94f68ec4
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
echo (gc CMakeLists.txt) -replace 'add_library', "add_compile_options(-openmp-)`r`nadd_library" ^| Out-File -encoding ASCII CMakeLists.txt > patch.ps1
|
||||
echo (gc CMakeLists.txt) -replace ' SHARED', ' STATIC' ^| Out-File -encoding ASCII CMakeLists.txt >> patch.ps1
|
||||
powershell .\patch.ps1
|
||||
set CMAKE=cmake.exe -DCMAKE_VERBOSE_MAKEFILE=ON -DCMAKE_RULE_MESSAGES:BOOL=OFF
|
||||
set CMAKE=%CMAKE% -DCMAKE_BUILD_TYPE=Release
|
||||
%CMAKE% -G "NMake Makefiles" .
|
||||
nmake -nologo -f Makefile clean
|
||||
nmake -nologo -f Makefile
|
||||
copy /Y /B *.h %INCLIB%
|
||||
copy /Y /B *.lib %INCLIB%
|
||||
shell: cmd
|
||||
if: "github.event_name != 'push'"
|
||||
run: "& winbuild\\build\\build_dep_libimagequant.cmd"
|
||||
|
||||
# for Raqm
|
||||
# Raqm dependencies
|
||||
- name: Build dependencies / HarfBuzz
|
||||
run: |
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
set INCLUDE=%INCLUDE%;%INCLIB%
|
||||
set LIB=%LIB%;%INCLIB%
|
||||
cd /D %BUILD%\harfbuzz-2.6.4
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
set CMAKE=cmake.exe -DCMAKE_VERBOSE_MAKEFILE=ON -DCMAKE_RULE_MESSAGES:BOOL=OFF
|
||||
set CMAKE=%CMAKE% -DHB_HAVE_FREETYPE:BOOL=ON -DCMAKE_BUILD_TYPE=Release
|
||||
%CMAKE% -G "NMake Makefiles" .
|
||||
nmake -nologo -f Makefile clean
|
||||
nmake -nologo -f Makefile harfbuzz
|
||||
copy /Y /B src\*.h %INCLIB%
|
||||
copy /Y /B *.lib %INCLIB%
|
||||
shell: cmd
|
||||
|
||||
# for Raqm
|
||||
run: "& winbuild\\build\\build_dep_harfbuzz.cmd"
|
||||
- name: Build dependencies / FriBidi
|
||||
run: |
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
cd /D %BUILD%\fribidi-1.0.9
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
copy /Y /B %GITHUB_WORKSPACE%\winbuild\fribidi.cmake CMakeLists.txt
|
||||
set CMAKE=cmake.exe -DCMAKE_VERBOSE_MAKEFILE=ON -DCMAKE_RULE_MESSAGES:BOOL=OFF
|
||||
set CMAKE=%CMAKE% -DCMAKE_BUILD_TYPE=Release
|
||||
%CMAKE% -G "NMake Makefiles" .
|
||||
nmake -nologo -f Makefile clean
|
||||
nmake -nologo -f Makefile fribidi
|
||||
copy /Y /B lib\*.h %INCLIB%
|
||||
copy /Y /B *.lib %INCLIB%
|
||||
shell: cmd
|
||||
|
||||
run: "& winbuild\\build\\build_dep_fribidi.cmd"
|
||||
- name: Build dependencies / Raqm
|
||||
run: |
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
set BUILD=%GITHUB_WORKSPACE%\winbuild\build
|
||||
set INCLUDE=%INCLUDE%;%INCLIB%
|
||||
set LIB=%LIB%;%INCLIB%
|
||||
cd /D %BUILD%\libraqm-0.7.0
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
echo on
|
||||
copy /Y /B %GITHUB_WORKSPACE%\winbuild\raqm.cmake CMakeLists.txt
|
||||
set CMAKE=cmake.exe -DCMAKE_VERBOSE_MAKEFILE=ON -DCMAKE_RULE_MESSAGES:BOOL=OFF
|
||||
set CMAKE=%CMAKE% -DCMAKE_BUILD_TYPE=Release
|
||||
%CMAKE% -G "NMake Makefiles" .
|
||||
nmake -nologo -f Makefile clean
|
||||
nmake -nologo -f Makefile libraqm
|
||||
copy /Y /B src\*.h %INCLIB%
|
||||
copy /Y /B libraqm.dll %INCLIB%
|
||||
shell: cmd
|
||||
run: "& winbuild\\build\\build_dep_libraqm.cmd"
|
||||
|
||||
- name: Build Pillow
|
||||
run: |
|
||||
set PYTHON=%pythonLocation%
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set MPLSRC=%GITHUB_WORKSPACE%
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
cd /D %GITHUB_WORKSPACE%
|
||||
set LIB=%INCLIB%;%PYTHON%\tcl
|
||||
set INCLUDE=%INCLIB%;%GITHUB_WORKSPACE%\depends\tcl86\include;%INCLUDE%
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
set MSSdk=1
|
||||
set DISTUTILS_USE_SDK=1
|
||||
set py_vcruntime_redist=true
|
||||
%PYTHON%\python.exe setup.py build_ext install
|
||||
rem Add libraqm.dll (copied to INCLIB) to PATH.
|
||||
path %INCLIB%;%PATH%
|
||||
%PYTHON%\python.exe selftest.py --installed
|
||||
shell: cmd
|
||||
& winbuild\build\build_pillow.cmd install
|
||||
& $env:pythonLocation\python.exe selftest.py --installed
|
||||
shell: pwsh
|
||||
|
||||
# failing with PyPy3
|
||||
- name: Enable heap verification
|
||||
if: "!contains(matrix.python-version, 'pypy')"
|
||||
run: |
|
||||
c:\"Program Files (x86)"\"Windows Kits"\10\Debuggers\x86\gflags.exe /p /enable %PYTHON%\python.exe
|
||||
shell: cmd
|
||||
run: "& 'C:\\Program Files (x86)\\Windows Kits\\10\\Debuggers\\x86\\gflags.exe' /p /enable $env:pythonLocation\\python.exe"
|
||||
|
||||
- name: Test Pillow
|
||||
run: |
|
||||
set PYTHON=%pythonLocation%
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
rem Add libraqm.dll (copied to INCLIB) to PATH.
|
||||
path %INCLIB%;%PATH%
|
||||
cd /D %GITHUB_WORKSPACE%
|
||||
%PYTHON%\python.exe -m pytest -vx -W always --cov PIL --cov Tests --cov-report term --cov-report xml Tests
|
||||
path %GITHUB_WORKSPACE%\\winbuild\\build\\bin;%PATH%
|
||||
python.exe -m pytest -vx -W always --cov PIL --cov Tests --cov-report term --cov-report xml Tests
|
||||
shell: cmd
|
||||
|
||||
- name: Prepare to upload errors
|
||||
|
@ -361,30 +139,21 @@ jobs:
|
|||
with:
|
||||
file: ./coverage.xml
|
||||
flags: GHA_Windows
|
||||
name: ${{ runner.os }} Python ${{ matrix.python-version }}
|
||||
name: ${{ runner.os }} Python ${{ matrix.python-version }} ${{ matrix.architecture }}
|
||||
|
||||
- name: Build wheel
|
||||
id: wheel
|
||||
if: "github.event_name == 'push' && !contains(matrix.python-version, 'pypy')"
|
||||
if: "github.event_name == 'push'"
|
||||
run: |
|
||||
for /f "tokens=3 delims=/" %%a in ("${{ github.ref }}") do echo ##[set-output name=dist;]dist-%%a
|
||||
for /f "tokens=3 delims=/" %%a in ("${{ github.ref }}") do echo ::set-output name=dist::dist-%%a
|
||||
set PYTHON=%pythonLocation%
|
||||
set INCLUDE=C:\Program Files (x86)\Microsoft SDKs\Windows\V7.1A\Include
|
||||
set MPLSRC=%GITHUB_WORKSPACE%
|
||||
set INCLIB=%GITHUB_WORKSPACE%\winbuild\depends\msvcr10-x32
|
||||
cd /D %GITHUB_WORKSPACE%
|
||||
set LIB=%INCLIB%;%PYTHON%\tcl
|
||||
set INCLUDE=%INCLIB%;%GITHUB_WORKSPACE%\depends\tcl86\include;%INCLUDE%
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio\2019\Enterprise\VC\Auxiliary\Build\vcvarsall.bat" ${{ matrix.platform-vcvars }}
|
||||
%PYTHON%\python.exe setup.py bdist_wheel
|
||||
winbuild\\build\\build_pillow.cmd bdist_wheel"
|
||||
shell: cmd
|
||||
|
||||
- uses: actions/upload-artifact@v1
|
||||
if: "github.event_name == 'push' && !contains(matrix.python-version, 'pypy')"
|
||||
- uses: actions/upload-artifact@v2
|
||||
if: "github.event_name == 'push'"
|
||||
with:
|
||||
name: ${{ steps.wheel.outputs.dist }}
|
||||
path: dist
|
||||
path: dist\*.whl
|
||||
|
||||
msys:
|
||||
runs-on: windows-2019
|
||||
|
|
|
@ -63,6 +63,12 @@ def test_aspect():
|
|||
assert im.size == (75, 23) # ratio is 3.260869565217
|
||||
|
||||
|
||||
def test_division_by_zero():
|
||||
im = Image.new("L", (200, 2))
|
||||
im.thumbnail((75, 75))
|
||||
assert im.size == (75, 1)
|
||||
|
||||
|
||||
def test_float():
|
||||
im = Image.new("L", (128, 128))
|
||||
im.thumbnail((99.9, 99.9))
|
||||
|
|
|
@ -1,7 +1,7 @@
|
|||
import pytest
|
||||
from PIL import Image, ImageShow
|
||||
|
||||
from .helper import hopper, is_win32, on_ci, on_github_actions
|
||||
from .helper import hopper, is_win32, on_ci
|
||||
|
||||
|
||||
def test_sanity():
|
||||
|
@ -38,8 +38,7 @@ def test_viewer_show():
|
|||
|
||||
|
||||
@pytest.mark.skipif(
|
||||
not on_ci() or (is_win32() and on_github_actions()),
|
||||
reason="Only run on CIs; hangs on Windows on GitHub Actions",
|
||||
not on_ci() or is_win32(), reason="Only run on CIs; hangs on Windows CIs",
|
||||
)
|
||||
def test_show():
|
||||
for mode in ("1", "I;16", "LA", "RGB", "RGBA"):
|
||||
|
|
|
@ -292,9 +292,10 @@ or from within the uncompressed source directory::
|
|||
Building on Windows
|
||||
^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
We don't recommend trying to build on Windows. It is a maze of twisty
|
||||
passages, mostly dead ends. There are build scripts and notes for the
|
||||
Windows build in the ``winbuild`` directory.
|
||||
We recommend you use prebuilt wheels from PyPI.
|
||||
If you wish to compile Pillow manually, you can use the build scripts
|
||||
in the ``winbuild`` directory used for CI testing and development.
|
||||
These scripts require Visual Studio 2017 or newer and NASM.
|
||||
|
||||
Building on FreeBSD
|
||||
^^^^^^^^^^^^^^^^^^^
|
||||
|
@ -408,9 +409,11 @@ These platforms are built and tested for every change.
|
|||
+----------------------------------+--------------------------+-----------------------+
|
||||
| Ubuntu Linux 20.04 LTS | 3.8 |x86-64 |
|
||||
+----------------------------------+--------------------------+-----------------------+
|
||||
| Windows Server 2012 R2 | 3.5, 3.8 |x86, x86-64 |
|
||||
| Windows Server 2016 | 3.8 |x86 |
|
||||
| +--------------------------+-----------------------+
|
||||
| | PyPy3, 3.7/MinGW |x86 |
|
||||
| | 3.5 |x86-64 |
|
||||
| +--------------------------+-----------------------+
|
||||
| | 3.7/MinGW |x86 |
|
||||
+----------------------------------+--------------------------+-----------------------+
|
||||
| Windows Server 2019 | 3.5, 3.6, 3.7, 3.8 |x86, x86-64 |
|
||||
| +--------------------------+-----------------------+
|
||||
|
@ -478,11 +481,13 @@ These platforms have been reported to work at the versions mentioned.
|
|||
+----------------------------------+------------------------------+--------------------------------+-----------------------+
|
||||
| FreeBSD 10.2 | 2.7, 3.4 | 3.1.0 |x86-64 |
|
||||
+----------------------------------+------------------------------+--------------------------------+-----------------------+
|
||||
| Windows 10 | 3.7 | 7.1.0 |x86-64 |
|
||||
+----------------------------------+------------------------------+--------------------------------+-----------------------+
|
||||
| Windows 8.1 Pro | 2.6, 2.7, 3.2, 3.3, 3.4 | 2.4.0 |x86,x86-64 |
|
||||
+----------------------------------+------------------------------+--------------------------------+-----------------------+
|
||||
| Windows 8 Pro | 2.6, 2.7, 3.2, 3.3, 3.4a3 | 2.2.0 |x86,x86-64 |
|
||||
+----------------------------------+------------------------------+--------------------------------+-----------------------+
|
||||
| Windows 7 Pro | 2.7, 3.2, 3.3 | 3.4.1 |x86-64 |
|
||||
| Windows 7 Professional | 3.7 | 7.0.0 |x86,x86-64 |
|
||||
+----------------------------------+------------------------------+--------------------------------+-----------------------+
|
||||
| Windows Server 2008 R2 Enterprise| 3.3 | |x86-64 |
|
||||
+----------------------------------+------------------------------+--------------------------------+-----------------------+
|
||||
|
|
|
@ -2277,7 +2277,9 @@ class Image:
|
|||
if x / y >= aspect:
|
||||
x = round_aspect(y * aspect, key=lambda n: abs(aspect - n / y))
|
||||
else:
|
||||
y = round_aspect(x / aspect, key=lambda n: abs(aspect - x / n))
|
||||
y = round_aspect(
|
||||
x / aspect, key=lambda n: 0 if n == 0 else abs(aspect - x / n)
|
||||
)
|
||||
size = (x, y)
|
||||
|
||||
box = None
|
||||
|
|
|
@ -40,6 +40,7 @@
|
|||
#
|
||||
import io
|
||||
import itertools
|
||||
import logging
|
||||
import os
|
||||
import struct
|
||||
import warnings
|
||||
|
@ -51,7 +52,7 @@ from . import Image, ImageFile, ImagePalette, TiffTags
|
|||
from ._binary import i8, o8
|
||||
from .TiffTags import TYPES
|
||||
|
||||
DEBUG = False # Needs to be merged with the new logging approach.
|
||||
logger = logging.getLogger(__name__)
|
||||
|
||||
# Set these to true to force use of libtiff for reading or writing.
|
||||
READ_LIBTIFF = False
|
||||
|
@ -734,29 +735,21 @@ class ImageFileDirectory_v2(MutableMapping):
|
|||
try:
|
||||
for i in range(self._unpack("H", self._ensure_read(fp, 2))[0]):
|
||||
tag, typ, count, data = self._unpack("HHL4s", self._ensure_read(fp, 12))
|
||||
if DEBUG:
|
||||
|
||||
tagname = TiffTags.lookup(tag).name
|
||||
typname = TYPES.get(typ, "unknown")
|
||||
print(
|
||||
"tag: %s (%d) - type: %s (%d)" % (tagname, tag, typname, typ),
|
||||
end=" ",
|
||||
)
|
||||
msg = "tag: %s (%d) - type: %s (%d)" % (tagname, tag, typname, typ)
|
||||
|
||||
try:
|
||||
unit_size, handler = self._load_dispatch[typ]
|
||||
except KeyError:
|
||||
if DEBUG:
|
||||
print("- unsupported type", typ)
|
||||
logger.debug(msg + " - unsupported type {}".format(typ))
|
||||
continue # ignore unsupported type
|
||||
size = count * unit_size
|
||||
if size > 4:
|
||||
here = fp.tell()
|
||||
(offset,) = self._unpack("L", data)
|
||||
if DEBUG:
|
||||
print(
|
||||
"Tag Location: {} - Data Location: {}".format(here, offset),
|
||||
end=" ",
|
||||
)
|
||||
msg += " Tag Location: {} - Data Location: {}".format(here, offset)
|
||||
fp.seek(offset)
|
||||
data = ImageFile._safe_read(fp, size)
|
||||
fp.seek(here)
|
||||
|
@ -769,19 +762,20 @@ class ImageFileDirectory_v2(MutableMapping):
|
|||
"Expecting to read %d bytes but only got %d."
|
||||
" Skipping tag %s" % (size, len(data), tag)
|
||||
)
|
||||
logger.debug(msg)
|
||||
continue
|
||||
|
||||
if not data:
|
||||
logger.debug(msg)
|
||||
continue
|
||||
|
||||
self._tagdata[tag] = data
|
||||
self.tagtype[tag] = typ
|
||||
|
||||
if DEBUG:
|
||||
if size > 32:
|
||||
print("- value: <table: %d bytes>" % size)
|
||||
else:
|
||||
print("- value:", self[tag])
|
||||
msg += " - value: " + (
|
||||
"<table: %d bytes>" % size if size > 32 else str(data)
|
||||
)
|
||||
logger.debug(msg)
|
||||
|
||||
(self.next,) = self._unpack("L", self._ensure_read(fp, 4))
|
||||
except OSError as msg:
|
||||
|
@ -802,21 +796,17 @@ class ImageFileDirectory_v2(MutableMapping):
|
|||
if tag == STRIPOFFSETS:
|
||||
stripoffsets = len(entries)
|
||||
typ = self.tagtype.get(tag)
|
||||
if DEBUG:
|
||||
print("Tag {}, Type: {}, Value: {}".format(tag, typ, value))
|
||||
logger.debug("Tag {}, Type: {}, Value: {}".format(tag, typ, value))
|
||||
values = value if isinstance(value, tuple) else (value,)
|
||||
data = self._write_dispatch[typ](self, *values)
|
||||
if DEBUG:
|
||||
|
||||
tagname = TiffTags.lookup(tag).name
|
||||
typname = TYPES.get(typ, "unknown")
|
||||
print(
|
||||
"save: %s (%d) - type: %s (%d)" % (tagname, tag, typname, typ),
|
||||
end=" ",
|
||||
msg = "save: %s (%d) - type: %s (%d)" % (tagname, tag, typname, typ)
|
||||
msg += " - value: " + (
|
||||
"<table: %d bytes>" % len(data) if len(data) >= 16 else str(values)
|
||||
)
|
||||
if len(data) >= 16:
|
||||
print("- value: <table: %d bytes>" % len(data))
|
||||
else:
|
||||
print("- value:", values)
|
||||
logger.debug(msg)
|
||||
|
||||
# count is sum of lengths for string and arbitrary data
|
||||
if typ in [TiffTags.BYTE, TiffTags.ASCII, TiffTags.UNDEFINED]:
|
||||
|
@ -840,8 +830,9 @@ class ImageFileDirectory_v2(MutableMapping):
|
|||
|
||||
# pass 2: write entries to file
|
||||
for tag, typ, count, value, data in entries:
|
||||
if DEBUG:
|
||||
print(tag, typ, count, repr(value), repr(data))
|
||||
logger.debug(
|
||||
"{} {} {} {} {}".format(tag, typ, count, repr(value), repr(data))
|
||||
)
|
||||
result += self._pack("HHL4s", tag, typ, count, value)
|
||||
|
||||
# -- overwrite here for multi-page --
|
||||
|
@ -997,10 +988,9 @@ class TiffImageFile(ImageFile.ImageFile):
|
|||
self._frame_pos = []
|
||||
self._n_frames = None
|
||||
|
||||
if DEBUG:
|
||||
print("*** TiffImageFile._open ***")
|
||||
print("- __first:", self.__first)
|
||||
print("- ifh: ", ifh)
|
||||
logger.debug("*** TiffImageFile._open ***")
|
||||
logger.debug("- __first: {}".format(self.__first))
|
||||
logger.debug("- ifh: {}".format(ifh))
|
||||
|
||||
# and load the first frame
|
||||
self._seek(0)
|
||||
|
@ -1031,8 +1021,7 @@ class TiffImageFile(ImageFile.ImageFile):
|
|||
while len(self._frame_pos) <= frame:
|
||||
if not self.__next:
|
||||
raise EOFError("no more images in TIFF file")
|
||||
if DEBUG:
|
||||
print(
|
||||
logger.debug(
|
||||
"Seeking to frame %s, on frame %s, __next %s, location: %s"
|
||||
% (frame, self.__frame, self.__next, self.fp.tell())
|
||||
)
|
||||
|
@ -1041,8 +1030,7 @@ class TiffImageFile(ImageFile.ImageFile):
|
|||
self.fp.tell()
|
||||
self.fp.seek(self.__next)
|
||||
self._frame_pos.append(self.__next)
|
||||
if DEBUG:
|
||||
print("Loading tags, location: %s" % self.fp.tell())
|
||||
logger.debug("Loading tags, location: %s" % self.fp.tell())
|
||||
self.tag_v2.load(self.fp)
|
||||
self.__next = self.tag_v2.next
|
||||
if self.__next == 0:
|
||||
|
@ -1140,21 +1128,18 @@ class TiffImageFile(ImageFile.ImageFile):
|
|||
# Rearranging for supporting byteio items, since they have a fileno
|
||||
# that returns an OSError if there's no underlying fp. Easier to
|
||||
# deal with here by reordering.
|
||||
if DEBUG:
|
||||
print("have getvalue. just sending in a string from getvalue")
|
||||
logger.debug("have getvalue. just sending in a string from getvalue")
|
||||
n, err = decoder.decode(self.fp.getvalue())
|
||||
elif fp:
|
||||
# we've got a actual file on disk, pass in the fp.
|
||||
if DEBUG:
|
||||
print("have fileno, calling fileno version of the decoder.")
|
||||
logger.debug("have fileno, calling fileno version of the decoder.")
|
||||
if not close_self_fp:
|
||||
self.fp.seek(0)
|
||||
# 4 bytes, otherwise the trace might error out
|
||||
n, err = decoder.decode(b"fpfp")
|
||||
else:
|
||||
# we have something else.
|
||||
if DEBUG:
|
||||
print("don't have fileno or getvalue. just reading")
|
||||
logger.debug("don't have fileno or getvalue. just reading")
|
||||
self.fp.seek(0)
|
||||
# UNDONE -- so much for that buffer size thing.
|
||||
n, err = decoder.decode(self.fp.read())
|
||||
|
@ -1194,21 +1179,19 @@ class TiffImageFile(ImageFile.ImageFile):
|
|||
|
||||
fillorder = self.tag_v2.get(FILLORDER, 1)
|
||||
|
||||
if DEBUG:
|
||||
print("*** Summary ***")
|
||||
print("- compression:", self._compression)
|
||||
print("- photometric_interpretation:", photo)
|
||||
print("- planar_configuration:", self._planar_configuration)
|
||||
print("- fill_order:", fillorder)
|
||||
print("- YCbCr subsampling:", self.tag.get(530))
|
||||
logger.debug("*** Summary ***")
|
||||
logger.debug("- compression: {}".format(self._compression))
|
||||
logger.debug("- photometric_interpretation: {}".format(photo))
|
||||
logger.debug("- planar_configuration: {}".format(self._planar_configuration))
|
||||
logger.debug("- fill_order: {}".format(fillorder))
|
||||
logger.debug("- YCbCr subsampling: {}".format(self.tag.get(530)))
|
||||
|
||||
# size
|
||||
xsize = int(self.tag_v2.get(IMAGEWIDTH))
|
||||
ysize = int(self.tag_v2.get(IMAGELENGTH))
|
||||
self._size = xsize, ysize
|
||||
|
||||
if DEBUG:
|
||||
print("- size:", self.size)
|
||||
logger.debug("- size: {}".format(self.size))
|
||||
|
||||
sampleFormat = self.tag_v2.get(SAMPLEFORMAT, (1,))
|
||||
if len(sampleFormat) > 1 and max(sampleFormat) == min(sampleFormat) == 1:
|
||||
|
@ -1242,18 +1225,15 @@ class TiffImageFile(ImageFile.ImageFile):
|
|||
bps_tuple,
|
||||
extra_tuple,
|
||||
)
|
||||
if DEBUG:
|
||||
print("format key:", key)
|
||||
logger.debug("format key: {}".format(key))
|
||||
try:
|
||||
self.mode, rawmode = OPEN_INFO[key]
|
||||
except KeyError:
|
||||
if DEBUG:
|
||||
print("- unsupported format")
|
||||
logger.debug("- unsupported format")
|
||||
raise SyntaxError("unknown pixel mode")
|
||||
|
||||
if DEBUG:
|
||||
print("- raw mode:", rawmode)
|
||||
print("- pil mode:", self.mode)
|
||||
logger.debug("- raw mode: {}".format(rawmode))
|
||||
logger.debug("- pil mode: {}".format(self.mode))
|
||||
|
||||
self.info["compression"] = self._compression
|
||||
|
||||
|
@ -1294,8 +1274,7 @@ class TiffImageFile(ImageFile.ImageFile):
|
|||
if fillorder == 2:
|
||||
# Replace fillorder with fillorder=1
|
||||
key = key[:3] + (1,) + key[4:]
|
||||
if DEBUG:
|
||||
print("format key:", key)
|
||||
logger.debug("format key: {}".format(key))
|
||||
# this should always work, since all the
|
||||
# fillorder==2 modes have a corresponding
|
||||
# fillorder=1 mode
|
||||
|
@ -1357,8 +1336,7 @@ class TiffImageFile(ImageFile.ImageFile):
|
|||
x = y = 0
|
||||
layer += 1
|
||||
else:
|
||||
if DEBUG:
|
||||
print("- unsupported data organization")
|
||||
logger.debug("- unsupported data organization")
|
||||
raise SyntaxError("unknown data organization")
|
||||
|
||||
# Fix up info.
|
||||
|
@ -1438,8 +1416,7 @@ def _save(im, fp, filename):
|
|||
|
||||
# write any arbitrary tags passed in as an ImageFileDirectory
|
||||
info = im.encoderinfo.get("tiffinfo", {})
|
||||
if DEBUG:
|
||||
print("Tiffinfo Keys: %s" % list(info))
|
||||
logger.debug("Tiffinfo Keys: %s" % list(info))
|
||||
if isinstance(info, ImageFileDirectory_v1):
|
||||
info = info.to_v2()
|
||||
for key in info:
|
||||
|
@ -1524,9 +1501,8 @@ def _save(im, fp, filename):
|
|||
)
|
||||
ifd[JPEGQUALITY] = quality
|
||||
|
||||
if DEBUG:
|
||||
print("Saving using libtiff encoder")
|
||||
print("Items: %s" % sorted(ifd.items()))
|
||||
logger.debug("Saving using libtiff encoder")
|
||||
logger.debug("Items: %s" % sorted(ifd.items()))
|
||||
_fp = 0
|
||||
if hasattr(fp, "fileno"):
|
||||
try:
|
||||
|
@ -1588,8 +1564,7 @@ def _save(im, fp, filename):
|
|||
else:
|
||||
atts[tag] = value
|
||||
|
||||
if DEBUG:
|
||||
print("Converted items: %s" % sorted(atts.items()))
|
||||
logger.debug("Converted items: %s" % sorted(atts.items()))
|
||||
|
||||
# libtiff always expects the bytes in native order.
|
||||
# we're storing image byte order. So, if the rawmode
|
||||
|
|
|
@ -43,14 +43,12 @@ void *
|
|||
ImagingError_ModeError(void)
|
||||
{
|
||||
return ImagingError_ValueError("bad image mode");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void *
|
||||
ImagingError_Mismatch(void)
|
||||
{
|
||||
return ImagingError_ValueError("images don't match");
|
||||
return NULL;
|
||||
}
|
||||
|
||||
void *
|
||||
|
|
|
@ -3,16 +3,28 @@ Quick README
|
|||
|
||||
For more extensive info, see the [Windows build instructions](build.rst).
|
||||
|
||||
* See https://github.com/python-pillow/Pillow/issues/553#issuecomment-37877416 and https://github.com/matplotlib/matplotlib/issues/1717#issuecomment-13343859
|
||||
* See [Current Windows Build/Testing process (Pillow#553)](https://github.com/python-pillow/Pillow/issues/553#issuecomment-37877416),
|
||||
[Definitive docs for how to compile on Windows (matplotlib#1717)](https://github.com/matplotlib/matplotlib/issues/1717#issuecomment-13343859),
|
||||
[Test Windows with GitHub Actions (Pillow#4084)](https://github.com/python-pillow/Pillow/pull/4084).
|
||||
|
||||
* Works best with Python 3.4, due to virtualenv and pip batteries included. Python3+ required for fetch command.
|
||||
* Check config.py for virtual env paths, suffix for 64-bit releases. Defaults to `x64`, set `X64_EXT` to change.
|
||||
* When running in CI with one Python per invocation, set the `PYTHON` env variable to the Python folder. (e.g. `PYTHON`=`c:\Python27\`) This overrides the matrix in config.py and will just build and test for the specific Python.
|
||||
* `python get_pythons.py` downloads all the Python releases, and their signatures. (Manually) Install in `c:\PythonXX[x64]\`.
|
||||
* `python build_dep.py` downloads and creates a build script for all the dependencies, in 32 and 64-bit versions, and with both compiler versions.
|
||||
* (in powershell) `build_deps.cmd` invokes the dependency build.
|
||||
* `python build.py --clean` makes Pillow for the matrix of Pythons.
|
||||
* `python test.py` runs the tests on Pillow in all the virtual envs.
|
||||
* Currently working with zlib, libjpeg, freetype, and libtiff on Python 2.7, and 3.4, both 32 and 64-bit, on a local win7 pro machine and appveyor.com
|
||||
* WebP is built, not detected.
|
||||
* LCMS, OpenJPEG and libimagequant are not building.
|
||||
|
||||
* Requires Microsoft Visual Studio 2017 or newer with C++ component.
|
||||
* Requires NASM for libjpeg-turbo, a required dependency when using this script.
|
||||
* Requires CMake 3.12 or newer (available as Visual Studio component).
|
||||
* Python 3.6+ is required to generate valid scripts, but builds targeting Python 3.5+ are supported.
|
||||
* Tested on Windows Server 2016 with Visual Studio 2017 Community (AppVeyor).
|
||||
* Tested on Windows Server 2019 with Visual Studio 2019 Enterprise (GitHub Actions).
|
||||
|
||||
The following is a simplified version of the script used on AppVeyor:
|
||||
```
|
||||
set PYTHON=C:\Python35\bin
|
||||
cd /D C:\Pillow\winbuild
|
||||
C:\Python37\bin\python.exe build_prepare.py -v --depends=C:\pillow-depends
|
||||
build\build_dep_all.cmd
|
||||
build\build_pillow.cmd install
|
||||
cd ..
|
||||
path C:\Pillow\winbuild\build\bin;%PATH%
|
||||
%PYTHON%\python.exe selftest.py
|
||||
%PYTHON%\python.exe -m pytest -vx --cov PIL --cov Tests --cov-report term --cov-report xml Tests
|
||||
build\build_pillow.cmd bdist_wheel
|
||||
```
|
||||
|
|
|
@ -1,3 +0,0 @@
|
|||
curl -fsSL -o pypy3.zip https://bitbucket.org/pypy/pypy/downloads/pypy3.6-v7.3.1-win32.zip
|
||||
7z x pypy3.zip -oc:\
|
||||
c:\Python37\Scripts\virtualenv.exe -p c:\pypy3.6-v7.3.1-win32\pypy3.exe c:\vp\pypy3
|
|
@ -1,205 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
|
||||
import getopt
|
||||
import os
|
||||
import shutil
|
||||
import subprocess
|
||||
import sys
|
||||
|
||||
from config import (
|
||||
VIRT_BASE,
|
||||
X64_EXT,
|
||||
bit_from_env,
|
||||
compiler_from_env,
|
||||
compilers,
|
||||
pythons,
|
||||
pyversion_from_env,
|
||||
)
|
||||
|
||||
|
||||
def setup_vms():
|
||||
ret = []
|
||||
for py in pythons:
|
||||
for arch in ("", X64_EXT):
|
||||
ret.append(
|
||||
"virtualenv -p c:/Python%s%s/python.exe --clear %s%s%s"
|
||||
% (py, arch, VIRT_BASE, py, arch)
|
||||
)
|
||||
ret.append(
|
||||
r"%s%s%s\Scripts\pip.exe install pytest pytest-cov"
|
||||
% (VIRT_BASE, py, arch)
|
||||
)
|
||||
return "\n".join(ret)
|
||||
|
||||
|
||||
def run_script(params):
|
||||
(version, script) = params
|
||||
try:
|
||||
print("Running %s" % version)
|
||||
filename = "build_pillow_%s.cmd" % version
|
||||
with open(filename, "w") as f:
|
||||
f.write(script)
|
||||
|
||||
command = ["powershell", "./%s" % filename]
|
||||
proc = subprocess.Popen(
|
||||
command,
|
||||
stdin=subprocess.PIPE,
|
||||
stdout=subprocess.PIPE,
|
||||
stderr=subprocess.PIPE,
|
||||
)
|
||||
(trace, stderr) = proc.communicate()
|
||||
status = proc.returncode
|
||||
print("-- stderr --")
|
||||
print(stderr.decode())
|
||||
print("-- stdout --")
|
||||
print(trace.decode())
|
||||
print("Done with {}: {}".format(version, status))
|
||||
return (version, status, trace, stderr)
|
||||
except Exception as msg:
|
||||
print("Error with {}: {}".format(version, str(msg)))
|
||||
return (version, -1, "", str(msg))
|
||||
|
||||
|
||||
def header(op):
|
||||
return r"""
|
||||
setlocal
|
||||
set MPLSRC=%%~dp0\..
|
||||
set INCLIB=%%~dp0\depends
|
||||
set BLDOPT=%s
|
||||
cd /D %%MPLSRC%%
|
||||
""" % (
|
||||
op
|
||||
)
|
||||
|
||||
|
||||
def footer():
|
||||
return """endlocal
|
||||
exit
|
||||
"""
|
||||
|
||||
|
||||
def vc_setup(compiler, bit):
|
||||
script = ""
|
||||
if compiler["vc_version"] == "2015":
|
||||
arch = "x86" if bit == 32 else "x86_amd64"
|
||||
script = (
|
||||
r"""
|
||||
call "C:\Program Files (x86)\Microsoft Visual Studio 14.0\VC\vcvarsall.bat" %s
|
||||
echo on"""
|
||||
% arch
|
||||
)
|
||||
return script
|
||||
|
||||
|
||||
def build_one(py_ver, compiler, bit):
|
||||
# UNDONE virtual envs if we're not running on AppVeyor
|
||||
args = {}
|
||||
args.update(compiler)
|
||||
if "PYTHON" in os.environ:
|
||||
args["python_path"] = "%PYTHON%"
|
||||
else:
|
||||
args["python_path"] = "{}{}\\Scripts".format(VIRT_BASE, py_ver)
|
||||
|
||||
args["executable"] = "python.exe"
|
||||
if "EXECUTABLE" in os.environ:
|
||||
args["executable"] = "%EXECUTABLE%"
|
||||
|
||||
args["py_ver"] = py_ver
|
||||
args["tcl_ver"] = "86"
|
||||
|
||||
if compiler["vc_version"] == "2015":
|
||||
args["imaging_libs"] = " build_ext --add-imaging-libs=msvcrt"
|
||||
else:
|
||||
args["imaging_libs"] = ""
|
||||
|
||||
args["vc_setup"] = vc_setup(compiler, bit)
|
||||
|
||||
script = r"""
|
||||
setlocal EnableDelayedExpansion
|
||||
call "%%ProgramFiles%%\Microsoft SDKs\Windows\%(env_version)s\Bin\SetEnv.Cmd" /Release %(env_flags)s
|
||||
set DISTUTILS_USE_SDK=1
|
||||
set LIB=%%LIB%%;%%INCLIB%%\%(inc_dir)s
|
||||
set INCLUDE=%%INCLUDE%%;%%INCLIB%%\%(inc_dir)s;%%INCLIB%%\tcl%(tcl_ver)s\include
|
||||
|
||||
setlocal
|
||||
set LIB=%%LIB%%;C:\Python%(py_ver)s\tcl%(vc_setup)s
|
||||
call %(python_path)s\%(executable)s setup.py %(imaging_libs)s %%BLDOPT%%
|
||||
call %(python_path)s\%(executable)s -c "from PIL import _webp;import os, shutil;shutil.copy(r'%%INCLIB%%\freetype.dll', os.path.dirname(_webp.__file__));"
|
||||
endlocal
|
||||
|
||||
endlocal
|
||||
""" # noqa: E501
|
||||
return script % args
|
||||
|
||||
|
||||
def clean():
|
||||
try:
|
||||
shutil.rmtree("../build")
|
||||
except Exception:
|
||||
# could already be removed
|
||||
pass
|
||||
run_script(("virtualenvs", setup_vms()))
|
||||
|
||||
|
||||
def main(op):
|
||||
scripts = []
|
||||
|
||||
for py_version, py_info in pythons.items():
|
||||
py_compilers = compilers[py_info["compiler"]][py_info["vc"]]
|
||||
scripts.append(
|
||||
(
|
||||
py_version,
|
||||
"\n".join(
|
||||
[header(op), build_one(py_version, py_compilers[32], 32), footer()]
|
||||
),
|
||||
)
|
||||
)
|
||||
|
||||
scripts.append(
|
||||
(
|
||||
"{}{}".format(py_version, X64_EXT),
|
||||
"\n".join(
|
||||
[
|
||||
header(op),
|
||||
build_one("%sx64" % py_version, py_compilers[64], 64),
|
||||
footer(),
|
||||
]
|
||||
),
|
||||
)
|
||||
)
|
||||
|
||||
results = map(run_script, scripts)
|
||||
|
||||
for (version, status, trace, err) in results:
|
||||
print("Compiled {}: {}".format(version, status and "ERR" or "OK"))
|
||||
|
||||
|
||||
def run_one(op):
|
||||
|
||||
compiler = compiler_from_env()
|
||||
py_version = pyversion_from_env()
|
||||
bit = bit_from_env()
|
||||
|
||||
run_script(
|
||||
(
|
||||
py_version,
|
||||
"\n".join([header(op), build_one(py_version, compiler, bit), footer()]),
|
||||
)
|
||||
)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
opts, args = getopt.getopt(sys.argv[1:], "", ["clean", "wheel"])
|
||||
opts = dict(opts)
|
||||
|
||||
if "--clean" in opts:
|
||||
clean()
|
||||
|
||||
op = "install"
|
||||
if "--wheel" in opts:
|
||||
op = "bdist_wheel"
|
||||
|
||||
if "PYTHON" in os.environ:
|
||||
run_one(op)
|
||||
else:
|
||||
main(op)
|
|
@ -5,89 +5,112 @@ Building Pillow on Windows
|
|||
<../docs/installation.rst#windows-installation>`_ should
|
||||
be sufficient.
|
||||
|
||||
This page will describe a build setup to build Pillow against the
|
||||
supported Python versions in 32 and 64-bit modes, using freely
|
||||
available Microsoft compilers. This has been developed and tested
|
||||
against 64-bit Windows 7 Professional and Windows Server 2012
|
||||
64-bit version on Amazon EC2.
|
||||
This page describes the steps necessary to build Pillow using the same
|
||||
scripts used on GitHub Actions and AppVeyor CIs.
|
||||
|
||||
Prerequisites
|
||||
-------------
|
||||
|
||||
Extra Build Helpers
|
||||
^^^^^^^^^^^^^^^^^^^
|
||||
|
||||
* Powershell (available by default on Windows Server)
|
||||
* GitHub client (provides git+bash shell)
|
||||
|
||||
Optional:
|
||||
* GPG (for checking signatures) (UNDONE -- Python signature checking)
|
||||
|
||||
|
||||
Pythons
|
||||
^^^^^^^
|
||||
|
||||
The build routines expect Python to be installed at C:\PythonXX for
|
||||
32-bit versions or C:\PythonXXx64 for the 64-bit versions.
|
||||
|
||||
Download Python 3.4, install it, and add it to the path. This is the
|
||||
Python that we will use to bootstrap the build process. (The download
|
||||
routines are using 3 features, and installing 3.4 gives us pip and
|
||||
virtualenv as well, reducing the number of packages that we need to
|
||||
install.)
|
||||
|
||||
Download the rest of the Pythons by opening a command window, changing
|
||||
to the ``winbuild`` directory, and running ``python
|
||||
get_pythons.py``.
|
||||
|
||||
UNDONE -- gpg verify the signatures (note that we can download from
|
||||
https)
|
||||
|
||||
Run each installer and set the proper path to the installation. Don't
|
||||
set any of them as the default Python, or add them to the path.
|
||||
Python
|
||||
^^^^^^
|
||||
|
||||
While the scripts can target any version of Python supported by Pillow,
|
||||
Python 3.6+ is required to generate valid build scripts.
|
||||
|
||||
Compilers
|
||||
^^^^^^^^^
|
||||
|
||||
Download and install:
|
||||
|
||||
* `Microsoft Windows SDK for Windows 7 and .NET Framework
|
||||
4 <https://www.microsoft.com/en-us/download/details.aspx?id=8279>`_
|
||||
* `Microsoft Visual Studio 2017 or newer or Build Tools for Visual Studio 2017 or newer
|
||||
<https://visualstudio.microsoft.com/downloads/>`_
|
||||
(MSVC C++ build tools, and any Windows SDK version required)
|
||||
|
||||
* `CMake-2.8.10.2-win32-x86.exe
|
||||
<https://cmake.org/files/v2.8/cmake-2.8.10.2-win32-x86.exe>`_
|
||||
* `CMake 3.12 or newer <https://cmake.org/download/>`_
|
||||
(also available as Visual Studio component C++ CMake tools for Windows)
|
||||
|
||||
The samples and the .NET SDK portions aren't required, just the
|
||||
compilers and other tools. UNDONE -- check exact wording.
|
||||
* `NASM <https://www.nasm.us/pub/nasm/releasebuilds/?C=M;O=D>`_
|
||||
|
||||
Any version of Visual Studio 2017 or newer should be supported,
|
||||
including Visual Studio 2017 Community, or Build Tools for Visual Studio 2019.
|
||||
|
||||
Paths to CMake (if standalone) and NASM must be added to the ``PATH`` environment variable.
|
||||
Visual Studio is found automatically with ``vswhere.exe``.
|
||||
|
||||
Build configuration
|
||||
-------------------
|
||||
|
||||
The following environment variables, if set, will override the default
|
||||
behaviour of ``build_prepare.py``:
|
||||
|
||||
* ``PYTHON`` + ``EXECUTABLE`` point to the target version of Python.
|
||||
If ``PYTHON`` is unset, the version of Python used to run
|
||||
``build_prepare.py`` will be used. If only ``PYTHON`` is set,
|
||||
``EXECUTABLE`` defaults to ``python.exe``.
|
||||
* ``ARCHITECTURE`` is used to select a ``x86`` or ``x64`` build. By default,
|
||||
uses same architecture as the version of Python used to run ``build_prepare.py``.
|
||||
is used.
|
||||
* ``PILLOW_BUILD`` can be used to override the ``winbuild\build`` directory
|
||||
path, used to store generated build scripts and compiled libraries.
|
||||
**Warning:** This directory is wiped when ``build_prepare.py`` is run.
|
||||
* ``PILLOW_DEPS`` points to the directory used to store downloaded
|
||||
dependencies. By default ``winbuild\depends`` is used.
|
||||
|
||||
``build_prepare.py`` also supports the following command line parameters:
|
||||
|
||||
* ``-v`` will print generated scripts.
|
||||
* ``--no-imagequant`` will skip GPL-licensed ``libimagequant`` optional dependency
|
||||
* ``--no-raqm`` will skip optional dependency Raqm (which itself depends on
|
||||
LGPL-licensed ``fribidi``).
|
||||
* ``--python=<path>`` and ``--executable=<exe>`` override ``PYTHON`` and ``EXECUTABLE``.
|
||||
* ``--architecture=<arch>`` overrides ``ARCHITECTURE``.
|
||||
* ``--dir=<path>`` and ``--depends=<path>`` override ``PILLOW_BUILD``
|
||||
and ``PILLOW_DEPS``.
|
||||
|
||||
Dependencies
|
||||
------------
|
||||
|
||||
The script 'build_dep.py' downloads and builds the dependencies. Open
|
||||
a command window, change directory into ``winbuild`` and run ``python
|
||||
build_dep.py``.
|
||||
Dependencies will be automatically downloaded by ``build_prepare.py``.
|
||||
By default, downloaded dependencies are stored in ``winbuild\depends``;
|
||||
set the ``PILLOW_DEPS`` environment variable to override this location.
|
||||
|
||||
This will download libjpeg, libtiff, libz, and freetype. It will then
|
||||
compile 32 and 64-bit versions of the libraries, with both versions of
|
||||
the compilers.
|
||||
|
||||
UNDONE -- lcms fails.
|
||||
UNDONE -- webp, jpeg2k not recognized
|
||||
To build all dependencies, run ``winbuild\build\build_dep_all.cmd``,
|
||||
or run the individual scripts to build each dependency separately.
|
||||
|
||||
Building Pillow
|
||||
---------------
|
||||
|
||||
Once the dependencies are built, run ``python build.py --clean`` to
|
||||
build and install Pillow in virtualenvs for each Python
|
||||
build. ``build.py --wheel`` will build wheels instead of
|
||||
installing into virtualenvs.
|
||||
|
||||
UNDONE -- suppressed output, what about failures.
|
||||
Once the dependencies are built, run
|
||||
``winbuild\build\build_pillow.cmd install`` to build and install
|
||||
Pillow for the selected version of Python.
|
||||
``winbuild\build\build_pillow.cmd bdist_wheel`` will build wheels
|
||||
instead of installing Pillow.
|
||||
|
||||
Testing Pillow
|
||||
--------------
|
||||
|
||||
Build and install Pillow, then run ``python test.py`` from the
|
||||
``winbuild`` directory.
|
||||
Some binary dependencies (e.g. ``libraqm.dll``) will be stored in the
|
||||
``winbuild\build\bin`` directory; this directory should be added to ``PATH``
|
||||
before running tests.
|
||||
|
||||
Build and install Pillow, then run ``python -m pytest Tests``
|
||||
from the root Pillow directory.
|
||||
|
||||
Example
|
||||
-------
|
||||
|
||||
The following is a simplified version of the script used on AppVeyor:
|
||||
|
||||
.. code-block::
|
||||
|
||||
set PYTHON=C:\Python35\bin
|
||||
cd /D C:\Pillow\winbuild
|
||||
C:\Python37\bin\python.exe build_prepare.py -v --depends=C:\pillow-depends
|
||||
build\build_dep_all.cmd
|
||||
build\build_pillow.cmd install
|
||||
cd ..
|
||||
path C:\Pillow\winbuild\build\bin;%PATH%
|
||||
%PYTHON%\python.exe selftest.py
|
||||
%PYTHON%\python.exe -m pytest -vx --cov PIL --cov Tests --cov-report term --cov-report xml Tests
|
||||
build\build_pillow.cmd bdist_wheel
|
||||
|
|
|
@ -1,328 +0,0 @@
|
|||
import os
|
||||
|
||||
from build import vc_setup
|
||||
from config import all_compilers, bit_from_env, compiler_from_env, compilers, libs
|
||||
from fetch import fetch
|
||||
from untar import untar
|
||||
from unzip import unzip
|
||||
|
||||
|
||||
def _relpath(*args):
|
||||
return os.path.join(os.getcwd(), *args)
|
||||
|
||||
|
||||
build_dir = _relpath("build")
|
||||
inc_dir = _relpath("depends")
|
||||
|
||||
|
||||
def check_sig(filename, signame):
|
||||
# UNDONE -- need gpg
|
||||
return filename
|
||||
|
||||
|
||||
def mkdirs():
|
||||
try:
|
||||
os.mkdir(build_dir)
|
||||
except OSError:
|
||||
pass
|
||||
try:
|
||||
os.mkdir(inc_dir)
|
||||
except OSError:
|
||||
pass
|
||||
for compiler in all_compilers():
|
||||
try:
|
||||
os.mkdir(os.path.join(inc_dir, compiler["inc_dir"]))
|
||||
except OSError:
|
||||
pass
|
||||
|
||||
|
||||
def extract(src, dest):
|
||||
if ".zip" in src:
|
||||
return unzip(src, dest)
|
||||
if ".tar.gz" in src or ".tgz" in src:
|
||||
return untar(src, dest)
|
||||
|
||||
|
||||
def extract_libs():
|
||||
for name, lib in libs.items():
|
||||
filename = fetch(lib["url"])
|
||||
if name == "openjpeg":
|
||||
for compiler in all_compilers():
|
||||
if not os.path.exists(
|
||||
os.path.join(build_dir, lib["dir"] + compiler["inc_dir"])
|
||||
):
|
||||
extract(filename, build_dir)
|
||||
os.rename(
|
||||
os.path.join(build_dir, lib["dir"]),
|
||||
os.path.join(build_dir, lib["dir"] + compiler["inc_dir"]),
|
||||
)
|
||||
else:
|
||||
extract(filename, build_dir)
|
||||
|
||||
|
||||
def extract_openjpeg(compiler):
|
||||
return (
|
||||
r"""
|
||||
rem build openjpeg
|
||||
setlocal
|
||||
cd %%BUILD%%
|
||||
mkdir %%INCLIB%%\openjpeg-2.0
|
||||
copy /Y /B openjpeg-2.0.0-win32-x86\include\openjpeg-2.0 %%INCLIB%%\openjpeg-2.0
|
||||
copy /Y /B openjpeg-2.0.0-win32-x86\bin\ %%INCLIB%%
|
||||
copy /Y /B openjpeg-2.0.0-win32-x86\lib\ %%INCLIB%%
|
||||
endlocal
|
||||
"""
|
||||
% compiler
|
||||
)
|
||||
|
||||
|
||||
def cp_tk(ver_85, ver_86):
|
||||
versions = {"ver_85": ver_85, "ver_86": ver_86}
|
||||
return (
|
||||
r"""
|
||||
mkdir %%INCLIB%%\tcl85\include\X11
|
||||
copy /Y /B %%BUILD%%\tcl%(ver_85)s\generic\*.h %%INCLIB%%\tcl85\include\
|
||||
copy /Y /B %%BUILD%%\tk%(ver_85)s\generic\*.h %%INCLIB%%\tcl85\include\
|
||||
copy /Y /B %%BUILD%%\tk%(ver_85)s\xlib\X11\* %%INCLIB%%\tcl85\include\X11\
|
||||
|
||||
mkdir %%INCLIB%%\tcl86\include\X11
|
||||
copy /Y /B %%BUILD%%\tcl%(ver_86)s\generic\*.h %%INCLIB%%\tcl86\include\
|
||||
copy /Y /B %%BUILD%%\tk%(ver_86)s\generic\*.h %%INCLIB%%\tcl86\include\
|
||||
copy /Y /B %%BUILD%%\tk%(ver_86)s\xlib\X11\* %%INCLIB%%\tcl86\include\X11\
|
||||
"""
|
||||
% versions
|
||||
)
|
||||
|
||||
|
||||
def header():
|
||||
return r"""setlocal
|
||||
set MSBUILD=C:\Windows\Microsoft.NET\Framework64\v4.0.30319\MSBuild.exe
|
||||
set CMAKE="cmake.exe"
|
||||
set INCLIB=%~dp0\depends
|
||||
set BUILD=%~dp0\build
|
||||
""" + "\n".join(
|
||||
r"set {}=%BUILD%\{}".format(k.upper(), v["dir"])
|
||||
for (k, v) in libs.items()
|
||||
if v["dir"]
|
||||
)
|
||||
|
||||
|
||||
def setup_compiler(compiler):
|
||||
return (
|
||||
r"""setlocal EnableDelayedExpansion
|
||||
call "%%ProgramFiles%%\Microsoft SDKs\Windows\%(env_version)s\Bin\SetEnv.Cmd" /Release %(env_flags)s
|
||||
echo on
|
||||
set INCLIB=%%INCLIB%%\%(inc_dir)s
|
||||
""" # noqa: E501
|
||||
% compiler
|
||||
)
|
||||
|
||||
|
||||
def end_compiler():
|
||||
return """
|
||||
endlocal
|
||||
"""
|
||||
|
||||
|
||||
def nmake_openjpeg(compiler, bit):
|
||||
if compiler["env_version"] == "v7.0":
|
||||
return ""
|
||||
|
||||
atts = {"op_ver": "2.3.1"}
|
||||
atts.update(compiler)
|
||||
return (
|
||||
r"""
|
||||
rem build openjpeg
|
||||
setlocal
|
||||
"""
|
||||
+ vc_setup(compiler, bit)
|
||||
+ r"""
|
||||
cd /D %%OPENJPEG%%%(inc_dir)s
|
||||
|
||||
%%CMAKE%% -DBUILD_THIRDPARTY:BOOL=OFF -DBUILD_SHARED_LIBS:BOOL=OFF -DCMAKE_BUILD_TYPE=Release -G "NMake Makefiles" .
|
||||
nmake -nologo -f Makefile clean
|
||||
nmake -nologo -f Makefile
|
||||
copy /Y /B bin\* %%INCLIB%%
|
||||
mkdir %%INCLIB%%\openjpeg-%(op_ver)s
|
||||
copy /Y /B src\lib\openjp2\*.h %%INCLIB%%\openjpeg-%(op_ver)s
|
||||
endlocal
|
||||
""" # noqa: E501
|
||||
% atts
|
||||
)
|
||||
|
||||
|
||||
def nmake_libs(compiler, bit):
|
||||
# undone -- pre, makes, headers, libs
|
||||
script = (
|
||||
r"""
|
||||
rem Build libjpeg
|
||||
setlocal
|
||||
"""
|
||||
+ vc_setup(compiler, bit)
|
||||
+ r"""
|
||||
cd /D %%JPEG%%
|
||||
nmake -nologo -f makefile.vc setup-vc6
|
||||
nmake -nologo -f makefile.vc clean
|
||||
nmake -nologo -f makefile.vc nodebug=1 libjpeg.lib
|
||||
copy /Y /B *.dll %%INCLIB%%
|
||||
copy /Y /B *.lib %%INCLIB%%
|
||||
copy /Y /B j*.h %%INCLIB%%
|
||||
endlocal
|
||||
|
||||
rem Build zlib
|
||||
setlocal
|
||||
cd /D %%ZLIB%%
|
||||
nmake -nologo -f win32\Makefile.msc clean
|
||||
nmake -nologo -f win32\Makefile.msc zlib.lib
|
||||
copy /Y /B *.dll %%INCLIB%%
|
||||
copy /Y /B *.lib %%INCLIB%%
|
||||
copy /Y /B zlib.lib %%INCLIB%%\z.lib
|
||||
copy /Y /B zlib.h %%INCLIB%%
|
||||
copy /Y /B zconf.h %%INCLIB%%
|
||||
endlocal
|
||||
|
||||
rem Build webp
|
||||
setlocal
|
||||
"""
|
||||
+ vc_setup(compiler, bit)
|
||||
+ r"""
|
||||
cd /D %%WEBP%%
|
||||
rd /S /Q %%WEBP%%\output\release-static
|
||||
nmake -nologo -f Makefile.vc CFG=release-static RTLIBCFG=static OBJDIR=output all
|
||||
copy /Y /B output\release-static\%(webp_platform)s\lib\* %%INCLIB%%
|
||||
mkdir %%INCLIB%%\webp
|
||||
copy /Y /B src\webp\*.h %%INCLIB%%\\webp
|
||||
endlocal
|
||||
|
||||
rem Build libtiff
|
||||
setlocal
|
||||
"""
|
||||
+ vc_setup(compiler, bit)
|
||||
+ r"""
|
||||
rem do after building jpeg and zlib
|
||||
copy %%~dp0\tiff.opt %%TIFF%%\nmake.opt
|
||||
|
||||
cd /D %%TIFF%%
|
||||
nmake -nologo -f makefile.vc clean
|
||||
nmake -nologo -f makefile.vc lib
|
||||
copy /Y /B libtiff\*.dll %%INCLIB%%
|
||||
copy /Y /B libtiff\*.lib %%INCLIB%%
|
||||
copy /Y /B libtiff\tiff*.h %%INCLIB%%
|
||||
endlocal
|
||||
"""
|
||||
)
|
||||
return script % compiler
|
||||
|
||||
|
||||
def msbuild_freetype(compiler, bit):
|
||||
script = r"""
|
||||
rem Build freetype
|
||||
setlocal
|
||||
rd /S /Q %%FREETYPE%%\objs
|
||||
set DefaultPlatformToolset=v100
|
||||
"""
|
||||
properties = r"""/p:Configuration="Release" /p:Platform=%(platform)s"""
|
||||
if bit == 64:
|
||||
script += (
|
||||
r"copy /Y /B "
|
||||
r'"C:\Program Files (x86)\Microsoft SDKs\Windows\v7.1A\Lib\x64\*.Lib" '
|
||||
r"%%FREETYPE%%\builds\windows\vc2010"
|
||||
)
|
||||
properties += r" /p:_IsNativeEnvironment=false"
|
||||
script += (
|
||||
r"""
|
||||
%%MSBUILD%% %%FREETYPE%%\builds\windows\vc2010\freetype.sln /t:Clean;Build """
|
||||
+ properties
|
||||
+ r""" /m
|
||||
xcopy /Y /E /Q %%FREETYPE%%\include %%INCLIB%%
|
||||
"""
|
||||
)
|
||||
freetypeReleaseDir = r"%%FREETYPE%%\objs\%(platform)s\Release"
|
||||
script += (
|
||||
r"""
|
||||
copy /Y /B """
|
||||
+ freetypeReleaseDir
|
||||
+ r"""\freetype.lib %%INCLIB%%\freetype.lib
|
||||
copy /Y /B """
|
||||
+ freetypeReleaseDir
|
||||
+ r"""\freetype.dll %%INCLIB%%\..\freetype.dll
|
||||
endlocal
|
||||
"""
|
||||
)
|
||||
return script % compiler
|
||||
|
||||
|
||||
def build_lcms2(compiler):
|
||||
if compiler["env_version"] == "v7.1":
|
||||
return build_lcms_71(compiler)
|
||||
return build_lcms_70(compiler)
|
||||
|
||||
|
||||
def build_lcms_70(compiler):
|
||||
"""Link error here on x64"""
|
||||
if compiler["platform"] == "x64":
|
||||
return ""
|
||||
|
||||
"""Build LCMS on VC2008. This version is only 32bit/Win32"""
|
||||
return (
|
||||
r"""
|
||||
rem Build lcms2
|
||||
setlocal
|
||||
set LCMS=%%LCMS-2.7%%
|
||||
rd /S /Q %%LCMS%%\Lib
|
||||
rd /S /Q %%LCMS%%\Projects\VC%(vc_version)s\Release
|
||||
%%MSBUILD%% %%LCMS%%\Projects\VC%(vc_version)s\lcms2.sln /t:Clean /p:Configuration="Release" /p:Platform=Win32 /m
|
||||
%%MSBUILD%% %%LCMS%%\Projects\VC%(vc_version)s\lcms2.sln /t:lcms2_static /p:Configuration="Release" /p:Platform=Win32 /p:PlatformToolset=v90 /m
|
||||
xcopy /Y /E /Q %%LCMS%%\include %%INCLIB%%
|
||||
copy /Y /B %%LCMS%%\Lib\MS\*.lib %%INCLIB%%
|
||||
endlocal
|
||||
""" # noqa: E501
|
||||
% compiler
|
||||
)
|
||||
|
||||
|
||||
def build_lcms_71(compiler):
|
||||
return (
|
||||
r"""
|
||||
rem Build lcms2
|
||||
setlocal
|
||||
set LCMS=%%LCMS-2.8%%
|
||||
rd /S /Q %%LCMS%%\Lib
|
||||
rd /S /Q %%LCMS%%\Projects\VC%(vc_version)s\Release
|
||||
powershell -Command "(gc Projects\VC2015\lcms2_static\lcms2_static.vcxproj) -replace 'MultiThreadedDLL', 'MultiThreaded' | Out-File -encoding ASCII Projects\VC2015\lcms2_static\lcms2_static.vcxproj"
|
||||
%%MSBUILD%% %%LCMS%%\Projects\VC%(vc_version)s\lcms2.sln /t:Clean /p:Configuration="Release" /p:Platform=%(platform)s /m
|
||||
%%MSBUILD%% %%LCMS%%\Projects\VC%(vc_version)s\lcms2.sln /t:lcms2_static /p:Configuration="Release" /p:Platform=%(platform)s /m
|
||||
xcopy /Y /E /Q %%LCMS%%\include %%INCLIB%%
|
||||
copy /Y /B %%LCMS%%\Lib\MS\*.lib %%INCLIB%%
|
||||
endlocal
|
||||
""" # noqa: E501
|
||||
% compiler
|
||||
)
|
||||
|
||||
|
||||
def add_compiler(compiler, bit):
|
||||
script.append(setup_compiler(compiler))
|
||||
script.append(nmake_libs(compiler, bit))
|
||||
|
||||
# script.append(extract_openjpeg(compiler))
|
||||
|
||||
script.append(msbuild_freetype(compiler, bit))
|
||||
script.append(build_lcms2(compiler))
|
||||
script.append(nmake_openjpeg(compiler, bit))
|
||||
script.append(end_compiler())
|
||||
|
||||
|
||||
mkdirs()
|
||||
extract_libs()
|
||||
script = [header(), cp_tk(libs["tk-8.5"]["version"], libs["tk-8.6"]["version"])]
|
||||
|
||||
|
||||
if "PYTHON" in os.environ:
|
||||
add_compiler(compiler_from_env(), bit_from_env())
|
||||
else:
|
||||
# for compiler in all_compilers():
|
||||
# add_compiler(compiler)
|
||||
add_compiler(compilers[7.0][2010][32], 32)
|
||||
|
||||
with open("build_deps.cmd", "w") as f:
|
||||
f.write("\n".join(script))
|
557
winbuild/build_prepare.py
Normal file
557
winbuild/build_prepare.py
Normal file
|
@ -0,0 +1,557 @@
|
|||
import os
|
||||
import shutil
|
||||
import struct
|
||||
import subprocess
|
||||
import sys
|
||||
|
||||
|
||||
def cmd_cd(path):
|
||||
return "cd /D {path}".format(**locals())
|
||||
|
||||
|
||||
def cmd_set(name, value):
|
||||
return "set {name}={value}".format(**locals())
|
||||
|
||||
|
||||
def cmd_append(name, value):
|
||||
op = "path " if name == "PATH" else "set {name}="
|
||||
return (op + "%{name}%;{value}").format(**locals())
|
||||
|
||||
|
||||
def cmd_copy(src, tgt):
|
||||
return 'copy /Y /B "{src}" "{tgt}"'.format(**locals())
|
||||
|
||||
|
||||
def cmd_xcopy(src, tgt):
|
||||
return 'xcopy /Y /E "{src}" "{tgt}"'.format(**locals())
|
||||
|
||||
|
||||
def cmd_mkdir(path):
|
||||
return 'mkdir "{path}"'.format(**locals())
|
||||
|
||||
|
||||
def cmd_rmdir(path):
|
||||
return 'rmdir /S /Q "{path}"'.format(**locals())
|
||||
|
||||
|
||||
def cmd_nmake(makefile=None, target="", params=None):
|
||||
if params is None:
|
||||
params = ""
|
||||
elif isinstance(params, list) or isinstance(params, tuple):
|
||||
params = " ".join(params)
|
||||
else:
|
||||
params = str(params)
|
||||
|
||||
return " ".join(
|
||||
[
|
||||
"{{nmake}}",
|
||||
"-nologo",
|
||||
'-f "{makefile}"' if makefile is not None else "",
|
||||
"{params}",
|
||||
'"{target}"',
|
||||
]
|
||||
).format(**locals())
|
||||
|
||||
|
||||
def cmd_cmake(params=None, file="."):
|
||||
if params is None:
|
||||
params = ""
|
||||
elif isinstance(params, list) or isinstance(params, tuple):
|
||||
params = " ".join(params)
|
||||
else:
|
||||
params = str(params)
|
||||
return " ".join(
|
||||
[
|
||||
"{{cmake}}",
|
||||
"-DCMAKE_VERBOSE_MAKEFILE=ON",
|
||||
"-DCMAKE_RULE_MESSAGES:BOOL=OFF",
|
||||
"-DCMAKE_BUILD_TYPE=Release",
|
||||
"{params}",
|
||||
'-G "NMake Makefiles"',
|
||||
'"{file}"',
|
||||
]
|
||||
).format(**locals())
|
||||
|
||||
|
||||
def cmd_msbuild(
|
||||
file, configuration="Release", target="Build", platform="{msbuild_arch}"
|
||||
):
|
||||
return " ".join(
|
||||
[
|
||||
"{{msbuild}}",
|
||||
"{file}",
|
||||
'/t:"{target}"',
|
||||
'/p:Configuration="{configuration}"',
|
||||
"/p:Platform={platform}",
|
||||
"/m",
|
||||
]
|
||||
).format(**locals())
|
||||
|
||||
|
||||
SF_MIRROR = "http://iweb.dl.sourceforge.net"
|
||||
|
||||
architectures = {
|
||||
"x86": {"vcvars_arch": "x86", "msbuild_arch": "Win32"},
|
||||
"x64": {"vcvars_arch": "x86_amd64", "msbuild_arch": "x64"},
|
||||
}
|
||||
|
||||
header = [
|
||||
cmd_set("INCLUDE", "{inc_dir}"),
|
||||
cmd_set("INCLIB", "{lib_dir}"),
|
||||
cmd_set("LIB", "{lib_dir}"),
|
||||
cmd_append("PATH", "{bin_dir}"),
|
||||
]
|
||||
|
||||
# dependencies, listed in order of compilation
|
||||
deps = {
|
||||
"libjpeg": {
|
||||
"url": SF_MIRROR + "/project/libjpeg-turbo/2.0.3/libjpeg-turbo-2.0.3.tar.gz",
|
||||
"filename": "libjpeg-turbo-2.0.3.tar.gz",
|
||||
"dir": "libjpeg-turbo-2.0.3",
|
||||
"build": [
|
||||
cmd_cmake(
|
||||
[
|
||||
"-DENABLE_SHARED:BOOL=FALSE",
|
||||
"-DWITH_JPEG8:BOOL=TRUE",
|
||||
"-DWITH_CRT_DLL:BOOL=TRUE",
|
||||
]
|
||||
),
|
||||
cmd_nmake(target="clean"),
|
||||
cmd_nmake(target="jpeg-static"),
|
||||
cmd_copy("jpeg-static.lib", "libjpeg.lib"),
|
||||
cmd_nmake(target="cjpeg-static"),
|
||||
cmd_copy("cjpeg-static.exe", "cjpeg.exe"),
|
||||
cmd_nmake(target="djpeg-static"),
|
||||
cmd_copy("djpeg-static.exe", "djpeg.exe"),
|
||||
],
|
||||
"headers": ["j*.h"],
|
||||
"libs": ["libjpeg.lib"],
|
||||
"bins": ["cjpeg.exe", "djpeg.exe"],
|
||||
},
|
||||
"zlib": {
|
||||
"url": "http://zlib.net/zlib1211.zip",
|
||||
"filename": "zlib1211.zip",
|
||||
"dir": "zlib-1.2.11",
|
||||
"build": [
|
||||
cmd_nmake(r"win32\Makefile.msc", "clean"),
|
||||
cmd_nmake(r"win32\Makefile.msc", "zlib.lib"),
|
||||
cmd_copy("zlib.lib", "z.lib"),
|
||||
],
|
||||
"headers": [r"z*.h"],
|
||||
"libs": [r"*.lib"],
|
||||
},
|
||||
"libtiff": {
|
||||
"url": "https://download.osgeo.org/libtiff/tiff-4.1.0.tar.gz",
|
||||
"filename": "tiff-4.1.0.tar.gz",
|
||||
"dir": "tiff-4.1.0",
|
||||
"build": [
|
||||
cmd_copy(r"{winbuild_dir}\tiff.opt", "nmake.opt"),
|
||||
cmd_nmake("makefile.vc", "clean"),
|
||||
cmd_nmake("makefile.vc", "lib"),
|
||||
],
|
||||
"headers": [r"libtiff\tiff*.h"],
|
||||
"libs": [r"libtiff\*.lib"],
|
||||
# "bins": [r"libtiff\*.dll"],
|
||||
},
|
||||
"libwebp": {
|
||||
"url": "http://downloads.webmproject.org/releases/webp/libwebp-1.1.0.tar.gz", # noqa: E501
|
||||
"filename": "libwebp-1.1.0.tar.gz",
|
||||
"dir": "libwebp-1.1.0",
|
||||
"build": [
|
||||
cmd_rmdir(r"output\release-static"), # clean
|
||||
cmd_nmake(
|
||||
"Makefile.vc",
|
||||
"all",
|
||||
["CFG=release-static", "OBJDIR=output", "ARCH={architecture}"],
|
||||
),
|
||||
cmd_mkdir(r"{inc_dir}\webp"),
|
||||
cmd_copy(r"src\webp\*.h", r"{inc_dir}\webp"),
|
||||
],
|
||||
"libs": [r"output\release-static\{architecture}\lib\*.lib"],
|
||||
},
|
||||
"freetype": {
|
||||
"url": "https://download.savannah.gnu.org/releases/freetype/freetype-2.10.2.tar.gz", # noqa: E501
|
||||
"filename": "freetype-2.10.2.tar.gz",
|
||||
"dir": "freetype-2.10.2",
|
||||
"patch": {
|
||||
r"builds\windows\vc2010\freetype.vcxproj": {
|
||||
# freetype setting is /MD for .dll and /MT for .lib, we need /MD
|
||||
"<RuntimeLibrary>MultiThreaded</RuntimeLibrary>": "<RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>", # noqa: E501
|
||||
# freetype doesn't specify SDK version, MSBuild may guess incorrectly
|
||||
'<PropertyGroup Label="Globals">': '<PropertyGroup Label="Globals">\n <WindowsTargetPlatformVersion>$(WindowsSDKVersion)</WindowsTargetPlatformVersion>', # noqa: E501
|
||||
}
|
||||
},
|
||||
"build": [
|
||||
cmd_rmdir("objs"),
|
||||
cmd_msbuild(
|
||||
r"builds\windows\vc2010\freetype.sln", "Release Static", "Clean"
|
||||
),
|
||||
cmd_msbuild(
|
||||
r"builds\windows\vc2010\freetype.sln", "Release Static", "Build"
|
||||
),
|
||||
cmd_xcopy("include", "{inc_dir}"),
|
||||
],
|
||||
"libs": [r"objs\{msbuild_arch}\Release Static\freetype.lib"],
|
||||
# "bins": [r"objs\{msbuild_arch}\Release\freetype.dll"],
|
||||
},
|
||||
"lcms2": {
|
||||
"url": SF_MIRROR + "/project/lcms/lcms/2.9/lcms2-2.9.tar.gz",
|
||||
"filename": "lcms2-2.9.tar.gz",
|
||||
"dir": "lcms2-2.9",
|
||||
"patch": {
|
||||
r"Projects\VC2017\lcms2_static\lcms2_static.vcxproj": {
|
||||
# default is /MD for x86 and /MT for x64, we need /MD always
|
||||
"<RuntimeLibrary>MultiThreaded</RuntimeLibrary>": "<RuntimeLibrary>MultiThreadedDLL</RuntimeLibrary>", # noqa: E501
|
||||
# retarget to default toolset (selected by vcvarsall.bat)
|
||||
"<PlatformToolset>v141</PlatformToolset>": "<PlatformToolset>$(DefaultPlatformToolset)</PlatformToolset>", # noqa: E501
|
||||
# retarget to latest (selected by vcvarsall.bat)
|
||||
"<WindowsTargetPlatformVersion>8.1</WindowsTargetPlatformVersion>": "<WindowsTargetPlatformVersion>$(WindowsSDKVersion)</WindowsTargetPlatformVersion>", # noqa: E501
|
||||
}
|
||||
},
|
||||
"build": [
|
||||
cmd_rmdir("Lib"),
|
||||
cmd_rmdir(r"Projects\VC2017\Release"),
|
||||
cmd_msbuild(r"Projects\VC2017\lcms2.sln", "Release", "Clean"),
|
||||
cmd_msbuild(r"Projects\VC2017\lcms2.sln", "Release", "lcms2_static"),
|
||||
cmd_xcopy("include", "{inc_dir}"),
|
||||
],
|
||||
"libs": [r"Lib\MS\*.lib"],
|
||||
},
|
||||
"openjpeg": {
|
||||
"url": "https://github.com/uclouvain/openjpeg/archive/v2.3.1.tar.gz",
|
||||
"filename": "openjpeg-2.3.1.tar.gz",
|
||||
"dir": "openjpeg-2.3.1",
|
||||
"build": [
|
||||
cmd_cmake(("-DBUILD_THIRDPARTY:BOOL=OFF", "-DBUILD_SHARED_LIBS:BOOL=OFF")),
|
||||
cmd_nmake(target="clean"),
|
||||
cmd_nmake(target="openjp2"),
|
||||
cmd_mkdir(r"{inc_dir}\openjpeg-2.3.1"),
|
||||
cmd_copy(r"src\lib\openjp2\*.h", r"{inc_dir}\openjpeg-2.3.1"),
|
||||
],
|
||||
"libs": [r"bin\*.lib"],
|
||||
},
|
||||
"libimagequant": {
|
||||
# e5d454b: Merge tag '2.12.6' into msvc
|
||||
"url": "https://github.com/ImageOptim/libimagequant/archive/e5d454bc7f5eb63ee50c84a83a7fa5ac94f68ec4.zip", # noqa: E501
|
||||
"filename": "libimagequant-e5d454bc7f5eb63ee50c84a83a7fa5ac94f68ec4.zip",
|
||||
"dir": "libimagequant-e5d454bc7f5eb63ee50c84a83a7fa5ac94f68ec4",
|
||||
"patch": {
|
||||
"CMakeLists.txt": {
|
||||
"add_library": "add_compile_options(-openmp-)\r\nadd_library",
|
||||
" SHARED": " STATIC",
|
||||
}
|
||||
},
|
||||
"build": [
|
||||
# lint: do not inline
|
||||
cmd_cmake(),
|
||||
cmd_nmake(target="clean"),
|
||||
cmd_nmake(),
|
||||
],
|
||||
"headers": [r"*.h"],
|
||||
"libs": [r"*.lib"],
|
||||
},
|
||||
"harfbuzz": {
|
||||
"url": "https://github.com/harfbuzz/harfbuzz/archive/2.6.4.zip",
|
||||
"filename": "harfbuzz-2.6.4.zip",
|
||||
"dir": "harfbuzz-2.6.4",
|
||||
"build": [
|
||||
cmd_cmake("-DHB_HAVE_FREETYPE:BOOL=TRUE"),
|
||||
cmd_nmake(target="clean"),
|
||||
cmd_nmake(target="harfbuzz"),
|
||||
],
|
||||
"headers": [r"src\*.h"],
|
||||
"libs": [r"*.lib"],
|
||||
},
|
||||
"fribidi": {
|
||||
"url": "https://github.com/fribidi/fribidi/archive/v1.0.9.zip",
|
||||
"filename": "fribidi-1.0.9.zip",
|
||||
"dir": "fribidi-1.0.9",
|
||||
"build": [
|
||||
cmd_copy(r"{winbuild_dir}\fribidi.cmake", r"CMakeLists.txt"),
|
||||
cmd_cmake(),
|
||||
cmd_nmake(target="clean"),
|
||||
cmd_nmake(target="fribidi"),
|
||||
],
|
||||
"headers": [r"lib\*.h"],
|
||||
"libs": [r"*.lib"],
|
||||
},
|
||||
"libraqm": {
|
||||
"url": "https://github.com/HOST-Oman/libraqm/archive/v0.7.0.zip",
|
||||
"filename": "libraqm-0.7.0.zip",
|
||||
"dir": "libraqm-0.7.0",
|
||||
"build": [
|
||||
cmd_copy(r"{winbuild_dir}\raqm.cmake", r"CMakeLists.txt"),
|
||||
cmd_cmake(),
|
||||
cmd_nmake(target="clean"),
|
||||
cmd_nmake(target="libraqm"),
|
||||
],
|
||||
"headers": [r"src\*.h"],
|
||||
"bins": [r"libraqm.dll"],
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
# based on distutils._msvccompiler from CPython 3.7.4
|
||||
def find_msvs():
|
||||
root = os.environ.get("ProgramFiles(x86)") or os.environ.get("ProgramFiles")
|
||||
if not root:
|
||||
print("Program Files not found")
|
||||
return None
|
||||
|
||||
try:
|
||||
vspath = (
|
||||
subprocess.check_output(
|
||||
[
|
||||
os.path.join(
|
||||
root, "Microsoft Visual Studio", "Installer", "vswhere.exe"
|
||||
),
|
||||
"-latest",
|
||||
"-prerelease",
|
||||
"-requires",
|
||||
"Microsoft.VisualStudio.Component.VC.Tools.x86.x64",
|
||||
"-property",
|
||||
"installationPath",
|
||||
"-products",
|
||||
"*",
|
||||
]
|
||||
)
|
||||
.decode(encoding="mbcs")
|
||||
.strip()
|
||||
)
|
||||
except (subprocess.CalledProcessError, OSError, UnicodeDecodeError):
|
||||
print("vswhere not found")
|
||||
return None
|
||||
|
||||
if not os.path.isdir(os.path.join(vspath, "VC", "Auxiliary", "Build")):
|
||||
print("Visual Studio seems to be missing C compiler")
|
||||
return None
|
||||
|
||||
vs = {
|
||||
"header": [],
|
||||
# nmake selected by vcvarsall
|
||||
"nmake": "nmake.exe",
|
||||
"vs_dir": vspath,
|
||||
}
|
||||
|
||||
# vs2017
|
||||
msbuild = os.path.join(vspath, "MSBuild", "15.0", "Bin", "MSBuild.exe")
|
||||
if os.path.isfile(msbuild):
|
||||
vs["msbuild"] = '"{}"'.format(msbuild)
|
||||
else:
|
||||
# vs2019
|
||||
msbuild = os.path.join(vspath, "MSBuild", "Current", "Bin", "MSBuild.exe")
|
||||
if os.path.isfile(msbuild):
|
||||
vs["msbuild"] = '"{}"'.format(msbuild)
|
||||
else:
|
||||
print("Visual Studio MSBuild not found")
|
||||
return None
|
||||
|
||||
vcvarsall = os.path.join(vspath, "VC", "Auxiliary", "Build", "vcvarsall.bat")
|
||||
if not os.path.isfile(vcvarsall):
|
||||
print("Visual Studio vcvarsall not found")
|
||||
return None
|
||||
vs["header"].append('call "{}" {{vcvars_arch}}'.format(vcvarsall))
|
||||
|
||||
return vs
|
||||
|
||||
|
||||
def extract_dep(url, filename):
|
||||
import urllib.request
|
||||
import tarfile
|
||||
import zipfile
|
||||
|
||||
file = os.path.join(depends_dir, filename)
|
||||
if not os.path.exists(file):
|
||||
ex = None
|
||||
for i in range(3):
|
||||
try:
|
||||
print("Fetching %s (attempt %d)..." % (url, i + 1))
|
||||
content = urllib.request.urlopen(url).read()
|
||||
with open(file, "wb") as f:
|
||||
f.write(content)
|
||||
break
|
||||
except urllib.error.URLError as e:
|
||||
ex = e
|
||||
else:
|
||||
raise RuntimeError(ex)
|
||||
|
||||
print("Extracting " + filename)
|
||||
if filename.endswith(".zip"):
|
||||
with zipfile.ZipFile(file) as zf:
|
||||
zf.extractall(build_dir)
|
||||
elif filename.endswith(".tar.gz") or filename.endswith(".tgz"):
|
||||
with tarfile.open(file, "r:gz") as tgz:
|
||||
tgz.extractall(build_dir)
|
||||
else:
|
||||
raise RuntimeError("Unknown archive type: " + filename)
|
||||
|
||||
|
||||
def write_script(name, lines):
|
||||
name = os.path.join(build_dir, name)
|
||||
lines = [line.format(**prefs) for line in lines]
|
||||
print("Writing " + name)
|
||||
with open(name, "w") as f:
|
||||
f.write("\n\r".join(lines))
|
||||
if verbose:
|
||||
for line in lines:
|
||||
print(" " + line)
|
||||
|
||||
|
||||
def get_footer(dep):
|
||||
lines = []
|
||||
for out in dep.get("headers", []):
|
||||
lines.append(cmd_copy(out, "{inc_dir}"))
|
||||
for out in dep.get("libs", []):
|
||||
lines.append(cmd_copy(out, "{lib_dir}"))
|
||||
for out in dep.get("bins", []):
|
||||
lines.append(cmd_copy(out, "{bin_dir}"))
|
||||
return lines
|
||||
|
||||
|
||||
def build_dep(name):
|
||||
dep = deps[name]
|
||||
dir = dep["dir"]
|
||||
file = "build_dep_{name}.cmd".format(**locals())
|
||||
|
||||
extract_dep(dep["url"], dep["filename"])
|
||||
|
||||
for patch_file, patch_list in dep.get("patch", {}).items():
|
||||
patch_file = os.path.join(build_dir, dir, patch_file.format(**prefs))
|
||||
with open(patch_file, "r") as f:
|
||||
text = f.read()
|
||||
for patch_from, patch_to in patch_list.items():
|
||||
text = text.replace(patch_from.format(**prefs), patch_to.format(**prefs))
|
||||
with open(patch_file, "w") as f:
|
||||
f.write(text)
|
||||
|
||||
banner = "Building {name} ({dir})".format(**locals())
|
||||
lines = [
|
||||
"@echo " + ("=" * 70),
|
||||
"@echo ==== {:<60} ====".format(banner),
|
||||
"@echo " + ("=" * 70),
|
||||
"cd /D %s" % os.path.join(build_dir, dir),
|
||||
*prefs["header"],
|
||||
*dep.get("build", []),
|
||||
*get_footer(dep),
|
||||
]
|
||||
|
||||
write_script(file, lines)
|
||||
return file
|
||||
|
||||
|
||||
def build_dep_all():
|
||||
lines = ["@echo on"]
|
||||
for dep_name in deps:
|
||||
if dep_name in disabled:
|
||||
continue
|
||||
lines.append(r'cmd.exe /c "{{build_dir}}\{}"'.format(build_dep(dep_name)))
|
||||
lines.append("if errorlevel 1 echo Build failed! && exit /B 1")
|
||||
lines.append("@echo All Pillow dependencies built successfully!")
|
||||
write_script("build_dep_all.cmd", lines)
|
||||
|
||||
|
||||
def build_pillow():
|
||||
lines = [
|
||||
"@echo ---- Building Pillow (build_ext %*) ----",
|
||||
cmd_cd("{pillow_dir}"),
|
||||
*prefs["header"],
|
||||
cmd_set("DISTUTILS_USE_SDK", "1"), # use same compiler to build Pillow
|
||||
cmd_set("MSSdk", "1"), # for Python 3.5 and PyPy3.6
|
||||
cmd_set("py_vcruntime_redist", "true"), # use /MD, not /MT
|
||||
r'"{python_dir}\{python_exe}" setup.py build_ext %*',
|
||||
]
|
||||
|
||||
write_script("build_pillow.cmd", lines)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
# winbuild directory
|
||||
winbuild_dir = os.path.dirname(os.path.realpath(__file__))
|
||||
|
||||
verbose = False
|
||||
disabled = []
|
||||
depends_dir = os.environ.get("PILLOW_DEPS", os.path.join(winbuild_dir, "depends"))
|
||||
python_dir = os.environ.get("PYTHON")
|
||||
python_exe = os.environ.get("EXECUTABLE", "python.exe")
|
||||
architecture = os.environ.get(
|
||||
"ARCHITECTURE", "x86" if struct.calcsize("P") == 4 else "x64"
|
||||
)
|
||||
build_dir = os.environ.get("PILLOW_BUILD", os.path.join(winbuild_dir, "build"))
|
||||
for arg in sys.argv[1:]:
|
||||
if arg == "-v":
|
||||
verbose = True
|
||||
elif arg == "--no-imagequant":
|
||||
disabled += ["libimagequant"]
|
||||
elif arg == "--no-raqm":
|
||||
disabled += ["harfbuzz", "fribidi", "libraqm"]
|
||||
elif arg.startswith("--depends="):
|
||||
depends_dir = arg[10:]
|
||||
elif arg.startswith("--python="):
|
||||
python_dir = arg[9:]
|
||||
elif arg.startswith("--executable="):
|
||||
python_exe = arg[13:]
|
||||
elif arg.startswith("--architecture="):
|
||||
architecture = arg[15:]
|
||||
elif arg.startswith("--dir="):
|
||||
build_dir = arg[6:]
|
||||
else:
|
||||
raise ValueError("Unknown parameter: " + arg)
|
||||
|
||||
# dependency cache directory
|
||||
os.makedirs(depends_dir, exist_ok=True)
|
||||
print("Caching dependencies in:", depends_dir)
|
||||
|
||||
if python_dir is None:
|
||||
python_dir = os.path.dirname(os.path.realpath(sys.executable))
|
||||
python_exe = os.path.basename(sys.executable)
|
||||
print("Target Python:", os.path.join(python_dir, python_exe))
|
||||
|
||||
arch_prefs = architectures[architecture]
|
||||
print("Target Architecture:", architecture)
|
||||
|
||||
msvs = find_msvs()
|
||||
if msvs is None:
|
||||
raise RuntimeError(
|
||||
"Visual Studio not found. Please install Visual Studio 2017 or newer."
|
||||
)
|
||||
print("Found Visual Studio at:", msvs["vs_dir"])
|
||||
|
||||
print("Using output directory:", build_dir)
|
||||
|
||||
# build directory for *.h files
|
||||
inc_dir = os.path.join(build_dir, "inc")
|
||||
# build directory for *.lib files
|
||||
lib_dir = os.path.join(build_dir, "lib")
|
||||
# build directory for *.bin files
|
||||
bin_dir = os.path.join(build_dir, "bin")
|
||||
|
||||
shutil.rmtree(build_dir, ignore_errors=True)
|
||||
for path in [build_dir, inc_dir, lib_dir, bin_dir]:
|
||||
os.makedirs(path)
|
||||
|
||||
prefs = {
|
||||
# Python paths / preferences
|
||||
"python_dir": python_dir,
|
||||
"python_exe": python_exe,
|
||||
"architecture": architecture,
|
||||
**arch_prefs,
|
||||
# Pillow paths
|
||||
"pillow_dir": os.path.realpath(os.path.join(winbuild_dir, "..")),
|
||||
"winbuild_dir": winbuild_dir,
|
||||
# Build paths
|
||||
"build_dir": build_dir,
|
||||
"inc_dir": inc_dir,
|
||||
"lib_dir": lib_dir,
|
||||
"bin_dir": bin_dir,
|
||||
# Compilers / Tools
|
||||
**msvs,
|
||||
"cmake": "cmake.exe", # TODO find CMAKE automatically
|
||||
# TODO find NASM automatically
|
||||
# script header
|
||||
"header": sum([header, msvs["header"], ["@echo on"]], []),
|
||||
}
|
||||
|
||||
print()
|
||||
|
||||
build_dep_all()
|
||||
build_pillow()
|
|
@ -1,199 +0,0 @@
|
|||
import os
|
||||
|
||||
SF_MIRROR = "https://iweb.dl.sourceforge.net"
|
||||
|
||||
pythons = {
|
||||
"pypy3": {"compiler": 7.1, "vc": 2015},
|
||||
# for AppVeyor
|
||||
"35": {"compiler": 7.1, "vc": 2015},
|
||||
"36": {"compiler": 7.1, "vc": 2015},
|
||||
"37": {"compiler": 7.1, "vc": 2015},
|
||||
"38": {"compiler": 7.1, "vc": 2015},
|
||||
# for GitHub Actions
|
||||
"3.5": {"compiler": 7.1, "vc": 2015},
|
||||
"3.6": {"compiler": 7.1, "vc": 2015},
|
||||
"3.7": {"compiler": 7.1, "vc": 2015},
|
||||
"3.8": {"compiler": 7.1, "vc": 2015},
|
||||
}
|
||||
|
||||
VIRT_BASE = "c:/vp/"
|
||||
X64_EXT = os.environ.get("X64_EXT", "x64")
|
||||
|
||||
libs = {
|
||||
# 'openjpeg': {
|
||||
# 'filename': 'openjpeg-2.0.0-win32-x86.zip',
|
||||
# 'version': '2.0'
|
||||
# },
|
||||
"zlib": {
|
||||
"url": "http://zlib.net/zlib1211.zip",
|
||||
"filename": "zlib1211.zip",
|
||||
"dir": "zlib-1.2.11",
|
||||
},
|
||||
"jpeg": {
|
||||
"url": "http://www.ijg.org/files/jpegsr9d.zip",
|
||||
"filename": "jpegsr9d.zip",
|
||||
"dir": "jpeg-9d",
|
||||
},
|
||||
"tiff": {
|
||||
"url": "ftp://download.osgeo.org/libtiff/tiff-4.1.0.tar.gz",
|
||||
"filename": "tiff-4.1.0.tar.gz",
|
||||
"dir": "tiff-4.1.0",
|
||||
},
|
||||
"freetype": {
|
||||
"url": "https://download.savannah.gnu.org/releases/freetype/freetype-2.10.2.tar.gz", # noqa: E501
|
||||
"filename": "freetype-2.10.2.tar.gz",
|
||||
"dir": "freetype-2.10.2",
|
||||
},
|
||||
"lcms-2.7": {
|
||||
"url": SF_MIRROR + "/project/lcms/lcms/2.7/lcms2-2.7.zip",
|
||||
"filename": "lcms2-2.7.zip",
|
||||
"dir": "lcms2-2.7",
|
||||
},
|
||||
"lcms-2.8": {
|
||||
"url": SF_MIRROR + "/project/lcms/lcms/2.8/lcms2-2.8.zip",
|
||||
"filename": "lcms2-2.8.zip",
|
||||
"dir": "lcms2-2.8",
|
||||
},
|
||||
"tcl-8.5": {
|
||||
"url": SF_MIRROR + "/project/tcl/Tcl/8.5.19/tcl8519-src.zip",
|
||||
"filename": "tcl8519-src.zip",
|
||||
"dir": "",
|
||||
},
|
||||
"tk-8.5": {
|
||||
"url": SF_MIRROR + "/project/tcl/Tcl/8.5.19/tk8519-src.zip",
|
||||
"filename": "tk8519-src.zip",
|
||||
"dir": "",
|
||||
"version": "8.5.19",
|
||||
},
|
||||
"tcl-8.6": {
|
||||
"url": SF_MIRROR + "/project/tcl/Tcl/8.6.10/tcl8610-src.zip",
|
||||
"filename": "tcl8610-src.zip",
|
||||
"dir": "",
|
||||
},
|
||||
"tk-8.6": {
|
||||
"url": SF_MIRROR + "/project/tcl/Tcl/8.6.10/tk8610-src.zip",
|
||||
"filename": "tk8610-src.zip",
|
||||
"dir": "",
|
||||
"version": "8.6.10",
|
||||
},
|
||||
"webp": {
|
||||
"url": "http://downloads.webmproject.org/releases/webp/libwebp-1.1.0.tar.gz",
|
||||
"filename": "libwebp-1.1.0.tar.gz",
|
||||
"dir": "libwebp-1.1.0",
|
||||
},
|
||||
"openjpeg": {
|
||||
"url": "https://github.com/uclouvain/openjpeg/archive/v2.3.1.tar.gz",
|
||||
"filename": "openjpeg-2.3.1.tar.gz",
|
||||
"dir": "openjpeg-2.3.1",
|
||||
},
|
||||
"jpeg-turbo": {
|
||||
"url": SF_MIRROR + "/project/libjpeg-turbo/2.0.3/libjpeg-turbo-2.0.3.tar.gz",
|
||||
"filename": "libjpeg-turbo-2.0.3.tar.gz",
|
||||
"dir": "libjpeg-turbo-2.0.3",
|
||||
},
|
||||
# e5d454b: Merge tag '2.12.6' into msvc
|
||||
"imagequant": {
|
||||
"url": "https://github.com/ImageOptim/libimagequant/archive/e5d454bc7f5eb63ee50c84a83a7fa5ac94f68ec4.zip", # noqa: E501
|
||||
"filename": "libimagequant-e5d454bc7f5eb63ee50c84a83a7fa5ac94f68ec4.zip",
|
||||
"dir": "libimagequant-e5d454bc7f5eb63ee50c84a83a7fa5ac94f68ec4",
|
||||
},
|
||||
"harfbuzz": {
|
||||
"url": "https://github.com/harfbuzz/harfbuzz/archive/2.6.4.zip",
|
||||
"filename": "harfbuzz-2.6.4.zip",
|
||||
"dir": "harfbuzz-2.6.4",
|
||||
},
|
||||
"fribidi": {
|
||||
"url": "https://github.com/fribidi/fribidi/archive/v1.0.9.zip",
|
||||
"filename": "fribidi-1.0.9.zip",
|
||||
"dir": "fribidi-1.0.9",
|
||||
},
|
||||
"libraqm": {
|
||||
"url": "https://github.com/HOST-Oman/libraqm/archive/v0.7.0.zip",
|
||||
"filename": "libraqm-0.7.0.zip",
|
||||
"dir": "libraqm-0.7.0",
|
||||
},
|
||||
}
|
||||
|
||||
compilers = {
|
||||
7: {
|
||||
2010: {
|
||||
64: {
|
||||
"env_version": "v7.0",
|
||||
"vc_version": "2010",
|
||||
"env_flags": "/x64 /xp",
|
||||
"inc_dir": "msvcr90-x64",
|
||||
"platform": "x64",
|
||||
"webp_platform": "x64",
|
||||
},
|
||||
32: {
|
||||
"env_version": "v7.0",
|
||||
"vc_version": "2010",
|
||||
"env_flags": "/x86 /xp",
|
||||
"inc_dir": "msvcr90-x32",
|
||||
"platform": "Win32",
|
||||
"webp_platform": "x86",
|
||||
},
|
||||
}
|
||||
},
|
||||
7.1: {
|
||||
2015: {
|
||||
64: {
|
||||
"env_version": "v7.1",
|
||||
"vc_version": "2015",
|
||||
"env_flags": "/x64 /vista",
|
||||
"inc_dir": "msvcr10-x64",
|
||||
"platform": "x64",
|
||||
"webp_platform": "x64",
|
||||
},
|
||||
32: {
|
||||
"env_version": "v7.1",
|
||||
"vc_version": "2015",
|
||||
"env_flags": "/x86 /vista",
|
||||
"inc_dir": "msvcr10-x32",
|
||||
"platform": "Win32",
|
||||
"webp_platform": "x86",
|
||||
},
|
||||
}
|
||||
},
|
||||
}
|
||||
|
||||
|
||||
def pyversion_from_env():
|
||||
py = os.environ["PYTHON"]
|
||||
|
||||
py_version = "35"
|
||||
for k in pythons:
|
||||
if k in py:
|
||||
py_version = k
|
||||
break
|
||||
|
||||
if "64" in py:
|
||||
py_version = "{}{}".format(py_version, X64_EXT)
|
||||
|
||||
return py_version
|
||||
|
||||
|
||||
def compiler_from_env():
|
||||
py = os.environ["PYTHON"]
|
||||
|
||||
for k, v in pythons.items():
|
||||
if k in py:
|
||||
py_info = v
|
||||
break
|
||||
|
||||
bit = bit_from_env()
|
||||
return compilers[py_info["compiler"]][py_info["vc"]][bit]
|
||||
|
||||
|
||||
def bit_from_env():
|
||||
py = os.environ["PYTHON"]
|
||||
|
||||
return 64 if "64" in py else 32
|
||||
|
||||
|
||||
def all_compilers():
|
||||
all = []
|
||||
for vc_compilers in compilers.values():
|
||||
for bit_compilers in vc_compilers.values():
|
||||
all += bit_compilers.values()
|
||||
return all
|
|
@ -1,44 +0,0 @@
|
|||
import os
|
||||
import sys
|
||||
import urllib.parse
|
||||
import urllib.request
|
||||
|
||||
from config import libs
|
||||
|
||||
|
||||
def fetch(url):
|
||||
depends_filename = None
|
||||
for lib in libs.values():
|
||||
if lib["url"] == url:
|
||||
depends_filename = lib["filename"]
|
||||
break
|
||||
if depends_filename and os.path.exists(depends_filename):
|
||||
return depends_filename
|
||||
name = urllib.parse.urlsplit(url)[2].split("/")[-1]
|
||||
|
||||
if not os.path.exists(name):
|
||||
|
||||
def retrieve(request_url):
|
||||
print("Fetching", request_url)
|
||||
try:
|
||||
return urllib.request.urlopen(request_url)
|
||||
except urllib.error.URLError:
|
||||
return urllib.request.urlopen(request_url)
|
||||
|
||||
try:
|
||||
r = retrieve(url)
|
||||
except urllib.error.HTTPError:
|
||||
if depends_filename:
|
||||
r = retrieve(
|
||||
"https://github.com/python-pillow/pillow-depends/raw/master/"
|
||||
+ depends_filename
|
||||
)
|
||||
name = depends_filename
|
||||
content = r.read()
|
||||
with open(name, "wb") as fd:
|
||||
fd.write(content)
|
||||
return name
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
fetch(sys.argv[1])
|
|
@ -1,4 +1,4 @@
|
|||
cmake_minimum_required(VERSION 3.13)
|
||||
cmake_minimum_required(VERSION 3.12)
|
||||
|
||||
project(fribidi)
|
||||
|
||||
|
|
|
@ -1,15 +0,0 @@
|
|||
import os
|
||||
|
||||
from fetch import fetch
|
||||
|
||||
if __name__ == "__main__":
|
||||
for version in ["3.4.4"]:
|
||||
for platform in ["", ".amd64"]:
|
||||
for extension in ["", ".asc"]:
|
||||
fetch(
|
||||
"https://www.python.org/ftp/python/%s/python-%s%s.msi%s"
|
||||
% (version, version, platform, extension)
|
||||
)
|
||||
|
||||
# find pip, if it's not in the path!
|
||||
os.system("pip install virtualenv")
|
|
@ -1,9 +0,0 @@
|
|||
|
||||
Get-ChildItem .\Projects\VC2015\ *.vcxproj -recurse |
|
||||
Foreach-Object {
|
||||
$c = ($_ | Get-Content)
|
||||
$c = $c -replace 'MultiThreaded<','MultiThreadedDLL<'
|
||||
$c = $c -replace '<WindowsTargetPlatformVersion>8.1</WindowsTargetPlatformVersion>','<WindowsTargetPlatformVersion>10</WindowsTargetPlatformVersion>'
|
||||
$c = $c -replace '<PlatformToolset>v140</PlatformToolset>','<PlatformToolset>v142</PlatformToolset>'
|
||||
[IO.File]::WriteAllText($_.FullName, ($c -join "`r`n"))
|
||||
}
|
|
@ -1,4 +1,4 @@
|
|||
cmake_minimum_required(VERSION 3.13)
|
||||
cmake_minimum_required(VERSION 3.12)
|
||||
|
||||
project(libraqm)
|
||||
|
||||
|
|
|
@ -1,45 +0,0 @@
|
|||
#!/usr/bin/env python3
|
||||
|
||||
import glob
|
||||
import os
|
||||
import subprocess
|
||||
import sys
|
||||
|
||||
from config import VIRT_BASE, X64_EXT, pythons
|
||||
|
||||
|
||||
def test_one(params):
|
||||
python, architecture = params
|
||||
try:
|
||||
print("Running: %s, %s" % params)
|
||||
command = [
|
||||
r"{}\{}{}\Scripts\python.exe".format(VIRT_BASE, python, architecture),
|
||||
"test-installed.py",
|
||||
"--processes=-0",
|
||||
"--process-timeout=30",
|
||||
]
|
||||
command.extend(glob.glob("Tests/test*.py"))
|
||||
proc = subprocess.Popen(command, stdin=subprocess.PIPE, stdout=subprocess.PIPE)
|
||||
(trace, stderr) = proc.communicate()
|
||||
status = proc.returncode
|
||||
print("Done with {}, {} -- {}".format(python, architecture, status))
|
||||
return (python, architecture, status, trace)
|
||||
except Exception as msg:
|
||||
print("Error with {}, {}: {}".format(python, architecture, msg))
|
||||
return (python, architecture, -1, str(msg))
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
|
||||
os.chdir("..")
|
||||
matrix = [
|
||||
(python, architecture) for python in pythons for architecture in ("", X64_EXT)
|
||||
]
|
||||
|
||||
results = map(test_one, matrix)
|
||||
|
||||
for (python, architecture, status, trace) in results:
|
||||
print("{}{}: {}".format(python, architecture, status and "ERR" or "PASS"))
|
||||
|
||||
res = all(status for (python, architecture, status, trace) in results)
|
||||
sys.exit(res)
|
|
@ -1,11 +0,0 @@
|
|||
import sys
|
||||
import tarfile
|
||||
|
||||
|
||||
def untar(src, dest):
|
||||
with tarfile.open(src, "r:gz") as tgz:
|
||||
tgz.extractall(dest)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
untar(sys.argv[1], sys.argv[2])
|
|
@ -1,11 +0,0 @@
|
|||
import sys
|
||||
import zipfile
|
||||
|
||||
|
||||
def unzip(src, dest):
|
||||
with zipfile.ZipFile(src) as zf:
|
||||
zf.extractall(dest)
|
||||
|
||||
|
||||
if __name__ == "__main__":
|
||||
unzip(sys.argv[1], sys.argv[2])
|
Loading…
Reference in New Issue
Block a user