Skip to content

Commit 75f8dfa

Browse files
committed
Merge branch 'ps/rust-balloon'
Dip our toes a bit to (optionally) use Rust implemented helper called from our C code. * ps/rust-balloon: ci: enable Rust for breaking-changes jobs ci: convert "pedantic" job into full build with breaking changes BreakingChanges: announce Rust becoming mandatory varint: reimplement as test balloon for Rust varint: use explicit width for integers help: report on whether or not Rust is enabled Makefile: introduce infrastructure to build internal Rust library Makefile: reorder sources after includes meson: add infrastructure to build internal Rust library
2 parents 3aa0ced + e425c40 commit 75f8dfa

20 files changed

+410
-131
lines changed

.github/workflows/main.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -379,6 +379,8 @@ jobs:
379379
- jobname: linux-breaking-changes
380380
cc: gcc
381381
image: ubuntu:rolling
382+
- jobname: fedora-breaking-changes-meson
383+
image: fedora:latest
382384
- jobname: linux-leaks
383385
image: ubuntu:rolling
384386
cc: gcc
@@ -396,8 +398,6 @@ jobs:
396398
# Supported until 2025-04-02.
397399
- jobname: linux32
398400
image: i386/ubuntu:focal
399-
- jobname: pedantic
400-
image: fedora:latest
401401
# A RHEL 8 compatible distro. Supported until 2029-05-31.
402402
- jobname: almalinux-8
403403
image: almalinux:8

.gitignore

Lines changed: 2 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,4 +1,6 @@
11
/fuzz_corpora
2+
/target/
3+
/Cargo.lock
24
/GIT-BUILD-DIR
35
/GIT-BUILD-OPTIONS
46
/GIT-CFLAGS

.gitlab-ci.yml

Lines changed: 2 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -45,6 +45,8 @@ test:linux:
4545
- jobname: linux-breaking-changes
4646
image: ubuntu:20.04
4747
CC: gcc
48+
- jobname: fedora-breaking-changes-meson
49+
image: fedora:latest
4850
- jobname: linux-TEST-vars
4951
image: ubuntu:20.04
5052
CC: gcc
@@ -58,8 +60,6 @@ test:linux:
5860
- jobname: linux-asan-ubsan
5961
image: ubuntu:rolling
6062
CC: clang
61-
- jobname: pedantic
62-
image: fedora:latest
6363
- jobname: linux-musl-meson
6464
image: alpine:latest
6565
- jobname: linux32

Cargo.toml

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,9 @@
1+
[package]
2+
name = "gitcore"
3+
version = "0.1.0"
4+
edition = "2018"
5+
6+
[lib]
7+
crate-type = ["staticlib"]
8+
9+
[dependencies]

Documentation/BreakingChanges.adoc

Lines changed: 45 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -171,6 +171,51 @@ JGit, libgit2 and Gitoxide need to support it.
171171
matches the default branch name used in new repositories by many of the
172172
big Git forges.
173173

174+
* Git will require Rust as a mandatory part of the build process. While Git
175+
already started to adopt Rust in Git 2.49, all parts written in Rust are
176+
optional for the time being. This includes:
177+
+
178+
** The Rust wrapper around libgit.a that is part of "contrib/" and which has
179+
been introduced in Git 2.49.
180+
** Subsystems that have an alternative implementation in Rust to test
181+
interoperability between our C and Rust codebase.
182+
** Newly written features that are not mission critical for a fully functional
183+
Git client.
184+
+
185+
These changes are meant as test balloons to allow distributors of Git to prepare
186+
for Rust becoming a mandatory part of the build process. There will be multiple
187+
milestones for the introduction of Rust:
188+
+
189+
--
190+
1. Initially, with Git 2.52, support for Rust will be auto-detected by Meson and
191+
disabled in our Makefile so that the project can sort out the initial
192+
infrastructure.
193+
2. In Git 2.53, both build systems will default-enable support for Rust.
194+
Consequently, builds will break by default if Rust is not available on the
195+
build host. The use of Rust can still be explicitly disabled via build
196+
flags.
197+
3. In Git 3.0, the build options will be removed and support for Rust is
198+
mandatory.
199+
--
200+
+
201+
You can explicitly ask both Meson and our Makefile-based system to enable Rust
202+
by saying `meson configure -Drust=enabled` and `make WITH_RUST=YesPlease`,
203+
respectively.
204+
+
205+
The Git project will declare the last version before Git 3.0 to be a long-term
206+
support release. This long-term release will receive important bug fixes for at
207+
least four release cycles and security fixes for six release cycles. The Git
208+
project will hand over maintainership of the long-term release to distributors
209+
in case they need to extend the life of that long-term release even further.
210+
Details of how this long-term release will be handed over to the community will
211+
be discussed once the Git project decides to stop officially supporting it.
212+
+
213+
We will evaluate the impact on downstream distributions before making Rust
214+
mandatory in Git 3.0. If we see that the impact on downstream distributions
215+
would be significant, we may decide to defer this change to a subsequent minor
216+
release. This evaluation will also take into account our own experience with
217+
how painful it is to keep Rust an optional component.
218+
174219
=== Removals
175220

176221
* Support for grafting commits has long been superseded by git-replace(1).

Makefile

Lines changed: 127 additions & 87 deletions
Original file line numberDiff line numberDiff line change
@@ -483,6 +483,14 @@ include shared.mak
483483
# Define LIBPCREDIR=/foo/bar if your PCRE header and library files are
484484
# in /foo/bar/include and /foo/bar/lib directories.
485485
#
486+
# == Optional Rust support ==
487+
#
488+
# Define WITH_RUST if you want to include features and subsystems written in
489+
# Rust into Git. For now, Rust is still an optional feature of the build
490+
# process. With Git 3.0 though, Rust will always be enabled.
491+
#
492+
# Building Rust code requires Cargo.
493+
#
486494
# == SHA-1 and SHA-256 defines ==
487495
#
488496
# === SHA-1 backend ===
@@ -683,6 +691,7 @@ OBJECTS =
683691
OTHER_PROGRAMS =
684692
PROGRAM_OBJS =
685693
PROGRAMS =
694+
RUST_SOURCES =
686695
EXCLUDED_PROGRAMS =
687696
SCRIPT_PERL =
688697
SCRIPT_PYTHON =
@@ -920,6 +929,108 @@ TEST_SHELL_PATH = $(SHELL_PATH)
920929
LIB_FILE = libgit.a
921930
XDIFF_LIB = xdiff/lib.a
922931
REFTABLE_LIB = reftable/libreftable.a
932+
ifdef DEBUG
933+
RUST_LIB = target/debug/libgitcore.a
934+
else
935+
RUST_LIB = target/release/libgitcore.a
936+
endif
937+
938+
# xdiff and reftable libs may in turn depend on what is in libgit.a
939+
GITLIBS = common-main.o $(LIB_FILE) $(XDIFF_LIB) $(REFTABLE_LIB) $(LIB_FILE)
940+
EXTLIBS =
941+
942+
GIT_USER_AGENT = git/$(GIT_VERSION)
943+
944+
ifeq ($(wildcard sha1collisiondetection/lib/sha1.h),sha1collisiondetection/lib/sha1.h)
945+
DC_SHA1_SUBMODULE = auto
946+
endif
947+
948+
# Set CFLAGS, LDFLAGS and other *FLAGS variables. These might be
949+
# tweaked by config.* below as well as the command-line, both of
950+
# which'll override these defaults.
951+
# Older versions of GCC may require adding "-std=gnu99" at the end.
952+
CFLAGS = -g -O2 -Wall
953+
LDFLAGS =
954+
CC_LD_DYNPATH = -Wl,-rpath,
955+
BASIC_CFLAGS = -I.
956+
BASIC_LDFLAGS =
957+
958+
# library flags
959+
ARFLAGS = rcs
960+
PTHREAD_CFLAGS =
961+
962+
# Rust flags
963+
CARGO_ARGS =
964+
ifndef V
965+
CARGO_ARGS += --quiet
966+
endif
967+
ifndef DEBUG
968+
CARGO_ARGS += --release
969+
endif
970+
971+
# For the 'sparse' target
972+
SPARSE_FLAGS ?= -std=gnu99 -D__STDC_NO_VLA__
973+
SP_EXTRA_FLAGS =
974+
975+
# For informing GIT-BUILD-OPTIONS of the SANITIZE=leak,address targets
976+
SANITIZE_LEAK =
977+
SANITIZE_ADDRESS =
978+
979+
# For the 'coccicheck' target
980+
SPATCH_INCLUDE_FLAGS = --all-includes
981+
SPATCH_FLAGS =
982+
SPATCH_TEST_FLAGS =
983+
984+
# If *.o files are present, have "coccicheck" depend on them, with
985+
# COMPUTE_HEADER_DEPENDENCIES this will speed up the common-case of
986+
# only needing to re-generate coccicheck results for the users of a
987+
# given API if it's changed, and not all files in the project. If
988+
# COMPUTE_HEADER_DEPENDENCIES=no this will be unset too.
989+
SPATCH_USE_O_DEPENDENCIES = YesPlease
990+
991+
# Set SPATCH_CONCAT_COCCI to concatenate the contrib/cocci/*.cocci
992+
# files into a single contrib/cocci/ALL.cocci before running
993+
# "coccicheck".
994+
#
995+
# Pros:
996+
#
997+
# - Speeds up a one-shot run of "make coccicheck", as we won't have to
998+
# parse *.[ch] files N times for the N *.cocci rules
999+
#
1000+
# Cons:
1001+
#
1002+
# - Will make incremental development of *.cocci slower, as
1003+
# e.g. changing strbuf.cocci will re-run all *.cocci.
1004+
#
1005+
# - Makes error and performance analysis harder, as rules will be
1006+
# applied from a monolithic ALL.cocci, rather than
1007+
# e.g. strbuf.cocci. To work around this either undefine this, or
1008+
# generate a specific patch, e.g. this will always use strbuf.cocci,
1009+
# not ALL.cocci:
1010+
#
1011+
# make contrib/coccinelle/strbuf.cocci.patch
1012+
SPATCH_CONCAT_COCCI = YesPlease
1013+
1014+
# Rebuild 'coccicheck' if $(SPATCH), its flags etc. change
1015+
TRACK_SPATCH_DEFINES =
1016+
TRACK_SPATCH_DEFINES += $(SPATCH)
1017+
TRACK_SPATCH_DEFINES += $(SPATCH_INCLUDE_FLAGS)
1018+
TRACK_SPATCH_DEFINES += $(SPATCH_FLAGS)
1019+
TRACK_SPATCH_DEFINES += $(SPATCH_TEST_FLAGS)
1020+
GIT-SPATCH-DEFINES: FORCE
1021+
@FLAGS='$(TRACK_SPATCH_DEFINES)'; \
1022+
if test x"$$FLAGS" != x"`cat GIT-SPATCH-DEFINES 2>/dev/null`" ; then \
1023+
echo >&2 " * new spatch flags"; \
1024+
echo "$$FLAGS" >GIT-SPATCH-DEFINES; \
1025+
fi
1026+
1027+
include config.mak.uname
1028+
-include config.mak.autogen
1029+
-include config.mak
1030+
1031+
ifdef DEVELOPER
1032+
include config.mak.dev
1033+
endif
9231034

9241035
GENERATED_H += command-list.h
9251036
GENERATED_H += config-list.h
@@ -1198,7 +1309,9 @@ LIB_OBJS += urlmatch.o
11981309
LIB_OBJS += usage.o
11991310
LIB_OBJS += userdiff.o
12001311
LIB_OBJS += utf8.o
1312+
ifndef WITH_RUST
12011313
LIB_OBJS += varint.o
1314+
endif
12021315
LIB_OBJS += version.o
12031316
LIB_OBJS += versioncmp.o
12041317
LIB_OBJS += walker.o
@@ -1390,93 +1503,8 @@ CLAR_TEST_OBJS += $(UNIT_TEST_DIR)/unit-test.o
13901503

13911504
UNIT_TEST_OBJS += $(UNIT_TEST_DIR)/test-lib.o
13921505

1393-
# xdiff and reftable libs may in turn depend on what is in libgit.a
1394-
GITLIBS = common-main.o $(LIB_FILE) $(XDIFF_LIB) $(REFTABLE_LIB) $(LIB_FILE)
1395-
EXTLIBS =
1396-
1397-
GIT_USER_AGENT = git/$(GIT_VERSION)
1398-
1399-
ifeq ($(wildcard sha1collisiondetection/lib/sha1.h),sha1collisiondetection/lib/sha1.h)
1400-
DC_SHA1_SUBMODULE = auto
1401-
endif
1402-
1403-
# Set CFLAGS, LDFLAGS and other *FLAGS variables. These might be
1404-
# tweaked by config.* below as well as the command-line, both of
1405-
# which'll override these defaults.
1406-
# Older versions of GCC may require adding "-std=gnu99" at the end.
1407-
CFLAGS = -g -O2 -Wall
1408-
LDFLAGS =
1409-
CC_LD_DYNPATH = -Wl,-rpath,
1410-
BASIC_CFLAGS = -I.
1411-
BASIC_LDFLAGS =
1412-
1413-
# library flags
1414-
ARFLAGS = rcs
1415-
PTHREAD_CFLAGS =
1416-
1417-
# For the 'sparse' target
1418-
SPARSE_FLAGS ?= -std=gnu99 -D__STDC_NO_VLA__
1419-
SP_EXTRA_FLAGS =
1420-
1421-
# For informing GIT-BUILD-OPTIONS of the SANITIZE=leak,address targets
1422-
SANITIZE_LEAK =
1423-
SANITIZE_ADDRESS =
1424-
1425-
# For the 'coccicheck' target
1426-
SPATCH_INCLUDE_FLAGS = --all-includes
1427-
SPATCH_FLAGS =
1428-
SPATCH_TEST_FLAGS =
1429-
1430-
# If *.o files are present, have "coccicheck" depend on them, with
1431-
# COMPUTE_HEADER_DEPENDENCIES this will speed up the common-case of
1432-
# only needing to re-generate coccicheck results for the users of a
1433-
# given API if it's changed, and not all files in the project. If
1434-
# COMPUTE_HEADER_DEPENDENCIES=no this will be unset too.
1435-
SPATCH_USE_O_DEPENDENCIES = YesPlease
1436-
1437-
# Set SPATCH_CONCAT_COCCI to concatenate the contrib/cocci/*.cocci
1438-
# files into a single contrib/cocci/ALL.cocci before running
1439-
# "coccicheck".
1440-
#
1441-
# Pros:
1442-
#
1443-
# - Speeds up a one-shot run of "make coccicheck", as we won't have to
1444-
# parse *.[ch] files N times for the N *.cocci rules
1445-
#
1446-
# Cons:
1447-
#
1448-
# - Will make incremental development of *.cocci slower, as
1449-
# e.g. changing strbuf.cocci will re-run all *.cocci.
1450-
#
1451-
# - Makes error and performance analysis harder, as rules will be
1452-
# applied from a monolithic ALL.cocci, rather than
1453-
# e.g. strbuf.cocci. To work around this either undefine this, or
1454-
# generate a specific patch, e.g. this will always use strbuf.cocci,
1455-
# not ALL.cocci:
1456-
#
1457-
# make contrib/coccinelle/strbuf.cocci.patch
1458-
SPATCH_CONCAT_COCCI = YesPlease
1459-
1460-
# Rebuild 'coccicheck' if $(SPATCH), its flags etc. change
1461-
TRACK_SPATCH_DEFINES =
1462-
TRACK_SPATCH_DEFINES += $(SPATCH)
1463-
TRACK_SPATCH_DEFINES += $(SPATCH_INCLUDE_FLAGS)
1464-
TRACK_SPATCH_DEFINES += $(SPATCH_FLAGS)
1465-
TRACK_SPATCH_DEFINES += $(SPATCH_TEST_FLAGS)
1466-
GIT-SPATCH-DEFINES: FORCE
1467-
@FLAGS='$(TRACK_SPATCH_DEFINES)'; \
1468-
if test x"$$FLAGS" != x"`cat GIT-SPATCH-DEFINES 2>/dev/null`" ; then \
1469-
echo >&2 " * new spatch flags"; \
1470-
echo "$$FLAGS" >GIT-SPATCH-DEFINES; \
1471-
fi
1472-
1473-
include config.mak.uname
1474-
-include config.mak.autogen
1475-
-include config.mak
1476-
1477-
ifdef DEVELOPER
1478-
include config.mak.dev
1479-
endif
1506+
RUST_SOURCES += src/lib.rs
1507+
RUST_SOURCES += src/varint.rs
14801508

14811509
GIT-VERSION-FILE: FORCE
14821510
@OLD=$$(cat $@ 2>/dev/null || :) && \
@@ -1507,6 +1535,11 @@ endif
15071535
ALL_CFLAGS = $(DEVELOPER_CFLAGS) $(CPPFLAGS) $(CFLAGS) $(CFLAGS_APPEND)
15081536
ALL_LDFLAGS = $(LDFLAGS) $(LDFLAGS_APPEND)
15091537

1538+
ifdef WITH_RUST
1539+
BASIC_CFLAGS += -DWITH_RUST
1540+
GITLIBS += $(RUST_LIB)
1541+
endif
1542+
15101543
ifdef SANITIZE
15111544
SANITIZERS := $(foreach flag,$(subst $(comma),$(space),$(SANITIZE)),$(flag))
15121545
BASIC_CFLAGS += -fsanitize=$(SANITIZE) -fno-sanitize-recover=$(SANITIZE)
@@ -2921,6 +2954,12 @@ scalar$X: scalar.o GIT-LDFLAGS $(GITLIBS)
29212954
$(LIB_FILE): $(LIB_OBJS)
29222955
$(QUIET_AR)$(RM) $@ && $(AR) $(ARFLAGS) $@ $^
29232956

2957+
$(RUST_LIB): Cargo.toml $(RUST_SOURCES)
2958+
$(QUIET_CARGO)cargo build $(CARGO_ARGS)
2959+
2960+
.PHONY: rust
2961+
rust: $(RUST_LIB)
2962+
29242963
$(XDIFF_LIB): $(XDIFF_OBJS)
29252964
$(QUIET_AR)$(RM) $@ && $(AR) $(ARFLAGS) $@ $^
29262965

@@ -3771,6 +3810,7 @@ clean: profile-clean coverage-clean cocciclean
37713810
$(RM) $(FUZZ_PROGRAMS)
37723811
$(RM) $(SP_OBJ)
37733812
$(RM) $(HCC)
3813+
$(RM) -r Cargo.lock target/
37743814
$(RM) version-def.h
37753815
$(RM) -r $(dep_dirs) $(compdb_dir) compile_commands.json
37763816
$(RM) $(test_bindir_programs)

ci/install-dependencies.sh

Lines changed: 6 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -30,8 +30,12 @@ alpine-*)
3030
bash cvs gnupg perl-cgi perl-dbd-sqlite perl-io-tty >/dev/null
3131
;;
3232
fedora-*|almalinux-*)
33+
case "$jobname" in
34+
*-meson)
35+
MESON_DEPS="meson ninja";;
36+
esac
3337
dnf -yq update >/dev/null &&
34-
dnf -yq install shadow-utils sudo make gcc findutils diffutils perl python3 gawk gettext zlib-devel expat-devel openssl-devel curl-devel pcre2-devel >/dev/null
38+
dnf -yq install shadow-utils sudo make pkg-config gcc findutils diffutils perl python3 gawk gettext zlib-devel expat-devel openssl-devel curl-devel pcre2-devel $MESON_DEPS cargo >/dev/null
3539
;;
3640
ubuntu-*|i386/ubuntu-*|debian-*)
3741
# Required so that apt doesn't wait for user input on certain packages.
@@ -58,7 +62,7 @@ ubuntu-*|i386/ubuntu-*|debian-*)
5862
make libssl-dev libcurl4-openssl-dev libexpat-dev wget sudo default-jre \
5963
tcl tk gettext zlib1g-dev perl-modules liberror-perl libauthen-sasl-perl \
6064
libemail-valid-perl libio-pty-perl libio-socket-ssl-perl libnet-smtp-ssl-perl libdbd-sqlite3-perl libcgi-pm-perl \
61-
libsecret-1-dev libpcre2-dev meson ninja-build pkg-config \
65+
libsecret-1-dev libpcre2-dev meson ninja-build pkg-config cargo \
6266
${CC_PACKAGE:-${CC:-gcc}} $PYTHON_PACKAGE
6367

6468
case "$distro" in

0 commit comments

Comments
 (0)