Skip to content
Open
Show file tree
Hide file tree
Changes from all commits
Commits
File filter

Filter by extension

Filter by extension


Conversations
Failed to load comments.
Loading
Jump to
Jump to file
Failed to load files.
Loading
Diff view
Diff view
108 changes: 108 additions & 0 deletions .github/workflows/build_python_windows_arm64.yml
Original file line number Diff line number Diff line change
@@ -0,0 +1,108 @@
name: Build Windows ARM64 Python Wheels

on:
workflow_dispatch:

permissions:
contents: read

jobs:
build-sdist:
name: Build Python source distribution
runs-on: ubuntu-latest
steps:
- name: Checkout source
uses: actions/checkout@8e8c483db84b4bee98b60c0593521ed34d9990e8 # v6.0.1

- name: Set up Python
uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0
with:
python-version: "3.12"

- name: Set up Bazel
uses: bazel-contrib/setup-bazel@c5acdfb288317d0b5c0bbd7a396a3dc868bb0f86 # v0.19.0
with:
bazelisk-cache: true
repository-cache: true

- name: Build source distribution
run: |
bazel build //python/dist:source_wheel
mkdir dist
cp bazel-bin/python/dist/protobuf-*.tar.gz dist/

- name: Upload source distribution
uses: actions/upload-artifact@b7c566a772e6b6bfb58ed0dc250532a479d7789f # v6.0.0
with:
name: protobuf-sdist
path: dist/protobuf-*.tar.gz
if-no-files-found: error

build-wheels:
name: Build Windows ARM64 wheels
needs: build-sdist
runs-on: windows-11-arm
defaults:
run:
shell: pwsh
steps:
- name: Set up Python
uses: actions/setup-python@a309ff8b426b58ec0e2a45f0f869d46889d02405 # v6.2.0
with:
python-version: "3.12"
architecture: arm64

- name: Download source distribution
uses: actions/download-artifact@37930b1c2abaa49bbe596cd826c3c89aef350131 # v7.0.0
with:
name: protobuf-sdist
path: sdist

- name: Extract source distribution
run: |
$sdists = @(Get-ChildItem sdist -Filter protobuf-*.tar.gz -File)
if ($sdists.Count -ne 1) {
throw "Expected one source distribution, found $($sdists.Count)"
}

tar -xzf $sdists[0].FullName -C sdist
$sources = @(Get-ChildItem sdist -Filter protobuf-* -Directory)
if ($sources.Count -ne 1) {
throw "Expected one extracted source directory, found $($sources.Count)"
}

"PACKAGE_DIR=$($sources[0].FullName)" >> $env:GITHUB_ENV

- name: Install cibuildwheel
run: python -m pip install "cibuildwheel==4.1.0"

- name: Build and test wheels
env:
CIBW_ARCHS_WINDOWS: ARM64
CIBW_BUILD: "cp311-* cp312-* cp313-* cp314-*"
CIBW_BUILD_VERBOSITY: "1"
CIBW_TEST_COMMAND: >-
python -c "import platform;
from google._upb import _message;
assert platform.machine() == 'ARM64';
assert _message.__file__.endswith('.pyd')"
run: python -m cibuildwheel $env:PACKAGE_DIR --output-dir wheelhouse

- name: Validate wheel artifacts
run: |
$wheels = @(Get-ChildItem wheelhouse -Filter *.whl -File)
if ($wheels.Count -ne 4) {
throw "Expected four wheels, found $($wheels.Count)"
}

$invalidWheels = @($wheels | Where-Object Name -NotMatch '-win_arm64\.whl$')
if ($invalidWheels.Count -ne 0) {
throw "Unexpected wheel platform tags: $($invalidWheels.Name -join ', ')"
}

- name: Upload wheels
uses: actions/upload-artifact@b7c566a772e6b6bfb58ed0dc250532a479d7789f # v6.0.0
with:
name: protobuf-windows-arm64-wheels
path: wheelhouse/*.whl
if-no-files-found: error
2 changes: 0 additions & 2 deletions python/dist/BUILD.bazel
Original file line number Diff line number Diff line change
Expand Up @@ -304,8 +304,6 @@ pkg_files(
strip_prefix = strip_prefix.from_root(""),
)

# NOTE: This package currently only works for macos and ubuntu, MSVC users
# should use a binary wheel.
pkg_tar(
name = "source_tarball",
srcs = [
Expand Down
19 changes: 14 additions & 5 deletions python/dist/setup.py
Original file line number Diff line number Diff line change
Expand Up @@ -13,6 +13,7 @@
import sys

from setuptools import Extension, find_namespace_packages, setup
from setuptools.command.build_ext import build_ext


def GetVersion():
Expand All @@ -31,13 +32,21 @@ def GetVersion():
return file_globals['__version__']


class _BuildExt(build_ext):

def build_extensions(self):
if self.compiler.compiler_type == 'mingw32':
for extension in self.extensions:
extension.extra_link_args = (
extension.extra_link_args or []
) + ['-static']
super().build_extensions()


current_dir = os.path.dirname(os.path.abspath(__file__))
extra_link_args = []
extra_compile_args = []

if sys.platform.startswith('win'):
extra_link_args = ['-static']
else:
if not sys.platform.startswith('win'):
extra_compile_args = ['-fvisibility=hidden']

# If at some point the fasttable decoder is ready for prime time, we could
Expand Down Expand Up @@ -82,13 +91,13 @@ def GetVersion():
],
packages=find_namespace_packages(include=['google*']),
install_requires=[],
cmdclass={'build_ext': _BuildExt},
ext_modules=[
Extension(
'google._upb._message',
srcs,
include_dirs=[current_dir, os.path.join(current_dir, 'utf8_range')],
language='c',
extra_link_args=extra_link_args,
extra_compile_args=extra_compile_args,
)
],
Expand Down
5 changes: 4 additions & 1 deletion python/message.c
Original file line number Diff line number Diff line change
Expand Up @@ -1098,7 +1098,10 @@ bool PyUpb_Message_IsFrozen(PyObject* _self) {
* Attribute lookup must find both message fields and base class methods like
* msg.SerializeToString().
*/
__attribute__((flatten)) static PyObject* PyUpb_Message_GetAttr(
#if defined(__GNUC__) || defined(__clang__)
__attribute__((flatten))
#endif
static PyObject* PyUpb_Message_GetAttr(
PyObject* _self, PyObject* attr) {
PyUpb_Message* self = (void*)_self;

Expand Down
2 changes: 2 additions & 0 deletions python/protobuf.c
Original file line number Diff line number Diff line change
Expand Up @@ -42,6 +42,8 @@
typedef struct {
#ifdef ENABLE_MUTEX
pthread_mutex_t mutex;
#else
char unused;
#endif
} FreeThreadingMutex;

Expand Down
Loading