Initial project import

This commit is contained in:
Agila Forge Importer committed 2026-07-13 15:20:32 +00:00
commit 23f2d29e32
11957 files changed
+1754577

No files matched your search

+15
View File
@@ -0,0 +1,15 @@
.DS_Store
__MACOSX/
*.key
*.pem
*.p12
*.pfx
*.env
.env*
*.dylib
*.so
*.dll
*.exe
/tools/v/v
/build/
/dist/
+18
View File
@@ -0,0 +1,18 @@
# Installation Notes
## Font generator
```sh
python3 -m pip install Pillow
python3 tools/gen_font.py
```
Edit the output path in the script for the target open project before running it.
## V language
The V source is under `tools/v/`. Follow its bundled `README.md` and build instructions. No precompiled executable is included.
## crosstool-NG configuration
Install crosstool-NG separately, copy `tools/ct-ng-mingw/.config` into a dedicated build directory as `.config`, review all target paths, then run the normal crosstool-NG workflow.
+14
View File
@@ -0,0 +1,14 @@
# Open-Source Boundary
This repository is for reusable developer tools and third-party toolchain sources.
It must not contain:
- Agila kernel or boot internals
- Interrupt, memory-management, or scheduler implementation generators
- Proprietary AGX policy or optimization code
- Flying V proprietary compiler internals
- Private service protocols or system ABI implementations
- Signing keys, credentials, deployment tokens, or production configuration
Contributions should help developers create software for Agila or Agila Linux without providing enough implementation detail to reproduce Agila OS.
+35
View File
@@ -0,0 +1,35 @@
# Agila Open Tools
Public developer tools that can be used to build software for Agila and Agila Linux without exposing the proprietary Agila operating-system implementation.
## Included
- `tools/gen_font.py` — generates compact bitmap-font data from locally installed fonts.
- `tools/fv/fv` — lightweight Flying V command wrapper.
- `tools/ct-ng-mingw/.config` — cross-toolchain configuration starting point.
- `tools/v/` — third-party V language source distribution, with binaries and embedded Git history removed.
## Deliberately excluded
- Agila kernel interrupt/IDT generators.
- Kernel, scheduler, security, runtime, and hardware-policy implementation code.
- Precompiled V executables and platform-specific binaries.
- Bundled package-manager archives whose provenance/version could not be verified from this package alone.
- Credentials, deployment files, private keys, and internal repository metadata.
## Getting started
Run:
```sh
./bootstrap.sh
./verify.sh
```
The bootstrap script does not install system packages automatically. It reports the tools required for the selected components.
## Licensing
Each third-party component remains under its original license. See `THIRD_PARTY_NOTICES.md` and `licenses/`.
Agila names and logos are not granted for use as a competing operating-system identity.
+11
View File
@@ -0,0 +1,11 @@
# Security
Do not submit secrets, signing material, credentials, production addresses, or proprietary Agila source.
Before publishing a release, run:
```sh
./verify.sh
```
If sensitive material is published, remove it from repository history and rotate the affected credentials immediately.
+15
View File
@@ -0,0 +1,15 @@
# Third-Party Notices
## V language source
The source under `tools/v/` is redistributed under the license included in `licenses/V-LICENSE.txt` and in the upstream source directory.
The precompiled `v` executable and embedded `.git` repositories were removed from this public package.
## crosstool-NG configuration
`tools/ct-ng-mingw/.config` is configuration data intended for use with crosstool-NG. crosstool-NG itself is not bundled. Users must obtain it under its upstream terms.
## Local font inputs
`tools/gen_font.py` reads fonts installed on the user's system. Generated font data may be subject to the license of the selected font. Review that font's terms before redistribution.
+14
View File
@@ -0,0 +1,14 @@
#!/bin/sh
set -eu
printf '%s\n' 'Agila Open Tools bootstrap check'
command -v python3 >/dev/null 2>&1 && echo '[ok] python3' || echo '[missing] python3'
python3 - <<'PY' 2>/dev/null && echo '[ok] Pillow' || echo '[optional] Python Pillow is required by tools/gen_font.py'
import PIL
PY
command -v make >/dev/null 2>&1 && echo '[ok] make' || echo '[optional] make is required to build V'
command -v cc >/dev/null 2>&1 && echo '[ok] C compiler' || echo '[optional] a C compiler is required to build V'
command -v ct-ng >/dev/null 2>&1 && echo '[ok] crosstool-NG' || echo '[optional] ct-ng is required for the cross-toolchain config'
echo 'No packages were installed or system files changed.'
+21
View File
@@ -0,0 +1,21 @@
MIT License
Copyright (c) 2019-2024 Alexander Medvednikov
Permission is hereby granted, free of charge, to any person obtaining a copy
of this software and associated documentation files (the "Software"), to deal
in the Software without restriction, including without limitation the rights
to use, copy, modify, merge, publish, distribute, sublicense, and/or sell
copies of the Software, and to permit persons to whom the Software is
furnished to do so, subject to the following conditions:
The above copyright notice and this permission notice shall be included in all
copies or substantial portions of the Software.
THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR
IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY,
FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE
AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER
LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM,
OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE
SOFTWARE.
+801
View File
@@ -0,0 +1,801 @@
#
# Automatically generated file; DO NOT EDIT.
# crosstool-NG 1.28.0 Configuration
#
CT_CONFIGURE_has_cxx11=y
CT_CONFIGURE_has_lzip=y
CT_CONFIGURE_has_curl=y
CT_CONFIGURE_has_ninja=y
CT_CONFIGURE_has_make_3_81_or_newer=y
CT_CONFIGURE_has_make_4_0_or_newer=y
CT_CONFIGURE_has_make_4_4_or_newer=y
CT_CONFIGURE_has_libtool_2_4_or_newer=y
CT_CONFIGURE_has_libtoolize_2_4_or_newer=y
CT_CONFIGURE_has_autoconf_2_65_or_newer=y
CT_CONFIGURE_has_autoreconf_2_65_or_newer=y
CT_CONFIGURE_has_gnu_m4_1_4_12_or_newer=y
CT_CONFIGURE_has_python_3_4_or_newer=y
CT_CONFIGURE_has_bison_2_7_or_newer=y
CT_CONFIGURE_has_bison_3_0_4_or_newer=y
CT_CONFIGURE_has_python=y
CT_CONFIGURE_has_svn=y
CT_CONFIGURE_has_git=y
CT_CONFIGURE_has_md5sum=y
CT_CONFIGURE_has_sha1sum=y
CT_CONFIGURE_has_sha256sum=y
CT_CONFIGURE_has_sha512sum=y
CT_CONFIGURE_has_install_with_strip_program=y
CT_VERSION="1.28.0"
CT_VCHECK="load"
CT_CONFIG_VERSION_ENV="4"
CT_CONFIG_VERSION_CURRENT="4"
CT_CONFIG_VERSION="4"
CT_MODULES=y
#
# Paths and misc options
#
#
# crosstool-NG behavior
#
# CT_OBSOLETE is not set
CT_EXPERIMENTAL=y
# CT_ALLOW_BUILD_AS_ROOT is not set
# CT_ENABLE_EXPERIMENTAL_BUNDLED_PATCHES is not set
# CT_DEBUG_CT is not set
#
# Paths
#
CT_LOCAL_TARBALLS_DIR="${HOME}/src"
CT_SAVE_TARBALLS=y
# CT_TARBALLS_BUILDROOT_LAYOUT is not set
CT_WORK_DIR="${CT_TOP_DIR}/.build"
CT_BUILD_TOP_DIR="${CT_WORK_DIR:-${CT_TOP_DIR}/.build}/${CT_HOST:+HOST-${CT_HOST}/}${CT_TARGET}"
CT_BUILD_DIR="${CT_BUILD_TOP_DIR}/build"
CT_PREFIX_DIR="${CT_PREFIX:-${HOME}/x-tools}/${CT_HOST:+HOST-${CT_HOST}/}${CT_TARGET}"
CT_RM_RF_PREFIX_DIR=y
CT_REMOVE_DOCS=y
CT_INSTALL_LICENSES=y
CT_PREFIX_DIR_RO=y
CT_STRIP_HOST_TOOLCHAIN_EXECUTABLES=y
# CT_STRIP_TARGET_TOOLCHAIN_EXECUTABLES is not set
# CT_TARBALL_RESULT is not set
#
# Downloading
#
CT_DOWNLOAD_AGENT_CURL=y
# CT_DOWNLOAD_AGENT_NONE is not set
# CT_FORBID_DOWNLOAD is not set
# CT_FORCE_DOWNLOAD is not set
CT_CONNECT_TIMEOUT=10
CT_DOWNLOAD_CURL_OPTIONS="--location --ftp-pasv --retry 3 --fail --silent"
# CT_ONLY_DOWNLOAD is not set
# CT_USE_MIRROR is not set
CT_VERIFY_DOWNLOAD_DIGEST=y
CT_VERIFY_DOWNLOAD_DIGEST_SHA512=y
# CT_VERIFY_DOWNLOAD_DIGEST_SHA256 is not set
# CT_VERIFY_DOWNLOAD_DIGEST_SHA1 is not set
# CT_VERIFY_DOWNLOAD_DIGEST_MD5 is not set
CT_VERIFY_DOWNLOAD_DIGEST_ALG="sha512"
# CT_VERIFY_DOWNLOAD_SIGNATURE is not set
#
# Extracting
#
# CT_FORCE_EXTRACT is not set
CT_OVERRIDE_CONFIG_GUESS_SUB=y
# CT_ONLY_EXTRACT is not set
CT_PATCH_BUNDLED=y
# CT_PATCH_LOCAL is not set
# CT_PATCH_BUNDLED_LOCAL is not set
# CT_PATCH_LOCAL_BUNDLED is not set
# CT_PATCH_NONE is not set
CT_PATCH_ORDER="bundled"
#
# Build behavior
#
CT_PARALLEL_JOBS=0
CT_LOAD=""
CT_USE_PIPES=y
CT_EXTRA_CFLAGS_FOR_BUILD=""
CT_EXTRA_CXXFLAGS_FOR_BUILD=""
CT_EXTRA_LDFLAGS_FOR_BUILD=""
CT_EXTRA_CFLAGS_FOR_HOST=""
CT_EXTRA_LDFLAGS_FOR_HOST=""
# CT_CONFIG_SHELL_SH is not set
# CT_CONFIG_SHELL_ASH is not set
CT_CONFIG_SHELL_BASH=y
# CT_CONFIG_SHELL_CUSTOM is not set
CT_CONFIG_SHELL="${bash}"
#
# Logging
#
# CT_LOG_ERROR is not set
# CT_LOG_WARN is not set
# CT_LOG_INFO is not set
CT_LOG_EXTRA=y
# CT_LOG_ALL is not set
# CT_LOG_DEBUG is not set
CT_LOG_LEVEL_MAX="EXTRA"
# CT_LOG_SEE_TOOLS_WARN is not set
CT_LOG_PROGRESS_BAR=y
CT_LOG_TO_FILE=y
CT_LOG_FILE_COMPRESS=y
# end of Paths and misc options
#
# Target options
#
# CT_ARCH_ALPHA is not set
# CT_ARCH_ARC is not set
# CT_ARCH_ARM is not set
# CT_ARCH_AVR is not set
# CT_ARCH_BPF is not set
# CT_ARCH_C6X is not set
# CT_ARCH_LM32 is not set
# CT_ARCH_LOONGARCH is not set
# CT_ARCH_M68K is not set
# CT_ARCH_MICROBLAZE is not set
# CT_ARCH_MIPS is not set
# CT_ARCH_MOXIE is not set
# CT_ARCH_MSP430 is not set
# CT_ARCH_NIOS2 is not set
# CT_ARCH_OPENRISC is not set
# CT_ARCH_PARISC is not set
# CT_ARCH_POWERPC is not set
# CT_ARCH_PRU is not set
# CT_ARCH_RISCV is not set
# CT_ARCH_RX is not set
# CT_ARCH_S390 is not set
# CT_ARCH_SH is not set
# CT_ARCH_SPARC is not set
# CT_ARCH_TRICORE is not set
CT_ARCH_X86=y
# CT_ARCH_XTENSA is not set
CT_ARCH="x86"
CT_ARCH_CHOICE_KSYM="X86"
CT_ARCH_CPU=""
CT_ARCH_TUNE=""
CT_ARCH_X86_SHOW=y
#
# Options for x86
#
CT_ARCH_X86_PKG_KSYM=""
CT_ALL_ARCH_CHOICES="ALPHA ARC ARM AVR BPF C6X LM32 LOONGARCH M68K MICROBLAZE MIPS MOXIE MSP430 NIOS2 OPENRISC PARISC POWERPC PRU RISCV RX S390 SH SPARC TRICORE X86 XTENSA"
CT_ARCH_SUFFIX=""
# CT_OMIT_TARGET_VENDOR is not set
#
# Generic target options
#
CT_MULTILIB=y
# CT_DEMULTILIB is not set
CT_ARCH_USE_MMU=y
CT_ARCH_SUPPORTS_LIBSANITIZER=y
CT_ARCH_SUPPORTS_32=y
CT_ARCH_SUPPORTS_64=y
CT_ARCH_DEFAULT_32=y
CT_ARCH_BITNESS=64
# CT_ARCH_32 is not set
CT_ARCH_64=y
CT_ARCH_SUPPORTS_WITH_32_64=y
#
# Target optimisations
#
CT_ARCH_SUPPORTS_WITH_ARCH=y
CT_ARCH_SUPPORTS_WITH_CPU=y
CT_ARCH_SUPPORTS_WITH_TUNE=y
CT_ARCH_ARCH=""
CT_TARGET_CFLAGS=""
CT_TARGET_LDFLAGS=""
# end of Target options
#
# Toolchain options
#
#
# General toolchain options
#
CT_FORCE_SYSROOT=y
CT_USE_SYSROOT=y
CT_SYSROOT_NAME="sysroot"
CT_SYSROOT_DIR_PREFIX=""
CT_SHOW_CT_VERSION=y
CT_TOOLCHAIN_PKGVERSION=""
CT_TOOLCHAIN_BUGURL=""
#
# Tuple completion and aliasing
#
CT_TARGET_VENDOR="w64"
CT_TARGET_ALIAS_SED_EXPR=""
CT_TARGET_ALIAS=""
#
# Toolchain type
#
# CT_NATIVE is not set
CT_CROSS=y
# CT_CROSS_NATIVE is not set
# CT_CANADIAN is not set
CT_TOOLCHAIN_TYPE="cross"
#
# Build system
#
CT_BUILD=""
CT_BUILD_PREFIX=""
CT_BUILD_SUFFIX=""
#
# Misc options
#
# CT_TOOLCHAIN_ENABLE_NLS is not set
CT_TOOLCHAIN_CMAKE_TOOLCHAIN_FILE=y
# end of Toolchain options
#
# Operating System
#
CT_WINDOWS=y
CT_KERNEL_SUPPORTS_SHARED_LIBS=y
# CT_KERNEL_BARE_METAL is not set
# CT_KERNEL_LINUX is not set
CT_KERNEL_WINDOWS=y
CT_KERNEL="windows"
CT_KERNEL_CHOICE_KSYM="WINDOWS"
CT_KERNEL_WINDOWS_SHOW=y
#
# Options for windows
#
CT_KERNEL_WINDOWS_PKG_KSYM=""
CT_ALL_KERNEL_CHOICES="BARE_METAL LINUX WINDOWS"
#
# Common kernel options
#
CT_SHARED_LIBS=y
# end of Operating System
#
# Binary utilities
#
CT_ARCH_BINFMT_ELF=y
CT_BINUTILS_BINUTILS=y
CT_BINUTILS="binutils"
CT_BINUTILS_CHOICE_KSYM="BINUTILS"
CT_BINUTILS_BINUTILS_SHOW=y
#
# Options for binutils
#
CT_BINUTILS_BINUTILS_PKG_KSYM="BINUTILS"
CT_BINUTILS_DIR_NAME="binutils"
CT_BINUTILS_USE_GNU=y
# CT_BINUTILS_USE_LINARO is not set
# CT_BINUTILS_USE_ORACLE is not set
CT_BINUTILS_USE="BINUTILS"
CT_BINUTILS_PKG_NAME="binutils"
CT_BINUTILS_SRC_RELEASE=y
# CT_BINUTILS_SRC_DEVEL is not set
# CT_BINUTILS_SRC_CUSTOM is not set
CT_BINUTILS_PATCH_GLOBAL=y
# CT_BINUTILS_PATCH_BUNDLED is not set
# CT_BINUTILS_PATCH_LOCAL is not set
# CT_BINUTILS_PATCH_BUNDLED_LOCAL is not set
# CT_BINUTILS_PATCH_LOCAL_BUNDLED is not set
# CT_BINUTILS_PATCH_NONE is not set
CT_BINUTILS_PATCH_ORDER="global"
CT_BINUTILS_V_2_45=y
# CT_BINUTILS_V_2_44 is not set
# CT_BINUTILS_V_2_43 is not set
# CT_BINUTILS_V_2_42 is not set
# CT_BINUTILS_V_2_41 is not set
# CT_BINUTILS_V_2_40 is not set
# CT_BINUTILS_V_2_39 is not set
# CT_BINUTILS_V_2_38 is not set
# CT_BINUTILS_V_2_37 is not set
# CT_BINUTILS_V_2_36 is not set
# CT_BINUTILS_V_2_35 is not set
# CT_BINUTILS_V_2_34 is not set
# CT_BINUTILS_V_2_33 is not set
# CT_BINUTILS_V_2_32 is not set
# CT_BINUTILS_V_2_31 is not set
# CT_BINUTILS_V_2_30 is not set
# CT_BINUTILS_V_2_29 is not set
# CT_BINUTILS_V_2_28 is not set
# CT_BINUTILS_V_2_27 is not set
# CT_BINUTILS_V_2_26 is not set
CT_BINUTILS_VERSION="2.45"
CT_BINUTILS_MIRRORS="$(CT_Mirrors GNU binutils) $(CT_Mirrors sourceware binutils/releases)"
CT_BINUTILS_ARCHIVE_FILENAME="@{pkg_name}-@{version}"
CT_BINUTILS_ARCHIVE_DIRNAME="@{pkg_name}-@{version}"
CT_BINUTILS_ARCHIVE_FORMATS=".tar.xz .tar.bz2 .tar.gz"
CT_BINUTILS_SIGNATURE_FORMAT="packed/.sig"
CT_BINUTILS_2_45_or_later=y
CT_BINUTILS_2_45_or_older=y
CT_BINUTILS_later_than_2_44=y
CT_BINUTILS_2_44_or_later=y
CT_BINUTILS_later_than_2_41=y
CT_BINUTILS_2_41_or_later=y
CT_BINUTILS_later_than_2_39=y
CT_BINUTILS_2_39_or_later=y
CT_BINUTILS_later_than_2_30=y
CT_BINUTILS_2_30_or_later=y
CT_BINUTILS_later_than_2_27=y
CT_BINUTILS_2_27_or_later=y
CT_BINUTILS_later_than_2_26=y
CT_BINUTILS_2_26_or_later=y
#
# GNU binutils
#
CT_BINUTILS_GOLD_SUPPORTS_ARCH=y
CT_BINUTILS_FORCE_LD_BFD_DEFAULT=y
CT_BINUTILS_LINKER_LD=y
CT_BINUTILS_LINKERS_LIST="ld"
CT_BINUTILS_LINKER_DEFAULT="bfd"
CT_BINUTILS_PLUGINS=y
CT_BINUTILS_RELRO=m
CT_BINUTILS_DETERMINISTIC_ARCHIVES=y
CT_BINUTILS_EXTRA_CONFIG_ARRAY=""
# CT_BINUTILS_FOR_TARGET is not set
# CT_BINUTILS_GPROFNG is not set
CT_ALL_BINUTILS_CHOICES="BINUTILS"
# end of Binary utilities
#
# C-library
#
CT_LIBC_MINGW_W64=y
CT_LIBC="mingw-w64"
CT_LIBC_CHOICE_KSYM="MINGW_W64"
CT_THREADS="posix"
CT_LIBC_MINGW_W64_SHOW=y
#
# Options for mingw-w64
#
CT_LIBC_MINGW_W64_PKG_KSYM="MINGW_W64"
CT_MINGW_W64_DIR_NAME="mingw-w64"
CT_MINGW_W64_PKG_NAME="mingw-w64"
CT_MINGW_W64_SRC_RELEASE=y
# CT_MINGW_W64_SRC_DEVEL is not set
# CT_MINGW_W64_SRC_CUSTOM is not set
CT_MINGW_W64_PATCH_GLOBAL=y
# CT_MINGW_W64_PATCH_BUNDLED is not set
# CT_MINGW_W64_PATCH_LOCAL is not set
# CT_MINGW_W64_PATCH_BUNDLED_LOCAL is not set
# CT_MINGW_W64_PATCH_LOCAL_BUNDLED is not set
# CT_MINGW_W64_PATCH_NONE is not set
CT_MINGW_W64_PATCH_ORDER="global"
CT_MINGW_W64_V_V13_0=y
# CT_MINGW_W64_V_V12_0 is not set
# CT_MINGW_W64_V_V11_0 is not set
# CT_MINGW_W64_V_V10_0 is not set
# CT_MINGW_W64_V_V9_0 is not set
# CT_MINGW_W64_V_V8_0 is not set
# CT_MINGW_W64_V_V7_0 is not set
# CT_MINGW_W64_V_V6_0 is not set
# CT_MINGW_W64_V_V5_0 is not set
# CT_MINGW_W64_V_V4_0 is not set
CT_MINGW_W64_VERSION="v13.0.0"
CT_MINGW_W64_MIRRORS="http://downloads.sourceforge.net/sourceforge/mingw-w64 https://downloads.sourceforge.net/project/mingw-w64/mingw-w64/mingw-w64-release/"
CT_MINGW_W64_ARCHIVE_FILENAME="@{pkg_name}-@{version}"
CT_MINGW_W64_ARCHIVE_DIRNAME="@{pkg_name}-@{version}"
CT_MINGW_W64_ARCHIVE_FORMATS=".tar.bz2 .zip"
CT_MINGW_W64_SIGNATURE_FORMAT="packed/.sig"
CT_MINGW_SECURE_API=y
CT_MINGW_DEFAULT_MSVCRT_DEFAULT=y
# CT_MINGW_DEFAULT_MSVCRT_MSVCRT is not set
# CT_MINGW_DEFAULT_MSVCRT_UCRT is not set
# CT_MINGW_DEFAULT_MSVCRT_CUSTOM is not set
CT_MINGW_DIRECTX=y
CT_MINGW_DDK=y
CT_MINGW_TOOLS=y
CT_MINGW_TOOL_LIST_ARRAY="gendef genidl genlib genpeimg widl"
CT_ALL_LIBC_CHOICES="AVR_LIBC GLIBC MINGW_W64 MOXIEBOX MUSL NEWLIB NONE PICOLIBC UCLIBC_NG"
CT_LIBC_SUPPORT_THREADS_ANY=y
CT_LIBC_SUPPORT_THREADS_NATIVE=y
CT_LIBC_SUPPORT_THREADS_POSIX=y
#
# Common C library options
#
# CT_THREADS_NATIVE is not set
CT_THREADS_POSIX=y
CT_CREATE_LDSO_CONF=y
CT_LDSO_CONF_EXTRA_DIRS_ARRAY=""
CT_LIBC_XLDD=y
# end of C-library
#
# C compiler
#
CT_CC_CORE_NEEDED=y
CT_CC_SUPPORT_CXX=y
CT_CC_SUPPORT_FORTRAN=y
CT_CC_SUPPORT_ADA=y
CT_CC_SUPPORT_D=y
CT_CC_SUPPORT_JIT=y
CT_CC_SUPPORT_OBJC=y
CT_CC_SUPPORT_OBJCXX=y
CT_CC_SUPPORT_GOLANG=y
CT_CC_GCC=y
CT_CC="gcc"
CT_CC_CHOICE_KSYM="GCC"
CT_CC_GCC_SHOW=y
#
# Options for gcc
#
CT_CC_GCC_PKG_KSYM="GCC"
CT_GCC_DIR_NAME="gcc"
CT_GCC_USE_GNU=y
# CT_GCC_USE_LINARO is not set
# CT_GCC_USE_ORACLE is not set
CT_GCC_USE="GCC"
CT_GCC_PKG_NAME="gcc"
CT_GCC_SRC_RELEASE=y
# CT_GCC_SRC_DEVEL is not set
# CT_GCC_SRC_CUSTOM is not set
CT_GCC_PATCH_GLOBAL=y
# CT_GCC_PATCH_BUNDLED is not set
# CT_GCC_PATCH_LOCAL is not set
# CT_GCC_PATCH_BUNDLED_LOCAL is not set
# CT_GCC_PATCH_LOCAL_BUNDLED is not set
# CT_GCC_PATCH_NONE is not set
CT_GCC_PATCH_ORDER="global"
CT_GCC_V_15=y
# CT_GCC_V_14 is not set
# CT_GCC_V_13 is not set
# CT_GCC_V_12 is not set
# CT_GCC_V_11 is not set
# CT_GCC_V_10 is not set
# CT_GCC_V_9 is not set
# CT_GCC_V_8 is not set
# CT_GCC_V_7 is not set
# CT_GCC_V_6 is not set
# CT_GCC_V_5 is not set
# CT_GCC_V_4_9 is not set
CT_GCC_VERSION="15.2.0"
CT_GCC_MIRRORS="$(CT_Mirrors GNU gcc/gcc-${CT_GCC_VERSION}) $(CT_Mirrors sourceware gcc/releases/gcc-${CT_GCC_VERSION})"
CT_GCC_ARCHIVE_FILENAME="@{pkg_name}-@{version}"
CT_GCC_ARCHIVE_DIRNAME="@{pkg_name}-@{version}"
CT_GCC_ARCHIVE_FORMATS=".tar.xz .tar.gz"
CT_GCC_SIGNATURE_FORMAT=""
CT_GCC_later_than_15=y
CT_GCC_15_or_later=y
CT_GCC_later_than_14=y
CT_GCC_14_or_later=y
CT_GCC_later_than_13=y
CT_GCC_13_or_later=y
CT_GCC_later_than_12=y
CT_GCC_12_or_later=y
CT_GCC_later_than_11=y
CT_GCC_11_or_later=y
CT_GCC_later_than_10=y
CT_GCC_10_or_later=y
CT_GCC_later_than_9=y
CT_GCC_9_or_later=y
CT_GCC_later_than_8=y
CT_GCC_8_or_later=y
CT_GCC_later_than_7=y
CT_GCC_7_or_later=y
CT_GCC_later_than_6=y
CT_GCC_6_or_later=y
CT_GCC_later_than_5=y
CT_GCC_5_or_later=y
CT_GCC_later_than_4_9=y
CT_GCC_4_9_or_later=y
CT_CC_GCC_ENABLE_PLUGINS=y
CT_CC_GCC_HAS_LIBMPX=y
CT_CC_GCC_ENABLE_CXX_FLAGS=""
CT_CC_GCC_CORE_EXTRA_CONFIG_ARRAY=""
CT_CC_GCC_EXTRA_CONFIG_ARRAY=""
CT_CC_GCC_MULTILIB_LIST=""
# CT_CC_GCC_SYSTEM_ZLIB is not set
CT_CC_GCC_CONFIG_TLS=m
#
# Optimisation features
#
CT_CC_GCC_USE_GRAPHITE=y
CT_CC_GCC_USE_LTO=y
CT_CC_GCC_LTO_ZSTD=m
#
# Settings for libraries running on target
#
CT_CC_GCC_ENABLE_TARGET_OPTSPACE=y
CT_CC_GCC_LIBSTDCXX=m
# CT_CC_GCC_LIBSTDCXX_HOSTED_DISABLE is not set
CT_CC_GCC_LIBSTDCXX_TARGET_CXXFLAGS=""
# CT_CC_GCC_LIBMUDFLAP is not set
# CT_CC_GCC_LIBGOMP is not set
# CT_CC_GCC_LIBSSP is not set
# CT_CC_GCC_LIBQUADMATH is not set
CT_CC_GCC_LIBSTDCXX_VERBOSE=m
#
# Misc. obscure options.
#
CT_CC_CXA_ATEXIT=y
CT_CC_GCC_TM_CLONE_REGISTRY=m
# CT_CC_GCC_DISABLE_PCH is not set
CT_CC_GCC_SJLJ_EXCEPTIONS=m
CT_CC_GCC_LDBL_128=m
# CT_CC_GCC_BUILD_ID is not set
CT_CC_GCC_LNK_HASH_STYLE_DEFAULT=y
# CT_CC_GCC_LNK_HASH_STYLE_SYSV is not set
# CT_CC_GCC_LNK_HASH_STYLE_GNU is not set
# CT_CC_GCC_LNK_HASH_STYLE_BOTH is not set
CT_CC_GCC_LNK_HASH_STYLE=""
CT_CC_GCC_DEC_FLOATS_AUTO=y
# CT_CC_GCC_DEC_FLOATS_BID is not set
# CT_CC_GCC_DEC_FLOATS_DPD is not set
# CT_CC_GCC_DEC_FLOATS_NO is not set
CT_CC_GCC_DEC_FLOATS=""
CT_ALL_CC_CHOICES="GCC"
#
# Additional supported languages:
#
CT_CC_LANG_CXX=y
CT_CC_LANG_FORTRAN=y
# CT_CC_LANG_JIT is not set
# CT_CC_LANG_ADA is not set
# CT_CC_LANG_D is not set
# CT_CC_LANG_OBJC is not set
# CT_CC_LANG_OBJCXX is not set
# CT_CC_LANG_GOLANG is not set
CT_CC_LANG_OTHERS=""
# end of C compiler
#
# Linkers
#
#
# BFD enabled in binutils
#
# CT_LINKER_MOLD is not set
CT_ALL_LINKER_CHOICES="MOLD"
# end of Linkers
#
# Debug facilities
#
# CT_DEBUG_DUMA is not set
# CT_DEBUG_GDB is not set
# CT_DEBUG_LTRACE is not set
# CT_DEBUG_STRACE is not set
CT_ALL_DEBUG_CHOICES="DUMA GDB LTRACE STRACE"
# end of Debug facilities
#
# Companion libraries
#
# CT_COMPLIBS_CHECK is not set
# CT_COMP_LIBS_CLOOG is not set
# CT_COMP_LIBS_EXPAT is not set
# CT_COMP_LIBS_GETTEXT is not set
CT_COMP_LIBS_GMP=y
CT_COMP_LIBS_GMP_PKG_KSYM="GMP"
CT_GMP_DIR_NAME="gmp"
CT_GMP_PKG_NAME="gmp"
CT_GMP_SRC_RELEASE=y
# CT_GMP_SRC_DEVEL is not set
# CT_GMP_SRC_CUSTOM is not set
CT_GMP_PATCH_GLOBAL=y
# CT_GMP_PATCH_BUNDLED is not set
# CT_GMP_PATCH_LOCAL is not set
# CT_GMP_PATCH_BUNDLED_LOCAL is not set
# CT_GMP_PATCH_LOCAL_BUNDLED is not set
# CT_GMP_PATCH_NONE is not set
CT_GMP_PATCH_ORDER="global"
CT_GMP_V_6_3=y
# CT_GMP_V_6_2 is not set
# CT_GMP_V_6_1 is not set
CT_GMP_VERSION="6.3.0"
CT_GMP_MIRRORS="https://gmplib.org/download/gmp https://gmplib.org/download/gmp/archive $(CT_Mirrors GNU gmp)"
CT_GMP_ARCHIVE_FILENAME="@{pkg_name}-@{version}"
CT_GMP_ARCHIVE_DIRNAME="@{pkg_name}-@{version}"
CT_GMP_ARCHIVE_FORMATS=".tar.xz .tar.lz .tar.bz2"
CT_GMP_SIGNATURE_FORMAT="packed/.sig"
CT_GMP_EXTRA_CFLAGS="-std=gnu17"
CT_COMP_LIBS_ISL=y
CT_COMP_LIBS_ISL_PKG_KSYM="ISL"
CT_ISL_DIR_NAME="isl"
CT_ISL_PKG_NAME="isl"
CT_ISL_SRC_RELEASE=y
# CT_ISL_SRC_DEVEL is not set
# CT_ISL_SRC_CUSTOM is not set
CT_ISL_PATCH_GLOBAL=y
# CT_ISL_PATCH_BUNDLED is not set
# CT_ISL_PATCH_LOCAL is not set
# CT_ISL_PATCH_BUNDLED_LOCAL is not set
# CT_ISL_PATCH_LOCAL_BUNDLED is not set
# CT_ISL_PATCH_NONE is not set
CT_ISL_PATCH_ORDER="global"
CT_ISL_V_0_27=y
# CT_ISL_V_0_26 is not set
# CT_ISL_V_0_25 is not set
# CT_ISL_V_0_24 is not set
# CT_ISL_V_0_23 is not set
# CT_ISL_V_0_22 is not set
# CT_ISL_V_0_21 is not set
# CT_ISL_V_0_20 is not set
# CT_ISL_V_0_19 is not set
# CT_ISL_V_0_18 is not set
# CT_ISL_V_0_17 is not set
# CT_ISL_V_0_16 is not set
# CT_ISL_V_0_15 is not set
CT_ISL_VERSION="0.27"
CT_ISL_MIRRORS="https://libisl.sourceforge.io"
CT_ISL_ARCHIVE_FILENAME="@{pkg_name}-@{version}"
CT_ISL_ARCHIVE_DIRNAME="@{pkg_name}-@{version}"
CT_ISL_ARCHIVE_FORMATS=".tar.xz .tar.bz2 .tar.gz"
CT_ISL_SIGNATURE_FORMAT=""
CT_ISL_later_than_0_18=y
CT_ISL_0_18_or_later=y
CT_ISL_later_than_0_15=y
CT_ISL_0_15_or_later=y
# CT_COMP_LIBS_LIBELF is not set
# CT_COMP_LIBS_LIBICONV is not set
CT_COMP_LIBS_MPC=y
CT_COMP_LIBS_MPC_PKG_KSYM="MPC"
CT_MPC_DIR_NAME="mpc"
CT_MPC_PKG_NAME="mpc"
CT_MPC_SRC_RELEASE=y
# CT_MPC_SRC_DEVEL is not set
# CT_MPC_SRC_CUSTOM is not set
CT_MPC_PATCH_GLOBAL=y
# CT_MPC_PATCH_BUNDLED is not set
# CT_MPC_PATCH_LOCAL is not set
# CT_MPC_PATCH_BUNDLED_LOCAL is not set
# CT_MPC_PATCH_LOCAL_BUNDLED is not set
# CT_MPC_PATCH_NONE is not set
CT_MPC_PATCH_ORDER="global"
CT_MPC_V_1_3=y
CT_MPC_VERSION="1.3.1"
CT_MPC_MIRRORS="https://www.multiprecision.org/downloads $(CT_Mirrors GNU mpc)"
CT_MPC_ARCHIVE_FILENAME="@{pkg_name}-@{version}"
CT_MPC_ARCHIVE_DIRNAME="@{pkg_name}-@{version}"
CT_MPC_ARCHIVE_FORMATS=".tar.gz"
CT_MPC_SIGNATURE_FORMAT="packed/.sig"
CT_COMP_LIBS_MPFR=y
CT_COMP_LIBS_MPFR_PKG_KSYM="MPFR"
CT_MPFR_DIR_NAME="mpfr"
CT_MPFR_PKG_NAME="mpfr"
CT_MPFR_SRC_RELEASE=y
# CT_MPFR_SRC_DEVEL is not set
# CT_MPFR_SRC_CUSTOM is not set
CT_MPFR_PATCH_GLOBAL=y
# CT_MPFR_PATCH_BUNDLED is not set
# CT_MPFR_PATCH_LOCAL is not set
# CT_MPFR_PATCH_BUNDLED_LOCAL is not set
# CT_MPFR_PATCH_LOCAL_BUNDLED is not set
# CT_MPFR_PATCH_NONE is not set
CT_MPFR_PATCH_ORDER="global"
CT_MPFR_V_4_2=y
CT_MPFR_VERSION="4.2.2"
CT_MPFR_MIRRORS="https://www.mpfr.org/mpfr-${CT_MPFR_VERSION} $(CT_Mirrors GNU mpfr)"
CT_MPFR_ARCHIVE_FILENAME="@{pkg_name}-@{version}"
CT_MPFR_ARCHIVE_DIRNAME="@{pkg_name}-@{version}"
CT_MPFR_ARCHIVE_FORMATS=".tar.xz .tar.bz2 .tar.gz .zip"
CT_MPFR_SIGNATURE_FORMAT="packed/.asc"
# CT_COMP_LIBS_NCURSES is not set
CT_COMP_LIBS_ZLIB=y
CT_COMP_LIBS_ZLIB_PKG_KSYM="ZLIB"
CT_ZLIB_DIR_NAME="zlib"
CT_ZLIB_PKG_NAME="zlib"
CT_ZLIB_SRC_RELEASE=y
# CT_ZLIB_SRC_DEVEL is not set
# CT_ZLIB_SRC_CUSTOM is not set
CT_ZLIB_PATCH_GLOBAL=y
# CT_ZLIB_PATCH_BUNDLED is not set
# CT_ZLIB_PATCH_LOCAL is not set
# CT_ZLIB_PATCH_BUNDLED_LOCAL is not set
# CT_ZLIB_PATCH_LOCAL_BUNDLED is not set
# CT_ZLIB_PATCH_NONE is not set
CT_ZLIB_PATCH_ORDER="global"
CT_ZLIB_V_1_3_1=y
# CT_ZLIB_V_1_2_13 is not set
CT_ZLIB_VERSION="1.3.1"
CT_ZLIB_MIRRORS="https://github.com/madler/zlib/releases/download/v${CT_ZLIB_VERSION} https://www.zlib.net/"
CT_ZLIB_ARCHIVE_FILENAME="@{pkg_name}-@{version}"
CT_ZLIB_ARCHIVE_DIRNAME="@{pkg_name}-@{version}"
CT_ZLIB_ARCHIVE_FORMATS=".tar.xz .tar.gz"
CT_ZLIB_SIGNATURE_FORMAT="packed/.asc"
CT_COMP_LIBS_ZSTD=y
CT_COMP_LIBS_ZSTD_PKG_KSYM="ZSTD"
CT_ZSTD_DIR_NAME="zstd"
CT_ZSTD_PKG_NAME="zstd"
CT_ZSTD_SRC_RELEASE=y
# CT_ZSTD_SRC_DEVEL is not set
# CT_ZSTD_SRC_CUSTOM is not set
CT_ZSTD_PATCH_GLOBAL=y
# CT_ZSTD_PATCH_BUNDLED is not set
# CT_ZSTD_PATCH_LOCAL is not set
# CT_ZSTD_PATCH_BUNDLED_LOCAL is not set
# CT_ZSTD_PATCH_LOCAL_BUNDLED is not set
# CT_ZSTD_PATCH_NONE is not set
CT_ZSTD_PATCH_ORDER="global"
CT_ZSTD_V_1_5_7=y
# CT_ZSTD_V_1_5_6 is not set
# CT_ZSTD_V_1_5_5 is not set
# CT_ZSTD_V_1_5_2 is not set
CT_ZSTD_VERSION="1.5.7"
CT_ZSTD_MIRRORS="https://github.com/facebook/zstd/releases/download/v${CT_ZSTD_VERSION} https://downloads.sourceforge.net/project/zstandard.mirror/v${CT_ZSTD_VERSION}"
CT_ZSTD_ARCHIVE_FILENAME="@{pkg_name}-@{version}"
CT_ZSTD_ARCHIVE_DIRNAME="@{pkg_name}-@{version}"
CT_ZSTD_ARCHIVE_FORMATS=".tar.gz"
CT_ZSTD_SIGNATURE_FORMAT="packed/.sig"
CT_ALL_COMP_LIBS_CHOICES="CLOOG EXPAT GETTEXT GMP GNUPRUMCU ISL LIBELF LIBICONV MPC MPFR NCURSES NEWLIB_NANO PICOLIBC ZLIB ZSTD"
# CT_LIBICONV_NEEDED is not set
# CT_GETTEXT_NEEDED is not set
CT_GMP_NEEDED=y
CT_MPFR_NEEDED=y
CT_ISL_NEEDED=y
CT_MPC_NEEDED=y
CT_ZLIB_NEEDED=y
CT_ZSTD_NEEDED=y
CT_GMP=y
CT_MPFR=y
CT_ISL=y
CT_MPC=y
CT_ZLIB=y
CT_ZSTD=y
# end of Companion libraries
#
# Companion tools
#
# CT_COMP_TOOLS_FOR_HOST is not set
# CT_COMP_TOOLS_AUTOCONF is not set
CT_COMP_TOOLS_AUTOMAKE=y
CT_COMP_TOOLS_AUTOMAKE_PKG_KSYM="AUTOMAKE"
CT_AUTOMAKE_DIR_NAME="automake"
CT_AUTOMAKE_PKG_NAME="automake"
CT_AUTOMAKE_SRC_RELEASE=y
# CT_AUTOMAKE_SRC_DEVEL is not set
# CT_AUTOMAKE_SRC_CUSTOM is not set
CT_AUTOMAKE_PATCH_GLOBAL=y
# CT_AUTOMAKE_PATCH_BUNDLED is not set
# CT_AUTOMAKE_PATCH_LOCAL is not set
# CT_AUTOMAKE_PATCH_BUNDLED_LOCAL is not set
# CT_AUTOMAKE_PATCH_LOCAL_BUNDLED is not set
# CT_AUTOMAKE_PATCH_NONE is not set
CT_AUTOMAKE_PATCH_ORDER="global"
CT_AUTOMAKE_V_1_17=y
# CT_AUTOMAKE_V_1_16 is not set
# CT_AUTOMAKE_V_1_15 is not set
CT_AUTOMAKE_VERSION="1.17"
CT_AUTOMAKE_MIRRORS="$(CT_Mirrors GNU automake)"
CT_AUTOMAKE_ARCHIVE_FILENAME="@{pkg_name}-@{version}"
CT_AUTOMAKE_ARCHIVE_DIRNAME="@{pkg_name}-@{version}"
CT_AUTOMAKE_ARCHIVE_FORMATS=".tar.xz .tar.gz"
CT_AUTOMAKE_SIGNATURE_FORMAT="packed/.sig"
# CT_COMP_TOOLS_BISON is not set
# CT_COMP_TOOLS_DTC is not set
# CT_COMP_TOOLS_LIBTOOL is not set
# CT_COMP_TOOLS_M4 is not set
# CT_COMP_TOOLS_MAKE is not set
CT_ALL_COMP_TOOLS_CHOICES="AUTOCONF AUTOMAKE BISON DTC LIBTOOL M4 MAKE"
# end of Companion tools
#
# Test suite
#
# CT_TEST_SUITE_GCC is not set
# end of Test suite
+44
View File
@@ -0,0 +1,44 @@
#!/bin/sh
# tools/fv/fv - Flying V build wrapper.
# The public Agila source now uses the .fv extension, but the underlying V
# compiler only accepts .v files. This wrapper stages temporary .v copies of
# every .fv file in the project, invokes tools/v/v, and then removes the copies.
set -eu
ROOT=$(CDPATH= cd -- "$(dirname -- "$0")/../.." && pwd)
V_CMD="./tools/v/v"
stage_all_fv() {
# Copy every .fv source to a sibling .v, except inside the V compiler tree.
find "$ROOT" -name '*.fv' -not -path '*/tools/v/*' -print0 \
| while IFS= read -r -d '' fv; do
cp "$fv" "${fv%.fv}.v"
done
}
cleanup() {
# Remove any temporary .v files we created, but never touch the V compiler.
find "$ROOT" -name '*.v' -not -path '*/tools/v/*' -delete
}
trap cleanup EXIT INT TERM
stage_all_fv
# Rewrite arguments from .fv to .v and make them relative to ROOT so the V
# compiler does not have to deal with the space in the parent directory name.
new_args=""
for arg in "$@"; do
rel="$arg"
case "$arg" in
"$ROOT"/*) rel="${arg#$ROOT/}" ;;
"$ROOT") rel="." ;;
esac
case "$rel" in
*.fv) new_args="$new_args ${rel%.fv}.v" ;;
*) new_args="$new_args $rel" ;;
esac
done
cd "$ROOT"
"$V_CMD" $new_args
+58
View File
@@ -0,0 +1,58 @@
#!/usr/bin/env python3
"""Generate an 8x8 bitmap font for Agila from a system monospace font."""
from PIL import Image, ImageDraw, ImageFont
font_names = [
"/System/Library/Fonts/Menlo.ttc",
"/System/Library/Fonts/Monaco.dfont",
"/Library/Fonts/Courier New.ttf",
"/System/Library/Fonts/Courier.dfont",
]
font = None
for name in font_names:
try:
font = ImageFont.truetype(name, 8)
print(f"Using font: {name}")
break
except Exception as e:
print(f"Failed {name}: {e}")
if font is None:
print("No suitable font found, using default")
font = ImageFont.load_default()
w, h = 8, 8
values = []
for code in range(32, 127):
ch = chr(code)
img = Image.new("L", (w, h), 0)
draw = ImageDraw.Draw(img)
draw.text((0, 0), ch, font=font, fill=255)
bytes_data = []
for col in range(w):
byte_val = 0
for row in range(h):
px = img.getpixel((col, row))
if px > 127:
byte_val |= 1 << row
bytes_data.append(byte_val)
values.extend(bytes_data)
with open("api/v/font5x7.fv", "w") as f:
f.write("// font5x7.fv - 8x8 bitmap font (ASCII 32-126)\n")
f.write("module agila\n\n")
f.write("const font5x7 = [u8(0x{:02x}), ".format(values[0]))
f.write(", ".join(f"0x{v:02x}" for v in values[1:]))
f.write("]\n\n")
f.write("pub fn glyph5x7(ch rune) []u8 {\n")
f.write("\tcode := int(ch) - 32\n")
f.write("\tif code < 0 || code > 94 {\n")
f.write("\t\treturn font5x7[0..8] // space\n")
f.write("\t}\n")
f.write("\toff := code * 8\n")
f.write("\treturn font5x7[off..off+8]\n")
f.write("}\n")
print(f"Generated {len(values)} bytes for {len(values)//8} glyphs")
+32
View File
@@ -0,0 +1,32 @@
root = true
[*]
charset = utf-8
end_of_line = lf
insert_final_newline = true
trim_trailing_whitespace = true
[*.{v,js,css}]
indent_style = tab
[*.{bat,cmd}]
# BAT/CMD ~ DOS/Win requires BAT/CMD files to have CRLF EOLNs
end_of_line = crlf
[*.{yml,yaml}]
indent_style = space
indent_size = 2
[*.md]
trim_trailing_whitespace = false
# lines that are too long will trigger an error in cmd/tools/vcheck-md.v
# run v check-md [folder/file] to test markdown files
# the longest normal line is specified with this constant:
# `too_long_line_length_other = 100`
max_line_length = 100
[*.{txt,out}]
insert_final_newline = false
[{Makefile,GNUmakefile}]
indent_style = tab
+10
View File
@@ -0,0 +1,10 @@
* text=auto eol=lf
*.bat eol=crlf
*.v linguist-language=V
*.vv linguist-language=V
*.vsh linguist-language=V
v.mod linguist-language=V
.vdocignore linguist-language=ignore
Dockerfile.* linguist-language=Dockerfile
+3
View File
@@ -0,0 +1,3 @@
{
"singleQuote": true
}
+5
View File
@@ -0,0 +1,5 @@
# These are supported funding model platforms
open_collective: vlang
patreon: vlang
github: [medvednikov]
+9
View File
@@ -0,0 +1,9 @@
blank_issues_enabled: true
contact_links:
- name: 💬 General Questions and Answers about V
url: https://github.com/vlang/v/discussions/categories/questions-and-answers
about: You can ask and answer questions about V in the discussions forum.
- name: 💬 Discord Server
url: https://discord.gg/vlang
about: You can join our Discord server for real time discussion and support
+19
View File
@@ -0,0 +1,19 @@
name: 📕 Documentation Issue
description: Report an issue in the Reference documentation or Developer Guide
labels: ['Unit: Documentation']
body:
- type: textarea
id: description
attributes:
label: Describe the issue
description: A clear and concise description of the issue.
validations:
required: true
- type: textarea
id: links
attributes:
label: Links
description: Include links to affected documentation page(s).
validations:
required: true
+63
View File
@@ -0,0 +1,63 @@
name: 🚀 Feature Request
description: Suggest an idea for this project
labels: [Feature Request]
body:
- type: textarea
id: description
attributes:
label: Describe the feature
description: A clear and concise description of the feature you are proposing.
validations:
required: true
- type: textarea
id: use-case
attributes:
label: Use Case
description: |
Why do you need this feature? For example: "I'm always frustrated when..."
validations:
required: true
- type: textarea
id: solution
attributes:
label: Proposed Solution
description: Suggest how to implement the addition or change. Please include prototype/workaround/sketch/reference implementation.
validations:
required: false
- type: textarea
id: other
attributes:
label: Other Information
description: Any alternative solutions or features you considered, a more detailed explanation, stack traces, related issues, links for context, etc.
validations:
required: false
- type: checkboxes
id: ack
attributes:
label: Acknowledgements
options:
- label: I may be able to implement this feature request
required: false
- label: This feature might incur a breaking change
required: false
- type: input
id: version
attributes:
label: Version used
description: Please provide the version of the repository or tool you are using.
validations:
required: true
- type: textarea
id: environment
attributes:
label: Environment details (OS name and version, etc.)
description: You can use `v doctor` to fill up this section.
validations:
required: true
+34
View File
@@ -0,0 +1,34 @@
<!--
Please title your PR as follows: `module: description` (e.g. `time: fix date format`).
Always start with the thing you are fixing, then describe the fix.
Don't use past tense (e.g. "fixed foo bar").
Explain what your PR does and why.
If you are adding a new function, please document it and add tests:
```
// foo does foo and bar
fn foo() {
// file_test.v
fn test_foo() {
assert foo() == ...
...
}
```
If you are fixing a bug, please add a test that covers it.
Before submitting a PR, please run `v test-all` .
See also `TESTS.md`.
I try to process PRs as soon as possible. They should be handled within 24 hours.
Applying labels to PRs is not needed.
Thanks a lot for your contribution!
-->
@@ -0,0 +1,30 @@
name: 'Cache Apt Packages'
description: 'Cache all commonly used apt packages to speed up CI jobs'
# imagemagick : convert, mogrify
# xvfb : xvfb
# openimageio-tools : idiff
# libxcursor-dev libxi-dev : V gfx deps
# libgl1-mesa-dri : For headless rendering on the CI / software DRI driver (LIBGL_ALWAYS_SOFTWARE=true)
# freeglut3-dev : Fixes graphic apps compilation with tcc
# sdl2 : needed for Puzzle Vibes & Chocolate Doom
# libsodium-dev : needed for Gitly and C2V
runs:
using: 'composite'
steps:
- uses: awalsh128/cache-apt-pkgs-action@v1.5.3
with:
version: 1.0
packages: expect binutils postgresql sqlite3 clang valgrind \
imagemagick openimageio-tools xvfb xsel xclip \
libsodium-dev libpq-dev libssl-dev libsqlite3-dev \
libfreetype6-dev libxi-dev libxcursor-dev \
libgl-dev libxrandr-dev libasound2-dev \
libx11-dev freeglut3-dev mesa-common-dev libgl1-mesa-dev libgl1-mesa-dri \
libsdl2-dev libsdl2-ttf-dev libsdl2-mixer-dev libsdl2-image-dev libsdl2-net-dev \
libpng-dev libsamplerate0-dev \
xfonts-75dpi xfonts-base
- name: Install common packages
run: echo "done installing packages"
shell: bash
+6
View File
@@ -0,0 +1,6 @@
version: 2
updates:
- package-ecosystem: 'github-actions'
directory: '/'
schedule:
interval: 'daily'
+19
View File
@@ -0,0 +1,19 @@
// The task of this program, is to register all available .json files
// in this folder with Github Actions, so that it can make annotations
// for all found notices/warnings/errors produced by the V compiler
// while running the CI jobs.
// Those annotations provide a way to get a quick overview for failures,
// without having to scroll into the detailed logs produced by each job.
const github_job = getenv('GITHUB_JOB')
if github_job == '' {
exit(0)
}
dump(github_job)
chdir(@VEXEROOT)!
for f in walk_ext('.github/problem-matchers/', '.json').sorted() {
println('::add-matcher::${real_path(f)}')
println('registered matcher: `${f}`')
}
+18
View File
@@ -0,0 +1,18 @@
{
"__comment": "Based on https://github.com/python/cpython/blob/main/.github/problem-matchers/gcc.json",
"problemMatcher": [
{
"owner": "v-problem-matcher",
"pattern": [
{
"regexp": "^(.*):(\\d+):(\\d+):\\s+(?:fatal\\s+)?(error):\\s+(.*)$",
"file": 1,
"line": 2,
"column": 3,
"severity": 4,
"message": 5
}
]
}
]
}
+30
View File
@@ -0,0 +1,30 @@
module main
import os
fn show_release_tag_for(now string) string {
script_path := os.join_path(os.dir(@FILE), 'workflows', 'show_manual_release_cmd.vsh')
cmd := 'V_RELEASE_TAG_NOW="${now}" ${os.quoted_path(@VEXE)} run ${os.quoted_path(script_path)}'
res := os.execute(cmd)
assert res.exit_code == 0, res.output
for line in res.output.split_into_lines() {
if line.contains('current release_tag: ') {
return line.all_after('current release_tag: ')
}
}
panic('missing release tag in output:\n${res.output}')
}
fn test_show_manual_release_cmd_uses_iso_week_year() {
test_cases := {
'2025-12-28 00:00:00': 'weekly.2025.52'
'2025-12-29 00:00:00': 'weekly.2026.01'
'2025-12-31 00:00:00': 'weekly.2026.01'
'2026-01-01 00:00:00': 'weekly.2026.01'
'2026-01-04 00:00:00': 'weekly.2026.01'
'2026-01-05 00:00:00': 'weekly.2026.02'
}
for input, expected in test_cases {
assert show_release_tag_for(input) == expected
}
}
+52
View File
@@ -0,0 +1,52 @@
#######################################################################################
## The goal of this file, is to provide an easy and reproducible way to check *locally*
## the CI job `docker-alpine-musl-gcc`
## Building the docker image:
## docker build -t ci_alpine_local - < .github/workflows/Dockerfile.ci_alpine_local
## Running the docker image, after building it:
## docker run --rm -it -v .:/opt/vlang -w /opt/vlang ci_alpine_local
## Once it is running, inside the container you can:
## make && v -e 'println(2+2)'
## ... then do whatever you need to reproduce the CI test failure.
## Note: after you are finished, and exit the container, run `make` again, otherwise
## you will be using V (and potentially V tools) that were compiled with musl.
#######################################################################################
FROM thevlang/vlang:alpine-build
LABEL maintainer="spytheman <spytheman@bulsynt.org>"
WORKDIR /opt/vlang
ENV PATH /opt/vlang:/usr/local/sbin:/usr/local/bin:/usr/sbin:/usr/bin:/sbin:/bin
## install development packages
RUN apk --no-cache add \
musl-dev libc-dev libc6-compat gcompat \
libunwind-dev libunwind-static \
gc gc-dev \
binutils diffutils elfutils \
strace gdb \
pcre bash fzf fzf-vim tmux less file colordiff \
vim vim-editorconfig \
nano nano-syntax \
micro
RUN git config --global --add safe.directory /opt/vlang &&\
git config --global --add safe.directory /opt/vlang/vc &&\
git config --global --add safe.directory /opt/vlang/thirdparty/tcc &&\
find /usr/share/nano/ -iname "*.nanorc" -exec echo include {} \; >> ~/.nanorc &&\
micro -plugin install detectindent &&\
micro -plugin install editorconfig &&\
micro -plugin install monokai-dark &&\
micro -plugin install quickfix &&\
micro -plugin install runit &&\
micro -plugin install cheat &&\
micro -plugin install jump &&\
true
## setup runtime environment for v and bash:
ENV VTMP /tmp/v
ENV VMODULES /tmp/vmodules
ENV VFLAGS "-d dynamic_boehm"
CMD ["bash"]
+25
View File
@@ -0,0 +1,25 @@
name: Add voting info to new issue
on:
issues:
types:
- opened
jobs:
add-voting-info:
runs-on: ubuntu-latest
permissions:
issues: write
steps:
- name: Append voting info to issue body
uses: julien-deramond/update-issue-body@v1
with:
issue-number: ${{ github.event.issue.number }}
body: |
> [!NOTE]
> You can use the 👍 reaction to increase the issue's priority for developers.
>
> Please note that only the 👍 reaction to the issue itself counts as a vote.
> Other reactions and those to comments will not be taken into account.
edit-mode: append
append-separator: newline
+15
View File
@@ -0,0 +1,15 @@
#!/bin/sh -l
set -e
pwd
uname -a
make -j4
./v version
du -s .
echo "DONE"
+25
View File
@@ -0,0 +1,25 @@
#!/bin/sh -l
set -e
pwd
uname -a
du -s .
ls -lat
##./v -silent test-all
## try running the known failing tests first to get faster feedback
./v vlib/builtin/string_test.v
./v vlib/strings/builder_test.v
./v -silent test-cleancode
./v -silent test-self
./v build-vbinaries
echo "DONE"
+67
View File
@@ -0,0 +1,67 @@
#!/usr/bin/env -S v
module main
import os
import vab.vxt
import vab.android.ndk
fn main() {
assert ndk.found()
assert vxt.found()
work_dir := os.join_path(os.vtmp_dir(), 'android_cross_compile_test')
os.rm(work_dir) or {}
os.mkdir_all(work_dir) or { panic(err) }
vexe := vxt.vexe()
examples_dir := os.join_path(vxt.home(), 'examples')
v_example := os.join_path(examples_dir, 'toml.v')
ndk_version := ndk.default_version()
sysroot_path := ndk.sysroot_path(ndk_version) or { panic(err) }
include_path := os.join_path(sysroot_path, 'usr', 'include')
android_include_path := os.join_path(include_path, 'android')
//'-I"${include_path}"'
cflags := ['-I"${android_include_path}"', '-Wno-unused-value', '-Wno-implicit-function-declaration',
'-Wno-int-conversion']
for arch in ndk.supported_archs {
for level in ['min', 'max'] {
compiler_api := match level {
'min' {
ndk.compiler_min_api(.c, ndk_version, arch) or { panic(err) }
}
'max' {
ndk.compiler_max_api(.c, ndk_version, arch) or { panic(err) }
}
else {
panic('invalid min/max level')
}
}
os.setenv('VCROSS_COMPILER_NAME', compiler_api, true)
c_file := os.join_path(work_dir, arch + '-' + level + '.c')
o_file := os.join_path(work_dir, arch + '-' + level + '.o')
// x.v -> x.c
v_compile_cmd := '${vexe} -o ${c_file} -os android -gc none ${v_example}'
vres := os.execute(v_compile_cmd)
if vres.exit_code != 0 {
panic('"${v_compile_cmd}" failed: ${vres.output}')
}
assert os.exists(c_file)
// x.c -> x.o
compile_cmd := '${compiler_api} ${cflags.join(' ')} -c ${c_file} -o ${o_file}'
cres := os.execute(compile_cmd)
if cres.exit_code != 0 {
panic('"${compile_cmd}" failed: ${cres.output}')
}
assert os.exists(o_file)
compiler_exe_name := os.file_name(compiler_api)
println('Compiled examples/toml.v successfully for (${level}) ${arch} ${compiler_exe_name}')
}
}
}
@@ -0,0 +1,29 @@
name: json decoder benchmark CI
on:
push:
branches:
- master
paths:
- 'vlib/x/json2/**' # Trigger on changes in this folder
jobs:
json-encode-benchmark:
runs-on: ubuntu-latest
timeout-minutes: 5
steps:
- name: Checkout repository
uses: actions/checkout@v7
- name: Build V
run: make -j4 && ./v symlink
- name: Run V benchmark and save output
run: (echo '```txt'; v -prod crun vlib/x/json2/tests/bench.v; echo '```') > vlib/x/json2/tests/bench_out.md
- name: Upload result file
uses: actions/upload-artifact@v7
with:
name: program-output
path: vlib/x/json2/tests/bench_out.md
@@ -0,0 +1,31 @@
name: json encoder benchmark CI
on:
push:
branches:
- master
paths:
- 'vlib/x/json2/**' # Trigger on changes in this folder
- '!vlib/x/json2/strict/**' # Ignore
- '!vlib/x/json2/tests/**' # Ignore
jobs:
json-encode-benchmark:
runs-on: ubuntu-latest
timeout-minutes: 5
steps:
- name: Checkout repository
uses: actions/checkout@v7
- name: Build V
run: make -j4 && ./v symlink
- name: Run V benchmark and save output
run: (echo '```sh'; v -prod crun vlib/v/tests/bench/bench_json_vs_json2.v; echo '```') > vlib/v/tests/bench/bench_json_vs_json2_out.md
- name: Upload result file
uses: actions/upload-artifact@v7
with:
name: program-output
path: vlib/v/tests/bench/bench_json_vs_json2_out.md
+135
View File
@@ -0,0 +1,135 @@
name: Bootstrapping CI
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.yml'
- '**.md'
- '**.vv'
- '**.out'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
- '!cmd/tools/vup.v'
- '!**/bootstrapping_ci.yml'
pull_request:
paths-ignore:
- '**.yml'
- '**.md'
- '**.vv'
- '**.out'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
- '!cmd/tools/vup.v'
- '!**/bootstrapping_ci.yml'
concurrency:
group: bootstrapping-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
bootstrap-v:
strategy:
matrix:
os: [ubuntu-latest, macos-14]
fail-fast: false
runs-on: ${{ matrix.os }}
timeout-minutes: 20
env:
VFLAGS: -no-parallel
B_LFLAGS: -lm -lpthread
steps:
- uses: actions/checkout@v7
with:
fetch-depth: 0
- name: Build V
run: make -j4
- name: Test bootstrapping (v.c can be compiled and run with -os cross)
run: |
ls -la v vc/v.c
./v -os cross -o vc/v.c cmd/v
# shellcheck disable=SC2086
cc -o v_from_vc vc/v.c $B_LFLAGS
ls -lart v_from_vc
./v_from_vc version
./v_from_vc run examples/hello_world.v
./v_from_vc -o v_from_vc_produced_native_v cmd/v
./v_from_vc_produced_native_v run examples/hello_world.v
### the next make invocation will simulate building V from scratch
make local=1
ls -la v vc/v.c v_from_vc v_from_vc_produced_native_v
./v_from_vc_produced_native_v -os cross -o vc/v.c cmd/v
### do it a second time, just in case:
# shellcheck disable=SC2086
clang -o v_from_vc2 vc/v.c $B_LFLAGS
ls -lart v_from_vc2
./v_from_vc2 version
./v_from_vc2 run examples/hello_world.v
./v_from_vc2 -o v_from_vc_produced_native_v2 cmd/v
./v_from_vc_produced_native_v2 run examples/hello_world.v
make local=1
ls -la v vc/v.c
ls -la v_from_vc v_from_vc_produced_native_v
ls -la v_from_vc2 v_from_vc_produced_native_v2
- name: Ensure V master is available
if: github.ref_name != 'master'
run: git branch master remotes/origin/master
- name: Test `v up`
run: |
# Derive a commit sha from an older successful fast workflow on master that was able to build V.
# The workflow used below is `Path Testing CI` (18477644).
# Fetch several successful runs and pick the first commit that is actually reachable on master.
# Some runs may reference commits from force-pushed branches that are no longer on master.
fetch_page() {
local page="$1"
local body=""
for attempt in 1 2 3; do
body=$(curl -sL --max-time 30 \
-H "Accept: application/vnd.github+json" \
-H "Authorization: Bearer ${{ secrets.GITHUB_TOKEN }}" \
-H "X-GitHub-Api-Version: 2022-11-28" \
"https://api.github.com/repos/vlang/v/actions/workflows/18477644/runs?branch=master&status=success&event=push&per_page=10&page=$page")
if [ -n "$body" ] && echo "$body" | jq -e '.workflow_runs' >/dev/null 2>&1; then
echo "$body" | jq -r '.workflow_runs[].head_sha'
return 0
fi
echo "::warning::page $page attempt $attempt failed, retrying..." >&2
sleep 5
done
return 1
}
recent_good_commit=""
valid_count=0
for page in 1 2 3; do
commits=$(fetch_page "$page" || true)
commit_count=$(printf '%s\n' "$commits" | grep -c . || true)
echo "page $page: fetched $commit_count commits"
for sha in $commits; do
if git merge-base --is-ancestor "$sha" master 2>/dev/null; then
valid_count=$((valid_count + 1))
echo " valid #$valid_count: $sha"
# Skip the first few valid commits to get an older one for testing upgrades.
if [ "$valid_count" -ge 5 ]; then
recent_good_commit="$sha"
break 2
fi
fi
done
done
if [ -z "$recent_good_commit" ]; then
echo "Path Testing CI lookup yielded only $valid_count valid commits; falling back to git log."
recent_good_commit=$(git log master --first-parent --format=%H --before='14 days ago' -n 1)
fi
if [ -z "$recent_good_commit" ]; then
echo "Could not find a valid recent good commit on master"
exit 1
fi
echo "recent_good_commit=$recent_good_commit"
# Build oldv at recent_good_commit.
./v run cmd/tools/oldv.v -v "$recent_good_commit"
cd "$HOME/.cache/oldv/v_at_$recent_good_commit"
# Test updating
./v version && ./v -v up && ./v version
./v -o v2 cmd/v && ./v2 -o v3 cmd/v
+54
View File
@@ -0,0 +1,54 @@
name: CI Ubuntu 25 GCC 14.2
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/build_on_ubuntu_25_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/build_on_ubuntu_25_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
jobs:
ubuntu-25-gcc-14-2-build:
runs-on: ubuntu-latest
timeout-minutes: 30
steps:
- uses: actions/checkout@v7
- name: Build and test in Ubuntu 25.04 with GCC 14.2
run: |
set -o xtrace
echo "$PWD"
whoami
touch outside_docker.txt
git log -n4
echo "running docker ..."
docker run --rm \
--mount type=bind,source=/home/runner/work/v/v,destination=/src \
-w /src ubuntu:25.04 bash -c '
set -o xtrace
echo "running inside docker"
whoami
cp -r /src ~/vproject; cd ~/vproject
touch inside_docker.txt
ls -la
git log -n4
apt update -y -qq
apt install -y -qq git build-essential make
git config --global --add safe.directory /src/vc
git config --global --add safe.directory /src/thirdparty/tcc
make
./v symlink
v run examples/hello_world.v
v run examples/primes.v
'
+56
View File
@@ -0,0 +1,56 @@
#!/usr/bin/env bash
set -e
V=$PWD/v
if [[ -x "$V" ]]
then
echo "The v executable exists."
else
echo "This script should be run from the top level folder of a V repository"
echo "i.e. the folder where your V executable is."
exit 1
fi
BUILD=$PWD/vinix_build
echo "Creating $BUILD folder..."
rm -rf $BUILD
mkdir -p $BUILD
cd $BUILD
echo "Clone current Vinix"
./v retry -- git clone --depth=1 https://github.com/vlang/vinix.git
cd $BUILD
echo "Clone current mlibc"
./v retry -- git clone --depth=1 https://github.com/managarm/mlibc.git
cd $BUILD
echo "Patch mlibc for Vinix"
cd mlibc
patch -p3 < ../vinix/patches/mlibc/mlibc.patch
cd $BUILD
echo "Install mlibc headers"
mkdir mlibc-build
cd mlibc-build
meson --cross-file ../vinix/cross_file.txt --prefix=/ -Dheaders_only=true ../mlibc
ninja
mkdir ../mlibc-headers
DESTDIR=`realpath ../mlibc-headers` ninja install
cd $BUILD
echo "Attempt to build the Vinix kernel (debug)"
cd vinix/kernel
make PROD=false CFLAGS="-D__vinix__ -O2 -g -pipe -I../../mlibc-headers/include"
make clean
cd $BUILD
echo "Attempt to build the Vinix kernel (prod)"
cd vinix/kernel
make PROD=true CFLAGS="-D__vinix__ -O2 -g -pipe -I../../mlibc-headers/include"
make clean
rm -rf $BUILD
+142
View File
@@ -0,0 +1,142 @@
name: C2V apps
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/c2v_ci.yml'
- 'doc/**'
- 'examples/**'
- 'tutorials/**'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/c2v_ci.yml'
- 'doc/**'
- 'examples/**'
- 'tutorials/**'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: c2v-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
build-doom:
runs-on: ubuntu-24.04
timeout-minutes: 30
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make && ./v symlink
- name: Set 8.8.8.8 as dns server
run: |
sudo sed -i 's/#DNS=/DNS=8.8.8.8 8.8.4.4/g' /etc/systemd/resolved.conf
sudo systemctl daemon-reload
sudo systemctl restart systemd-networkd
sudo systemctl restart systemd-resolved
dig distro.ibiblio.org
- name: Install C2V
run: |
v retry -- v install --git https://github.com/vlang/c2v
v -g ~/.vmodules/c2v/ || true
- name: Install dependencies
run: |
if [ "${{ runner.os }}" == "Linux" ]; then
.github/workflows/disable_azure_mirror.sh
v retry -- sudo apt update -y -qq
v retry -- sudo apt install libsdl2-dev libsdl2-mixer-dev libsdl2-net-dev libpng-dev libsamplerate0-dev
else
v retry -- brew install sdl2 sdl2_mixer sdl2_net libpng libsamplerate
fi
- name: Build original Chocolate Doom
run: |
v retry -- git clone --quiet --depth 1 https://github.com/vlang/doom ~/code/doom
cd ~/code/doom/chocolate-doom
cmake -DCMAKE_BUILD_TYPE=Debug .
make chocolate-doom
- name: Translate the whole game in project/folder mode and compile it
run: |
touch ~/DOOM1.WAD
WAD_FILE=~/DOOM1.WAD ~/code/doom/build_whole_project.sh
test-regression:
runs-on: ubuntu-24.04
timeout-minutes: 20
env:
VFLAGS: -cc tcc
DISPLAY: :99
LIBGL_ALWAYS_SOFTWARE: true
VTMP: /tmp
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make && ./v symlink
- name: Set 8.8.8.8 as dns server
run: |
sudo sed -i 's/#DNS=/DNS=8.8.8.8 8.8.4.4/g' /etc/systemd/resolved.conf
sudo systemctl daemon-reload
sudo systemctl restart systemd-networkd
sudo systemctl restart systemd-resolved
dig distro.ibiblio.org
- name: Install C2V
run: |
v retry -- v install --git https://github.com/vlang/c2v
v -g ~/.vmodules/c2v/ || true
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
v retry -- sudo apt update -y -qq
v retry -- sudo apt install libsdl2-dev libsdl2-mixer-dev libsdl2-net-dev libpng-dev libsamplerate0-dev
# c2v / DOOM dependencies
# vgret dependencies
# imagemagick : convert, mogrify, import
# xvfb : For starting X11 Virtual FrameBuffers
# openimageio-tools : idiff
# libgl1-mesa-dri : For headless rendering / software DRI driver (LIBGL_ALWAYS_SOFTWARE=true)
# freeglut3-dev : Fixes graphic apps compilation with tcc
v retry -- sudo apt install imagemagick openimageio-tools freeglut3-dev libgl1-mesa-dri xvfb xsel xclip
- name: Setup test tools
run: |
# Fetch the free ~4MB DOOM1.WAD from the link at https://doomwiki.org/wiki/DOOM1.WAD
v retry -- v download https://distro.ibiblio.org/slitaz/sources/packages/d/doom1.wad
mv doom1.wad ~/doom1.wad
# Get imgur upload script
v retry -- v download https://raw.githubusercontent.com/tremby/imgur.sh/c98345d/imgur.sh
chmod +x ./imgur.sh
# Get regression images to test against
v retry -- git clone https://github.com/Larpon/doom-regression-images
- name: Build original Chocolate Doom
run: |
v retry -- git clone --quiet --depth 1 https://github.com/vlang/doom ~/code/doom
cd ~/code/doom/chocolate-doom
cmake -DCMAKE_BUILD_TYPE=Debug .
make chocolate-doom
- name: Translate the whole game in project/folder mode
run: WAD_FILE=~/doom1.wad ~/code/doom/build_whole_project.sh
- name: Sample and compare with vgret
id: compare
continue-on-error: true
run: |
Xvfb "$DISPLAY" -screen 0 800x600x24 -fbdir /var/tmp/ &
sleep 2; while [ ! -f /var/tmp/Xvfb_screen0 ]; do sleep 0.5; done # give xvfb time to start, even on slow CI runs
sleep 5; v gret -r ~/code/doom -t ./doom-regression-images/vgret.doom.toml -v ./doom-sample_images ./doom-regression-images
- name: Upload regression to imgur
if: steps.compare.outcome != 'success'
run: |
./imgur.sh /tmp/fail.png
./imgur.sh /tmp/diff.png
exit 1
+171
View File
@@ -0,0 +1,171 @@
import os
import time
const compare_prod = '-prod' in os.args
const cleanup_tmp = '-no-cleanup' !in os.args
const fetch_remote = '-no-fetch' !in os.args
fn gbranch() string {
return os.execute(r'git branch --list|grep ^\*').output.trim_left('* ').trim_space()
}
fn gcommit() string {
return os.execute(r'git rev-parse --short=7 HEAD').output.trim_left('* ').trim_space()
}
fn r(cmd string) {
res := os.system(cmd)
if res != 0 {
eprintln('> failed running: `${cmd}`')
exit(1)
}
}
fn xtime(cmd string) {
$if linux {
r('/usr/bin/time -f "CPU: %Us\tReal: %es\tElapsed: %E\tRAM: %MKB\t%C" ${cmd}')
return
}
$if macos {
r('/opt/homebrew/bin/gtime -f "CPU: %Us\tReal: %es\tElapsed: %E\tRAM: %MKB\t%C" ${cmd}')
return
}
// Pure V fallback - no memory stats, but better than nothing ...
before := time.now()
r(cmd)
after := time.now()
delta_time := after - before
println('> Elapsed time: ${delta_time.milliseconds()} ms, for cmd: ${cmd}')
}
fn show_size(fpath string) {
println('>Size of ${fpath:20s}: ${os.file_size(fpath):10}')
}
fn compare_size(fpath1 string, fpath2 string) {
size1 := os.file_size(fpath1)
size2 := os.file_size(fpath2)
diff_ := i64(size2) - i64(size1)
println('>>>>>> size("${fpath2:17}") - size("${fpath1:17}") = ${size2:10} - ${size1:10} = ${diff_:10}')
}
fn vcompare(vold string, vnew string) {
r("v repeat --nmaxs 7 -R 3 '${vold} -check-syntax examples/hello_world.v' '${vnew} -check-syntax examples/hello_world.v'")
r("v repeat --nmaxs 7 -R 3 '${vold} -check examples/hello_world.v' '${vnew} -check examples/hello_world.v'")
r("v repeat --nmaxs 7 -R 3 '${vold} -no-parallel -o ohw.c examples/hello_world.v' '${vnew} -no-parallel -o nhw.c examples/hello_world.v'")
compare_size('ohw.c', 'nhw.c')
r("v repeat --nmaxs 7 -R 3 '${vold} -no-parallel -o ohw.exe examples/hello_world.v' '${vnew} -no-parallel -o nhw.exe examples/hello_world.v'")
compare_size('ohw.exe', 'nhw.exe')
r("v repeat --nmaxs 7 -R 3 '${vold} -check-syntax cmd/v' '${vnew} -check-syntax cmd/v'")
r("v repeat --nmaxs 7 -R 3 '${vold} -check cmd/v' '${vnew} -check cmd/v'")
r("v repeat --nmaxs 7 -R 3 '${vold} -no-parallel -o ov.c cmd/v' '${vnew} -no-parallel -o nv.c cmd/v'")
compare_size('ov.c', 'nv.c')
r("v repeat --nmaxs 7 -R 3 '${vold} -no-parallel -o ov.exe cmd/v' '${vnew} -no-parallel -o nv.exe cmd/v'")
compare_size('ov.exe', 'nv.exe')
}
fn hline(header_message string) {
println('='.repeat(98))
println(header_message)
}
fn main() {
// The starting point, when this program should be started, is just after `gh pr checkout NUMBER`.
start := time.now()
pr_branch := gbranch()
pr_commit := gcommit()
hline('Current git branch: ${pr_branch}, commit: ${pr_commit}')
println(' Compiling new V executables from PR branch: ${pr_branch}, commit: ${pr_commit} ...')
// *not* using v self here is deliberate, so that the `v` executable itself, is not changed after running this script
xtime('./v -o vnew1 cmd/v')
xtime('./vnew1 -o vnew2 cmd/v')
xtime('./vnew2 -no-parallel -o vnew cmd/v')
xtime('./vnew -no-parallel -o nhw_current.c examples/hello_world.v')
xtime('./vnew -no-parallel -o nhw_current_gcc.c -cc gcc examples/hello_world.v')
xtime('./vnew -no-parallel -o nv_current.c cmd/v')
if compare_prod {
xtime('./vnew -no-parallel -prod -o vnew_prod cmd/v')
}
show_size('nhw_current.c')
show_size('nhw_current_gcc.c')
show_size('nv_current.c')
show_size('vnew')
if compare_prod {
show_size('vnew_prod')
}
r('rm -rf vnew1 vnew2')
if fetch_remote {
// make sure to always compare against the main V repo's master branch by default:
os.execute('git -C . remote add V_REPO https://github.com/vlang/v.git')
os.execute('git -C . fetch V_REPO')
os.execute('git branch -D v_repo_master')
os.execute('git branch -f --track v_repo_master V_REPO/master')
}
r('git checkout v_repo_master')
master_branch := gbranch()
hline(' Compiling old V executables from branch: ${master_branch}, commit: ${gcommit()} ...')
// Use `make` to bootstrap the old V from the C sources on the master branch,
// because the new V compiler may have breaking changes that prevent it from
// compiling the old code directly.
xtime('make -j4')
xtime('./v -o vold1 cmd/v')
xtime('./vold1 -no-parallel -o vold cmd/v')
xtime('./vold -no-parallel -o ohw_master.c examples/hello_world.v')
xtime('./vold -no-parallel -o ohw_master_gcc.c -cc gcc examples/hello_world.v')
xtime('./vold -no-parallel -o ov_master.c cmd/v')
if compare_prod {
xtime('./vold -no-parallel -prod -o vold_prod cmd/v')
show_size('vold_prod')
}
show_size('ohw_master.c')
show_size('ohw_master_gcc.c')
show_size('ov_master.c')
show_size('vold')
if compare_prod {
show_size('vold_prod')
}
r('rm -rf vold1')
hline('File sizes so far ...')
compare_size('ohw_master.c', 'nhw_current.c')
compare_size('ohw_master_gcc.c', 'nhw_current_gcc.c')
compare_size('ov_master.c', 'nv_current.c')
compare_size('vold', 'vnew')
r('git checkout ${pr_branch}')
// we are on the PR branch again
hline(' Measuring at PR branch: ${pr_branch}, commit: ${gcommit()} ...')
if compare_prod {
vcompare('./vold_prod', './vnew_prod')
} else {
vcompare('./vold', './vnew')
}
println('Done. Total time: ${(time.now() - start).seconds()} s.')
hline('Final summary for file diff sizes on their own branches:')
compare_size('ohw_master.c', 'nhw_current.c')
compare_size('ohw_master_gcc.c', 'nhw_current_gcc.c')
compare_size('ov_master.c', 'nv_current.c')
compare_size('vold', 'vnew')
if compare_prod {
compare_size('vold_prod', 'vnew_prod')
}
hline('Final summary for file diff sizes for generated files on the *current* branch:')
compare_size('ohw.c', 'nhw.c')
compare_size('ov.c', 'nv.c')
compare_size('ohw.exe', 'nhw.exe')
compare_size('ov.exe', 'nv.exe')
// After all the measurements are done, delete all the generated temporary files,
// except the `vold` and `vnew` compilers, so that they can be used later in manual
// experiments:
if cleanup_tmp {
r('rm -rf ohw* nhw* nv* ov*')
}
}
+25
View File
@@ -0,0 +1,25 @@
#!/usr/bin/env bash
set -e
function show() {
printf "\u001b[35m$1\u001b[0m\n"
}
## NOTE: this step is disabled in v_apps_and_modules_compile_ci.yml via `${{ false && ... }}`.
## Reason: discord.v uses x.json2.raw_decode which was deprecated-as-error in V on 2025-10-10.
## The upstream repo (vcv88/discord.v) has not been updated since Dec 2024.
## Re-enable both the yml step and this script once vcv88/discord.v#21 is resolved.
## Track: https://github.com/vlang/v/issues/26853
rm -rf discord/
show "Clone https://github.com/vcv88/discord.v"
v retry -- git clone --filter=blob:none --quiet https://github.com/vcv88/discord.v discord/
cd discord/
show "Checkout last known good commit"
git checkout ce9ff457fce92d5bb15df2974440cd8292457ee0
show "Execute Tests"
v test .
cd ..
rm -rf discord/
+47
View File
@@ -0,0 +1,47 @@
#!/usr/bin/env bash
set -e
function show() {
printf "\u001b[35m$1\u001b[0m\n"
}
rm -rf herolib/
show "Clone https://github.com/freeflowuniverse/herolib"
v retry -- git clone --filter=blob:none --quiet https://github.com/freeflowuniverse/herolib herolib
cd herolib
git checkout development
mkdir -p ~/.vmodules/freeflowuniverse
ln -s $(pwd)/lib ~/.vmodules/freeflowuniverse/herolib
cd cli
show "Checkout last known good commit"
git checkout ca8799af39228a5678a7be81128c5b0c342c9efc
v wipe-cache
show "Build project no parallel (gcc)"
v -cc gcc -cg -enable-globals -w -n hero.v
show "Checking build"
ls -l ./hero
v wipe-cache
show "Build project no parallel (clang)"
v -cc clang -cg -enable-globals -w -n hero.v
show "Checking build"
ls -l ./hero
v wipe-cache
show "Build project with -parallel-cc (clang)"
v -cc clang -cg -enable-globals -parallel-cc -w -n hero.v
show "Checking gcc build"
ls -l ./hero
v wipe-cache
show "Build project with -parallel-cc (gcc)"
v -cc gcc -cg -enable-globals -parallel-cc -w -n hero.v
show "Checking clang build"
ls -l ./hero
rm -rf ../../herolib
@@ -0,0 +1,7 @@
#!/usr/bin/env bash
for f in examples/sokol/*/ ; do
echo "compiling shaders for $f ...";
time ./v shader $f;
echo "done";
done;
+47
View File
@@ -0,0 +1,47 @@
#!/usr/bin/env bash
set -ex
function show() {
printf "\u001b[35m$1\u001b[0m\n"
}
show "Prepare"
rm -rf vtcc/
show "Clone vtcc"
.github/workflows/retry.sh git clone https://github.com/medvednikov/vtcc --branch stable --quiet vtcc/
du -s vtcc/
show "Compile vtcc"
cd vtcc/
v run make.vsh
cd ..
ls -la vtcc/vtcc
./vtcc/vtcc --version
show "Generate the C file, for the current V version"
./v -o vlang.c cmd/v
ls -la vlang.c
if [[ "$(uname)" == "Darwin" ]]; then
show "Compile the C file with vtcc (object only, vtcc targets x86_64 ELF)"
SDK_PATH="$(xcrun --show-sdk-path)"
./vtcc/vtcc -c vlang.c -o vlang.o -I"${SDK_PATH}/usr/include"
ls -la vlang.o
rm -rf vlang.o vlang.c vtcc/
else
show "Compile the C file with vtcc"
./vtcc/vtcc -o v_compiled_with_vtcc vlang.c -lpthread
ls -la v_compiled_with_vtcc
show "Test the resulting V compiler"
./v_compiled_with_vtcc version
show "Compile and run hello with vtcc"
./v_compiled_with_vtcc -cc vtcc/vtcc -showcc run examples/hello_world.v
show "Remove the generated temporary files, so the script can be re-run cleanly"
rm -rf v_compiled_with_vtcc vlang.c vtcc/
fi
+29
View File
@@ -0,0 +1,29 @@
#!/usr/bin/env bash
set -e
function show() {
printf "\u001b[35m$1\u001b[0m\n"
}
rm -rf ~/.vmodules/gui/ ~/.vmodules/vglyph/
export VJOBS=1
show "Clone https://github.com/vlang/vglyph"
v retry -- git clone --filter=blob:none --quiet https://github.com/vlang/vglyph ~/.vmodules/vglyph/
show "Use latest vlang/vglyph commit"
git -C ~/.vmodules/vglyph/ log -1 --oneline
show "Clone https://github.com/vlang/gui"
v retry -- git clone --filter=blob:none --quiet https://github.com/vlang/gui ~/.vmodules/gui/
show "Use latest vlang/gui commit"
git -C ~/.vmodules/gui/ log -1 --oneline
if [[ "$(uname)" == 'Darwin' ]]; then
export VFLAGS="${VFLAGS:-} -cc clang"
fi
show "Check module for syntax and semantic errors"
v -shared -check ~/.vmodules/gui
show "Execute Tests"
v test ~/.vmodules/gui/
show "Compile Examples"
v should-compile-all -no-parallel ~/.vmodules/gui/examples/
rm -rf ~/.vmodules/gui/ ~/.vmodules/vglyph/
+140
View File
@@ -0,0 +1,140 @@
name: Cross CI
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/cross_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/cross_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: cross-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
cross-macos:
runs-on: macos-latest
timeout-minutes: 20
env:
VFLAGS: -cc clang
steps:
- uses: actions/checkout@v7
with:
fetch-depth: 10
- name: Cache Homebrew downloads
uses: actions/cache@v5
with:
path: ~/Library/Caches/Homebrew
key: brew-cross-macos-${{ hashFiles('.github/workflows/cross_ci.yml') }}
restore-keys: |
brew-cross-macos-
- name: Build V
run: make -j4 && ./v symlink
- name: Install dependencies
run: |
./v retry -- brew install mingw-w64
export LIBRARY_PATH="$LIBRARY_PATH:/usr/local/opt/openssl/lib/"
- name: Test symlink
run: ./v symlink
- name: Cross-compilation to Linux
run: |
./v -os linux cmd/v
# TODO: fix this: ./v -os linux examples/2048/2048.v
- name: Cross-compilation of veb app to Linux with -d use_openssl
run: ./v -d use_openssl -os linux examples/veb/veb_example.v
- name: Cross-compilation of vlang/gitly to Linux with -d use_openssl
run: |
./v retry -- ./v install markdown
./v retry -- ./v install pcre
./v retry -- git clone --depth 1 https://github.com/vlang/gitly /tmp/gitly
./v -d use_openssl -os linux /tmp/gitly
file /tmp/gitly/gitly
- name: Cross-compilation to Windows
run: |
./v -os windows cmd/v
./v -os windows examples/2048/2048.v
cross-linux:
runs-on: ubuntu-24.04
timeout-minutes: 20
env:
VFLAGS: -cc tcc -no-retry-compilation
steps:
- uses: actions/checkout@v7
with:
fetch-depth: 10
- uses: ./.github/actions/cache-apt-packages-action
- name: Build v
run: make -j4 && ./v symlink
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update -y -qq
./v retry -- sudo apt install --quiet -y mingw-w64 wine wine64 winetricks libssl-dev sqlite3 libsqlite3-dev
- name: Show diagnostics for wine
run: |
which wine
# shellcheck disable=SC2046
ls -la $(realpath $(which wine))
- name: v.c can be compiled and run with -os cross
run: |
./v -os cross -o /tmp/v.c cmd/v
gcc -g -std=gnu11 -w -o v_from_vc /tmp/v.c -lm -lpthread
ls -lart v_from_vc
./v_from_vc version
- name: v_win.c can be compiled and run with -os windows
run: |
./v -cc msvc -os windows -o /tmp/v_win.c cmd/v
x86_64-w64-mingw32-gcc /tmp/v_win.c -std=c99 -w -municode -o v_from_vc.exe -lws2_32 -Wl,-stack=33554432
ls -lart v_from_vc.exe
wine ./v_from_vc.exe version
- name: hello_world.v can be cross compiled to hello_world.exe
run: |
./v -os windows examples/hello_world.v
ls -lart examples/hello_world.exe
wine examples/hello_world.exe
- name: 2048.v can be cross compiled to 2048.exe
run: |
./v -os windows examples/2048/2048.v
ls -lart examples/2048/2048.exe
cross-windows:
runs-on: windows-2025
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Build
run: |
echo %VFLAGS%
echo $VFLAGS
.\makev.bat -msvc
- name: TODO v_win.c can be compiled and run with -os windows
run: |
.\v.exe -os windows -cc msvc -showcc -o v2.exe cmd\v
.\v.exe -os windows -cc msvc -o v_win.c cmd\v
dir v2.exe
dir v_win.c
.\v2.exe version
+117
View File
@@ -0,0 +1,117 @@
name: Database CI
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/db_ci.yml'
- 'examples/**'
- 'doc/**'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/db_ci.yml'
- 'examples/**'
- 'doc/**'
concurrency:
group: db-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
mysql-driver-tests:
runs-on: ubuntu-24.04
timeout-minutes: 30
services:
mysql:
image: mysql:8.0
env:
MYSQL_ROOT_PASSWORD: 12345678
MYSQL_ROOT_HOST: '%'
ports:
- 3306:3306
options: >-
--health-cmd="mysqladmin ping -h 127.0.0.1 -uroot -p12345678"
--health-interval=10s
--health-timeout=5s
--health-retries=24
steps:
- uses: actions/checkout@v7
- name: Build V
run: make -j4 && ./v symlink
- name: Install mysql client headers
run: |
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update
./v retry -- sudo apt install --quiet -y libmariadb-dev
- name: Run mysql driver tests
run: ./v -d network -d started_mysqld -silent test vlib/db/mysql/
postgres-driver-tests:
runs-on: ubuntu-24.04
timeout-minutes: 30
services:
postgres:
image: postgres:16
env:
POSTGRES_PASSWORD: 12345678
ports:
- 5432:5432
options: >-
--health-cmd="pg_isready -U postgres -d postgres"
--health-interval=10s
--health-timeout=5s
--health-retries=24
steps:
- uses: actions/checkout@v7
- name: Build V
run: make -j4 && ./v symlink
- name: Install postgres client headers
run: |
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update
./v retry -- sudo apt install --quiet -y libpq-dev
- name: Run postgres driver tests
run: ./v -d network -d started_postgres -silent test vlib/db/pg/
mssql-driver-tests:
runs-on: ubuntu-24.04
timeout-minutes: 30
services:
mssql:
image: mcr.microsoft.com/mssql/server:2022-latest
env:
ACCEPT_EULA: Y
MSSQL_PID: Developer
MSSQL_SA_PASSWORD: Vlang12345678!
ports:
- 1433:1433
steps:
- uses: actions/checkout@v7
- name: Build V
run: make -j4 && ./v symlink
- name: Install ODBC dependencies
run: |
.github/workflows/disable_azure_mirror.sh
[ -f /usr/share/keyrings/microsoft-prod.gpg ] || curl -fsSL https://packages.microsoft.com/keys/microsoft.asc | sudo gpg --batch --no-tty --dearmor -o /usr/share/keyrings/microsoft-prod.gpg
curl -fsSL https://packages.microsoft.com/config/ubuntu/24.04/prod.list | sudo tee /etc/apt/sources.list.d/mssql-release.list
./v retry -- sudo apt update
sudo ACCEPT_EULA=Y apt install --quiet -y msodbcsql18 unixodbc-dev
- name: Wait for sql server
run: |
for _ in $(seq 1 60); do
if (echo > /dev/tcp/127.0.0.1/1433) >/dev/null 2>&1; then
exit 0
fi
sleep 2
done
exit 1
- name: Run mssql driver tests
env:
VMSSQL_CONN_STR: 'Driver={ODBC Driver 18 for SQL Server};Server=127.0.0.1;Port=1433;UID=sa;PWD=Vlang12345678!;Database=master;TrustServerCertificate=yes'
run: ./v -d network -d started_mssql -silent test vlib/db/mssql/
+40
View File
@@ -0,0 +1,40 @@
name: Debug CI
on: [workflow_dispatch]
jobs:
debug-msvc:
runs-on: windows-2025
timeout-minutes: 121
env:
VFLAGS: -cc msvc
steps:
- uses: actions/checkout@v7
- name: Build
run: |
echo %VFLAGS%
echo $VFLAGS
.\makev.bat -msvc
.\v.exe -cflags /WX self
- name: Install dependencies
run: |
.\v.exe setup-freetype
.\.github\workflows\windows-install-sqlite.bat
- name: v doctor
run: ./v doctor
- name: Verify `v test` works
run: |
./v cmd/tools/test_if_v_test_system_works.v
./cmd/tools/test_if_v_test_system_works
- name: All code is formatted
run: ./v -silent test-cleancode
- name: Self tests
run: ./v -silent test-self
- name: Test v->js
run: ./v -o hi.js examples/js_hello_world.v && node hi.js
- name: Test v binaries
run: ./v build-vbinaries
- name: Build examples
run: ./v -silent build-examples
- name: v2 self compilation
run: .\v.exe -o v2.exe cmd/v && .\v2.exe -o v3.exe cmd/v
+17
View File
@@ -0,0 +1,17 @@
#!/bin/bash
echo "APT MIRRORS BEFORE:"; cat /etc/apt/apt-mirrors.txt
sudo sed -i 's@http://azure.archive.ubuntu.com@http://archive.ubuntu.com@gm' /etc/apt/apt-mirrors.txt
echo "APT MIRRORS AFTER:"; cat /etc/apt/apt-mirrors.txt
echo "ls -la /etc/apt/sources.list.d/"; ls -la /etc/apt/sources.list.d/
for f in /etc/apt/sources.list.d/*; do echo "####### $f ######"; cat $f; done
for f in /etc/apt/sources.list.d/azure-cli.*; do
if [ -f "$f" ]; then
echo "DISABLE OPTIONAL APT SOURCE: $f"
sudo mv "$f" "$f.disabled"
fi
done
echo "APT SOURCES BEFORE:"; echo "ls -la /etc/apt/sources.list"; ls -la /etc/apt/sources.list; cat /etc/apt/sources.list
sudo sed -i 's@http://azure.archive.ubuntu.com@http://archive.ubuntu.com@gm' /etc/apt/sources.list
echo "APT SOURCES AFTER:"; echo "ls -la /etc/apt/sources.list"; ls -la /etc/apt/sources.list; cat /etc/apt/sources.list
+102
View File
@@ -0,0 +1,102 @@
name: Docker CI
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/docker_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/docker_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: docker-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
env:
V_CI_MUSL: 1
jobs:
docker-alpine-musl-gcc:
runs-on: ubuntu-24.04
timeout-minutes: 241
container:
image: thevlang/vlang:alpine-build
env:
VFLAGS: -cc gcc
volumes:
- ${{github.workspace}}:/opt/vlang
steps:
- name: Checkout
uses: actions/checkout@v7
- name: Show Environment
run: |
echo "PWD:"
pwd
echo "ENVIRONMENT:"
env
echo "C Compiler:"
gcc --version
- name: Add dependencies
run: apk add libc6-compat gcompat gc gc-dev binutils diffutils elfutils
- name: Build V
run: CC=gcc make
- name: All code is formatted
run: ./v -silent test-cleancode
- name: Run only essential tests
run: VTEST_JUST_ESSENTIAL=1 ./v -silent test-self
docker-alpine-musl-tcc:
runs-on: ubuntu-24.04
timeout-minutes: 241
container:
image: thevlang/vlang:alpine-build
volumes:
- ${{github.workspace}}:/opt/vlang
steps:
- name: Checkout
uses: actions/checkout@v7
- name: Add dependencies
run: apk add musl-dev libatomic_ops-dev libatomic openssl libc6-compat gcompat gc gc-dev binutils diffutils elfutils
- name: Build V
run: make
- name: Check if vpm compiles with tcc
run: ./v -show-c-output -showcc -no-retry-compilation -cc tcc cmd/tools/vpm
- name: Run only builtin and math tests
run: ./v test vlib/builtin
docker-ubuntu-musl:
runs-on: ubuntu-24.04
timeout-minutes: 121
container:
image: thevlang/vlang:ubuntu-build
env:
V_CI_UBUNTU_MUSL: 1
VFLAGS: -cc musl-gcc -gc none
volumes:
- ${{github.workspace}}:/opt/vlang
steps:
- name: Checkout
uses: actions/checkout@v7
- name: Build V
run: echo "$VFLAGS" && make -j4 && ./v -cg -o v cmd/v
- name: Verify `v test` works
run: |
echo "$VFLAGS"
./v cmd/tools/test_if_v_test_system_works.v
./cmd/tools/test_if_v_test_system_works
- name: Add dependencies
run: apt install libsqlite3-dev
- name: All code is formatted
run: ./v -silent test-cleancode
- name: Test V fixed tests
run: ./v -silent test-self vlib
+86
View File
@@ -0,0 +1,86 @@
name: Docs CI
### Run on *EVERY* .v or .md related commit.
### The documentation *SHOULD* stay valid, and the developers should receive
### early warning, if they break it.
on:
push:
branches:
- master
paths-ignore:
- '**.yml'
- '!**/docs_ci.yml'
- 'cmd/tools/vrepl.v'
pull_request:
paths-ignore:
- '**.yml'
- '!**/docs_ci.yml'
- 'cmd/tools/vrepl.v'
concurrency:
group: docs-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
check-markdown:
runs-on: ubuntu-24.04
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make
- name: Install dependencies (some examples show how to use sqlite and the x11 clipboard)
run: ./v retry -- sudo apt install --quiet -y libx11-dev libssl-dev sqlite3 libsqlite3-dev
- name: Check markdown line length & code examples
run: ./v check-md -hide-warnings .
## NB: -hide-warnings is used here, so that the output is less noisy,
## thus real errors are easier to spot.
report-missing-fn-doc:
runs-on: ubuntu-24.04
timeout-minutes: 5
env:
MOPTIONS: --diff --deprecated --relative-paths --exclude /vlib/v/ --exclude /vlib/v2_toberemoved/ --exclude /builtin/linux_bare/ --exclude /testdata/ --exclude /tests/ --exclude /vlib/sokol/ --exclude /vlib/x/
steps:
- uses: actions/checkout@v7
- name: Build V
run: make
- name: Checkout previous v
uses: actions/checkout@v7
with:
repository: vlang/v
ref: master
path: pv
- name: Check against parent commit
run: |
# shellcheck disable=SC2086
./v missdoc $MOPTIONS pv/vlib vlib
report-missing-dots-in-doc-comments:
runs-on: ubuntu-24.04
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Build V
run: make
- name: Check doc comment dots for some key modules
run: ./v run cmd/tools/find_doc_comments_with_no_dots.v \
vlib/builtin/ vlib/arrays/ vlib/flag/ \
vlib/bitfield/ vlib/term/ vlib/strings/ \
vlib/rand/ vlib/compress/ vlib/clipboard/ \
vlib/time/ \
vlib/os
report-wrong-examples-in-doc-comments:
runs-on: ubuntu-24.04
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Build V
run: make
- name: Check examples in the doc comments for all vlib modules
run: VJOBS=1 ./v doc -check-examples -f none vlib/
+114
View File
@@ -0,0 +1,114 @@
name: docs.vlang.io deploy
### Regenerate https://docs.vlang.io/ (the GitHub Pages site served from the
### `main` branch of https://github.com/vlang/docs ), on every change to
### doc/docs.md that lands on master.
###
### Historically docs.vlang.io was updated by the FreeBSD machine that also runs
### cmd/tools/fast/fast.v . When that single machine stops, the site silently
### goes stale (see issue #27038, where it was stuck at the 2026-02-09 snapshot).
### Generating and deploying from CI removes that single point of failure, the
### same way modules.vlang.io is deployed from module_docs_ci.yml .
on:
workflow_dispatch:
push:
branches:
- master
paths:
- 'doc/docs.md'
- '**/docs_site_ci.yml'
# Allow only one concurrent deployment, skipping runs queued between the run in-progress and latest queued.
# However, do NOT cancel in-progress runs as we want to allow these production deployments to complete.
concurrency:
group: docs_site-${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: ${{ !contains(github.ref, 'master')}}
jobs:
deploy-docs-site:
runs-on: ubuntu-latest
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make -j4 && ./v symlink
- name: Install dependencies (the docs generator uses the markdown module)
run: ./v retry -- ./v install markdown
- name: Generate the HTML pages from doc/docs.md
run: |
set -e
# The generator (the `generator` branch of vlang/docs) fetches
# doc/docs.md from the master branch of vlang/v, transforms it into one
# HTML page per section, and writes them into its own output/ folder.
rm -rf docs_generator
./v retry -- git clone --depth=1 --branch generator https://github.com/vlang/docs docs_generator
./v run docs_generator/.
[ -f docs_generator/output/introduction.html ]
- name: Deploy to vlang/docs (main branch -> docs.vlang.io)
if: github.event_name != 'pull_request' && github.repository == 'vlang/v' && github.ref == 'refs/heads/master'
run: |
set -e
git config --global user.email "vlang-bot@users.noreply.github.com"
git config --global user.name "vlang-bot"
COMMIT_HASH="$(git rev-parse --short HEAD)"
COMMIT_MSG="$(git log -1 --pretty='%s' HEAD)"
rm -rf docs_site
./v retry -- git clone --depth=1 --branch main "https://vlang-bot:${{ secrets.VLANG_BOT_SECRET }}@github.com/vlang/docs.git" docs_site
# The legacy FreeBSD uploader (cmd/tools/fast/fast.v) may still be
# pushing to vlang/docs main too, so our push can be rejected as
# non-fast-forward. `v retry` would only rerun the same push, never
# fetching the new tip, so retry here by re-syncing onto the latest main
# and pushing again. The sync is idempotent, so re-applying it on top of
# whatever landed meanwhile is safe.
deploy_attempts=5
for attempt in $(seq 1 "${deploy_attempts}"); do
git -C docs_site fetch --depth=1 origin main
git -C docs_site reset --hard FETCH_HEAD
# Sync the freshly generated pages onto the published site. --delete so
# that pages/assets removed or renamed in doc/docs.md do not linger as
# stale files, but protect the site-only files at the repo root that the
# generator does not produce (git metadata, CNAME, .nojekyll, README.md,
# favicon.ico and the legacy build.vsh).
rsync -a --delete \
--exclude '/.git' \
--exclude '/.gitattributes' \
--exclude '/.gitignore' \
--exclude '/.nojekyll' \
--exclude '/CNAME' \
--exclude '/README.md' \
--exclude '/favicon.ico' \
--exclude '/build.vsh' \
docs_generator/output/ docs_site/
git -C docs_site add -A
# `git diff --cached --quiet` exits 0 with nothing staged, 1 when there
# are staged changes, and >1 on a real error - so only 1 means "deploy".
set +e
git -C docs_site diff --cached --quiet
diff_rc=$?
set -e
if [ "${diff_rc}" -eq 0 ]; then
echo "docs.vlang.io is already up to date for ${COMMIT_HASH}; nothing to deploy."
exit 0
elif [ "${diff_rc}" -ne 1 ]; then
echo "::error::git diff --cached failed with exit code ${diff_rc}" >&2
exit "${diff_rc}"
fi
git -C docs_site commit -m "update docs for commit ${COMMIT_HASH} - ${COMMIT_MSG}"
if git -C docs_site push origin main; then
echo "docs.vlang.io updated for ${COMMIT_HASH} (attempt ${attempt})."
exit 0
fi
echo "push to vlang/docs main was rejected (attempt ${attempt}/${deploy_attempts}); refetching and retrying..."
done
echo "::error::could not push to vlang/docs main after ${deploy_attempts} attempts" >&2
exit 1
@@ -0,0 +1,20 @@
#!/usr/bin/env bash
set -ex
rm -rf vlib/toml/tests/testdata/iarna vlib/toml/tests/testdata/toml_rs vlib/toml/tests/testdata/toml_lang vlib/toml/tests/testdata/large_toml_file_test.toml
./v retry -- ./v download -o vlib/toml/tests/testdata/large_toml_file_test.toml https://gist.githubusercontent.com/Larpon/89b0e3d94c6903851ff15559e5df7a05/raw/62a1f87a4e37bf157f2e0bfb32d85d840c98e422/large_toml_file_test.toml
./v retry -- git clone -n https://github.com/iarna/toml-spec-tests.git vlib/toml/tests/testdata/iarna
git -C vlib/toml/tests/testdata/iarna checkout 1880b1a
./v retry -- git clone -n https://github.com/toml-lang/toml-test.git vlib/toml/tests/testdata/toml_lang
git -C vlib/toml/tests/testdata/toml_lang checkout 229ce2e
# A few history notes of toml-rs (previously alexcrichton):
# commit 7f5472c the test-suite dir moves to the crates/ sub-directory
# commit 8461f7c *a lot* of test files are removed in *hope* that they are covered by the compliance test suite (assumed to be BurntSushi/toml-test, later toml-lang/toml-test)
# commit 9bd454c the last known good commit we can test against
./v retry -- git clone -n https://github.com/toml-rs/toml.git vlib/toml/tests/testdata/toml_rs
git -C vlib/toml/tests/testdata/toml_rs reset --hard 9bd454c
+10
View File
@@ -0,0 +1,10 @@
@echo off
setlocal EnableDelayedExpansion
REM Find every openssl.exe reachable through PATH:
for /f "delims=" %%F in ('where openssl 2^>nul') do (
set "OPENSSL_DIR=%%~dpF"
echo OpenSSL lives in: "!OPENSSL_DIR!"
goto :end
)
echo OpenSSL not found in: "!PATH!"
:end
+149
View File
@@ -0,0 +1,149 @@
name: CI FreeBSD
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- 'cmd/tools/**'
- '!**/freebsd_ci.yml'
- '!ci/freebsd_ci.vsh'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- 'cmd/tools/**'
- '!**/freebsd_ci.yml'
- '!ci/freebsd_ci.vsh'
- '!cmd/tools/builders/**.v'
### See https://github.com/cross-platform-actions/action
### for a description of the used fields here
jobs:
tcc-freebsd:
runs-on: ubuntu-latest
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Start FreeBSD VM for tcc
id: vm-freebsd-tcc
uses: cross-platform-actions/action@v1.2.0
with:
operating_system: freebsd
version: '15.0'
memory: 4G
shell: sh
sync_files: runner-to-vm
- name: Tests on FreeBSD with tcc
id: tests-freebsd-tcc
shell: cpa.sh {0}
run: |
sudo pkg install -y git sqlite3 gmake boehm-gc-threaded libiconv
# Install DB packages needed to build examples
sudo pkg install -y mariadb118-client postgresql18-client
# Install packages needed by Sokol to build examples
sudo pkg install -y alsa-lib libglvnd libXi libXcursor
# Mandatory: hostname not set in VM => some tests fail
sudo hostname -s freebsd-ci
echo "::group::OS infos"
uname -a
echo "::endgroup::"
echo "::group::Build V"
git config --global --add safe.directory .
gmake
sudo ./v symlink
export VTEST_SHOW_LONGEST_BY_RUNTIME=3
export VTEST_SHOW_LONGEST_BY_COMPTIME=3
export VTEST_SHOW_LONGEST_BY_TOTALTIME=3
export VFLAGS='-cc tcc -no-retry-compilation'
echo "::endgroup::"
./v run ci/freebsd_ci.vsh all
clang-freebsd:
runs-on: ubuntu-latest
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Start FreeBSD VM for clang
id: vm-freebsd-clang
uses: cross-platform-actions/action@v1.2.0
with:
operating_system: freebsd
version: '15.0'
memory: 4G
shell: sh
sync_files: runner-to-vm
- name: Tests on FreeBSD with clang
id: tests-freebsd-clang
shell: cpa.sh {0}
run: |
sudo pkg install -y git sqlite3 gmake boehm-gc-threaded libiconv
# Install DB packages needed to build examples
sudo pkg install -y mariadb118-client postgresql18-client
# Install packages needed by Sokol to build examples
sudo pkg install -y alsa-lib libglvnd libXi libXcursor
# Mandatory: hostname not set in VM => some tests fail
sudo hostname -s freebsd-ci
echo "::group::OS infos"
uname -a
echo "::endgroup::"
echo "::group::Build V"
git config --global --add safe.directory .
gmake
sudo ./v symlink
export VTEST_SHOW_LONGEST_BY_RUNTIME=3
export VTEST_SHOW_LONGEST_BY_COMPTIME=3
export VTEST_SHOW_LONGEST_BY_TOTALTIME=3
export VFLAGS='-cc clang'
echo "::endgroup::"
./v run ci/freebsd_ci.vsh all
gcc-freebsd:
runs-on: ubuntu-latest
timeout-minutes: 30
steps:
- uses: actions/checkout@v7
- name: Start FreeBSD VM for gcc
id: vm-freebsd-gcc
uses: cross-platform-actions/action@v1.2.0
with:
operating_system: freebsd
version: '15.0'
memory: 4G
shell: sh
sync_files: runner-to-vm
- name: Tests on FreeBSD with gcc
id: tests-freebsd-gcc
shell: cpa.sh {0}
run: |
sudo pkg install -y git sqlite3 gmake boehm-gc-threaded libiconv gcc
# Install DB packages needed to build examples
sudo pkg install -y mariadb118-client postgresql18-client
# Install packages needed by Sokol to build examples
sudo pkg install -y alsa-lib libglvnd libXi libXcursor
# Mandatory: hostname not set in VM => some tests fail
sudo hostname -s freebsd-ci
echo "::group::OS infos"
uname -a
echo "::endgroup::"
echo "::group::Build V"
git config --global --add safe.directory .
gmake
sudo ./v symlink
export VTEST_SHOW_LONGEST_BY_RUNTIME=3
export VTEST_SHOW_LONGEST_BY_COMPTIME=3
export VTEST_SHOW_LONGEST_BY_TOTALTIME=3
export VFLAGS='-cc gcc'
echo "::endgroup::"
./v run ci/freebsd_ci.vsh all
+75
View File
@@ -0,0 +1,75 @@
name: VC gen
on:
workflow_dispatch:
pull_request:
paths-ignore:
- '**.vv'
- '**.out'
- '**.md'
- '**.yml'
- '!**/gen_vc_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
push:
branches:
- master
paths-ignore:
- '**.vv'
- '**.out'
- '**.md'
- '**.yml'
- '!**/gen_vc_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
# Allow only one concurrent deployment, skipping runs queued between the run in-progress and latest queued.
# However, do NOT cancel in-progress runs as we want to allow these production deployments to complete.
concurrency:
group: gen_vc-${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: ${{ !contains(github.ref, 'master')}}
jobs:
build-vc:
runs-on: ubuntu-latest
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Build V
run: make -j4
- name: Regenerate v.c and v_win.c
run: |
git config --global user.email "vlang-bot@users.noreply.github.com"
git config --global user.name "vlang-bot"
COMMIT_HASH="$(git rev-parse HEAD)"
COMMIT_MSG="$(git log -1 --oneline --pretty='%s' HEAD)"
rm -rf vc
./v retry -- git clone --depth=1 "https://vlang-bot:${{ secrets.VLANG_BOT_SECRET }}@github.com/vlang/vc.git"
rm -rf vc/v.c vc/v_win.c
./v -o vc/v.c -cross cmd/v
./v -o vc/v_win.c -os windows -cc msvc cmd/v
sed -i "1s/^/#define V_COMMIT_HASH \"$COMMIT_HASH\"\n/" vc/v.c
sed -i "1s/^/#define V_COMMIT_HASH \"$COMMIT_HASH\"\n/" vc/v_win.c
# do some sanity checks for the generated v.c file:
grep 'Turned ON custom defines: no_backtrace,cross' vc/v.c
grep '#define CUSTOM_DEFINE_cross' vc/v.c
# ensure the generated C files for the compiler, are over 5000 lines long, as a safety measure
[ "$(wc -l < vc/v.c)" -gt 5000 ]
[ "$(wc -l < vc/v_win.c)" -gt 5000 ]
git -C vc add v.c v_win.c
git -C vc commit -m "[v:master] $COMMIT_HASH - $COMMIT_MSG"
# in case there are recent commits:
./v retry -- git -C vc pull --rebase origin master
git -C vc log -3
- name: Deploy
if: github.event_name == 'push' && github.repository == 'vlang/v' && github.ref == 'refs/heads/master'
run: git -C vc push || true
+74
View File
@@ -0,0 +1,74 @@
name: Graphics CI
on:
push:
branches:
- master
paths:
- 'vlib/**'
- 'thirdparty/**'
- 'cmd/tools/builders/**.v'
- '**/gg_regressions_ci.yml'
- '!**.md'
pull_request:
paths:
- 'vlib/**'
- 'thirdparty/**'
- 'cmd/tools/builders/**.v'
- '**/gg_regressions_ci.yml'
- '!**.md'
concurrency:
group: gg-regressions-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
gg-regressions:
runs-on: ubuntu-24.04
timeout-minutes: 20
env:
VFLAGS: -cc tcc
DISPLAY: :99
LIBGL_ALWAYS_SOFTWARE: true
VTMP: /tmp
steps:
- name: Checkout V
uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build local v
run: make -j4 && ./v symlink
- name: Clear module cache
run: ./v wipe-cache
- name: Setup dependencies
run: |
# imagemagick : convert, mogrify
# xvfb : xvfb
# openimageio-tools : idiff
# libxcursor-dev libxi-dev : V gfx deps
# libgl1-mesa-dri : For headless rendering / software DRI driver (LIBGL_ALWAYS_SOFTWARE=true)
# freeglut3-dev : Fixes graphic apps compilation with tcc
# libx11-dev : X11 headers for clipboard and sokol (default backend on Linux)
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update
./v retry -- sudo apt install imagemagick openimageio-tools libgl1-mesa-dri xvfb libxcursor-dev libxi-dev libxrandr-dev freeglut3-dev xsel xclip libx11-dev libegl-dev
./v retry -- ./v download https://raw.githubusercontent.com/tremby/imgur.sh/c98345d/imgur.sh
./v retry -- git clone https://github.com/Larpon/gg-regression-images gg-regression-images
chmod +x ./imgur.sh
- name: Sample and compare
id: compare
continue-on-error: true
run: |
Xvfb "$DISPLAY" -screen 0 1280x1024x24 -fbdir /var/tmp/ &
sleep 2; while [ ! -f /var/tmp/Xvfb_screen0 ]; do sleep 0.5; done # give xvfb time to start, even on slow CI runs
sleep 5; ./v gret -t ./gg-regression-images/vgret.v_examples.toml -v ./gg-sample_images ./gg-regression-images
- name: Upload regression to imgur
if: steps.compare.outcome != 'success'
run: |
./imgur.sh /tmp/fail.png
./imgur.sh /tmp/diff.png
exit 1
+184
View File
@@ -0,0 +1,184 @@
import os
import json
import term
import time
const c = term.colorize
const tg = term.green
const tm = term.magenta
const tb = term.bold
struct Check {
name string
bucket string
state string
link string
workflow string
}
fn (c Check) is_failed() bool {
return c.bucket == 'fail' || c.state in ['FAILURE', 'TIMED_OUT']
}
fn (c Check) is_cancelled() bool {
return c.bucket == 'cancel' || c.state == 'CANCELLED'
}
struct GhCheckRun {
name string
status string
conclusion string
html_url string @[json: html_url]
}
struct GhCheckRunsResponse {
check_runs []GhCheckRun @[json: check_runs]
}
fn main() {
unbuffer_stdout()
arg := os.args[1] or {
println('Usage: v run gh_restart_failed.v <PR_NUMBER|REF>')
return
}
is_pr := arg.len < 6 && arg.bytes().all(it.is_digit())
checks := if is_pr { get_checks_for_pr(arg.int()) } else { get_checks_for_commit(arg) }
mut failed := []Check{}
mut cancelled := []Check{}
mut succeeded := 0
mut in_progress := 0
for check in checks {
if check.is_failed() {
failed << check
} else if check.is_cancelled() {
cancelled << check
} else if check.bucket == 'pass' || check.state == 'SUCCESS' {
succeeded++
} else {
in_progress++
}
}
mut to_restart := []Check{}
to_restart << failed
to_restart << cancelled
mut restarted_count := 0
if to_restart.len > 0 {
println('Found ${to_restart.len} failed or cancelled jobs:')
for job in to_restart {
println('- ${job.workflow} / ${job.name} (${job.state})')
}
println('\n' + c(tg, 'Do you want to restart these ${to_restart.len} jobs? [y/N]: '))
if os.input('').to_lower().trim_space() == 'y' {
println('')
for job in to_restart {
run_id, job_id := parse_ids(job.link)
if run_id == '' || job_id == '' {
println('Could not parse IDs from link: ${job.link} (Skipping)')
continue
}
print('Restarting ${job.name} (Run: ${run_id}, Job: ${job_id})... ')
res := execute_with_progress('gh run rerun ${run_id} --job ${job_id}')
if res.exit_code == 0 {
restarted_count++
} else {
println(' Error: ${res.output.trim_space()}')
}
}
} else {
println('Aborted restart.')
}
} else {
println('No failed or cancelled jobs found.')
}
println('\n' + c(tg, 'Summary:'))
println('Total jobs: ${m(checks.len)}')
println('Failed: ${m(failed.len)}')
println('Cancelled: ${m(cancelled.len)}')
println('Succeeded: ${m(succeeded)}')
println('In Progress: ${m(in_progress)}')
println('Restarted: ${m(restarted_count)}')
}
fn m(n int) string {
return c(tb, n.str())
}
fn parse_ids(link string) (string, string) {
parts := link.split('/')
runs_idx := parts.index('runs')
job_idx := parts.index('job')
mut run_id := ''
mut job_id := ''
if runs_idx != -1 && runs_idx + 1 < parts.len {
run_id = parts[runs_idx + 1]
}
if job_idx != -1 && job_idx + 1 < parts.len {
job_id = parts[job_idx + 1]
}
return run_id, job_id
}
fn get_checks_for_pr(pr_number int) []Check {
println(c(tg, 'Fetching checks for PR ${m(pr_number)}...'))
res := execute_with_progress('gh pr checks ${pr_number} --json name,bucket,state,link,workflow')
if res.exit_code != 0 {
println('Error: ${res.output}')
exit(1)
}
return json.decode([]Check, res.output) or { exit(1) }
}
fn get_checks_for_commit(commit string) []Check {
println(c(tg, 'Fetching checks for ref ${c(tb, commit)}...'))
res := execute_with_progress('gh api repos/:owner/:repo/commits/${commit}/check-runs?per_page=100')
if res.exit_code != 0 {
println('Error: ${res.output}')
exit(1)
}
resp := json.decode(GhCheckRunsResponse, res.output) or { exit(1) }
mut checks := []Check{}
for cr in resp.check_runs {
checks << Check{
name: cr.name
bucket: if cr.conclusion == 'failure' {
'fail'
} else if cr.conclusion == 'cancelled' {
'cancel'
} else if cr.conclusion == 'success' {
'pass'
} else {
'pending'
}
state: if cr.conclusion != '' {
cr.conclusion.to_upper()
} else {
cr.status.to_upper()
}
link: cr.html_url
workflow: 'Actions'
}
}
return checks
}
fn execute_with_progress(cmd string) os.Result {
start := time.now()
mut stop := false
spawn fn (cmd string, start time.Time, mut stop &bool) {
start_str := start.hhmmss()
for !*stop {
elapsed := time.since(start).seconds()
print('\rRunning ${c(tm, cmd)} [${start_str}] ... ${elapsed:.1f}s')
os.flush()
time.sleep(100 * time.millisecond)
}
}(cmd, start, mut &stop)
res := os.execute(cmd)
elapsed := time.since(start).seconds()
stop = true
time.sleep(100 * time.millisecond)
status := if res.exit_code == 0 { 'OK' } else { 'Failed' }
print('\r')
println('Command ${c(tm, cmd)} done in ${elapsed:.1f}s. ${status}')
return res
}
+80
View File
@@ -0,0 +1,80 @@
name: hub_docker_ci
### NB: avoid caching things here, since the action is rare (once per week),
### and the potential benefits are less than the complexity of debugging
### cache invalidation issues...
## Trigger on both new release tags, and on weekly tags.
## Allow for manual override too:
on:
workflow_dispatch:
push:
tags:
- '[0-9].[0-9]+.[0-9]+'
- 'weekly.*'
concurrency:
group: 'hub_docker_ci-${{ github.ref }}'
cancel-in-progress: true
jobs:
publish-new-docker-images:
strategy:
matrix:
os: [debian, alpine]
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v7
with:
repository: 'vlang/docker'
- name: Set up QEMU
uses: docker/setup-qemu-action@v4
- name: Set up Docker Buildx
uses: docker/setup-buildx-action@v4
- name: Login to hub.docker.com
uses: docker/login-action@v4
with:
username: ${{ secrets.DOCKER_USERNAME }}
password: ${{ secrets.DOCKER_PASSWORD }}
- name: Create & bootstrap persistent builder
run: |
docker buildx create --name gh-builder --driver docker-container --use
docker buildx inspect --bootstrap
- name: generate tags conditionally
id: gen_tags
run: |
if [[ "${{ matrix.os }}" == 'debian' ]]; then
echo 'TAGS=thevlang/vlang:latest,thevlang/vlang:${{ matrix.os }}' >> "$GITHUB_OUTPUT"
else
echo 'TAGS=thevlang/vlang:${{ matrix.os }}' >> "$GITHUB_OUTPUT"
fi
- uses: docker/build-push-action@v7
name: Build and deploy v image
with:
builder: gh-builder
context: .
platforms: linux/amd64,linux/arm64
tags: ${{ steps.gen_tags.outputs.TAGS }}
file: docker/vlang/Dockerfile.${{ matrix.os }}
push: true
build-args: 'USER=thevlang'
## cache-from: type=registry,ref=thevlang/vlang:${{ matrix.os }}-buildcache
## cache-to: type=registry,ref=thevlang/vlang:${{ matrix.os }}-buildcache,mode=max
- uses: docker/build-push-action@v7
name: Build and deploy developer build
with:
builder: gh-builder
context: .
platforms: linux/amd64,linux/arm64
tags: thevlang/vlang:${{ matrix.os }}-dev
file: docker/vlang/Dockerfile.${{ matrix.os }}.dev-full
push: true
build-args: 'USER=thevlang'
## cache-from: type=registry,ref=thevlang/vlang:${{ matrix.os }}-dev-buildcache
## cache-to: type=registry,ref=thevlang/vlang:${{ matrix.os }}-dev-buildcache,mode=max
+575
View File
@@ -0,0 +1,575 @@
name: CI Linux
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/linux_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/linux_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: linux-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
tcc-linux:
runs-on: ubuntu-24.04
timeout-minutes: 121
env:
VFLAGS: -cc tcc -no-retry-compilation
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build v
run: make -j4 && ./v symlink
- name: Build v with -prealloc
run: v run ci/linux_ci.vsh build_v_with_prealloc
- name: All code is formatted
run: v run ci/linux_ci.vsh all_code_is_formatted_tcc
- name: Install dependencies for examples and tools
run: v run ci/linux_ci.vsh install_dependencies_for_examples_and_tools_tcc
- name: Test v->c
run: v run ci/linux_ci.vsh test_v_to_c_tcc
- name: v self compilation
run: v run ci/linux_ci.vsh v_self_compilation_tcc
- name: v doctor
run: v run ci/linux_ci.vsh v_doctor_tcc
- name: Verify `v test` works
run: v run ci/linux_ci.vsh verify_v_test_works_tcc
- name: Test pure V math module
run: v run ci/linux_ci.vsh test_pure_v_math_module_tcc
- name: Test inline assembly on linux
run: v run ci/linux_ci.vsh test_inline_assembly
- name: Self tests
run: v run ci/linux_ci.vsh self_tests_tcc
- name: Build examples
run: v run ci/linux_ci.vsh build_examples_tcc
- name: Run the submodule example, using a relative path
run: v run ci/linux_ci.vsh run_submodule_example_tcc
- name: Build v tools
run: v run ci/linux_ci.vsh build_tools_tcc
- name: Build v binaries
run: v run ci/linux_ci.vsh build_vbinaries_tcc
- name: Build benches
run: v run ci/linux_ci.vsh build_benches_tcc
- name: Run a VSH script
run: v run ci/linux_ci.vsh run_vsh_script_tcc
- name: Test v tutorials
run: v run ci/linux_ci.vsh test_v_tutorials_tcc
- name: Build cmd/tools/fast
run: v run ci/linux_ci.vsh build_fast_tcc
- name: V self compilation with -usecache
run: v run ci/linux_ci.vsh v_self_compilation_usecache_tcc
- name: Test password input
run: v run ci/linux_ci.vsh test_password_input_tcc
- name: Test readline
run: v run ci/linux_ci.vsh test_readline_tcc
- name: Test leak detector
run: v run ci/linux_ci.vsh test_leak_detector_tcc
- name: Test leak detector not being active for normal compile
run: v run ci/linux_ci.vsh test_leak_detector_not_active_tcc
gcc-linux:
runs-on: ubuntu-24.04
timeout-minutes: 121
env:
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make -j4 && ./v symlink
- name: backend x64 regressions
if: ${{ false }} # Temporarily disabled.
run: |
set -e
VJOBS=1 ./v test \
vlib/v2_toberemoved/abi \
vlib/v2_toberemoved/gen/x64/x64_abi_test.v \
vlib/v2_toberemoved/gen/x64/x64_backend_diagnostics_test.v \
vlib/v2_toberemoved/gen/x64/x64_object_format_test.v \
vlib/v2_toberemoved/gen/x64/x64_pe_linker_test.v \
vlib/v2_toberemoved/ssa/tree_sumtype_lowering_test.v
VJOBS=1 ./v test -run-only test_module_qualified_alias_array_field_index_has_alias_element_type,test_module_storage_legacy_direct_import_nested_module_selector_uses_declared_leaf_module,test_module_storage_flat_direct_import_nested_module_selector_uses_declared_leaf_module vlib/v2_toberemoved/ssa/module_storage_test.v
VJOBS=1 ./v test -run-only test_x64_linux_math_log_20_stdout_exact_bytes,test_x64_linux_generic_sumtype_direct_wrap_stdout_exact_bytes,test_x64_linux_generic_sumtype_repeated_base_specialization_stdout_exact_bytes,test_x64_linux_generic_sumtype_receiver_size_stdout_exact_bytes,test_x64_linux_generic_sumtype_insert_size_stdout_exact_bytes,test_x64_linux_struct_float_fields_stdout_exact_bytes,test_x64_linux_union_f64_bits_stdout_exact_bytes,test_x64_linux_f64_str_interpolation_stdout_exact_bytes,test_x64_linux_f64_for_interpolation_stdout_exact_bytes,test_x64_linux_formatted_int_interpolation_stdout_exact_bytes,test_x64_linux_formatted_int_width_100_interpolation_stdout_exact_bytes,test_x64_linux_formatted_f64_interpolation_stdout_exact_bytes,test_x64_linux_formatted_string_return_lifetime_stdout_exact_bytes,test_x64_linux_spectral_reduced_formatted_stdout_exact_bytes,test_x64_linux_bits_len32_stdout_exact_bytes,test_x64_linux_rand_u32n_interface_result_stdout_exact_bytes,test_x64_linux_rand_intn_range_interface_result_stdout_exact_bytes,test_x64_linux_textscanner_embedded_parser_stdout_exact_bytes,test_x64_linux_struct_positional_side_effect_stdout_exact_bytes,test_x64_linux_struct_named_side_effect_stdout_exact_bytes,test_x64_linux_unrelated_same_shape_struct_stdout_exact_bytes,test_x64_linux_named_init_embedded_value_stdout_exact_bytes,test_x64_linux_get_raw_line_example_stdin_stdout_exact_bytes,test_x64_linux_mini_calculator_example_stdin_stdout_exact_bytes,test_x64_linux_mini_calculator_recursive_descent_example_stdin_stdout_exact_bytes,test_x64_linux_external_c_flag_source_uses_hosted_link_with_compile_flags vlib/v2_toberemoved/gen/x64/x64_runtime_smoke_test.v
VJOBS=1 ./v test -run-only test_non_generic_concrete_sumtype_return_wraps_variant,test_option_concrete_sumtype_return_wraps_variant,test_generic_sumtype_declared_param_order_is_preserved_for_crossed_variants,test_worker_clone_sees_sumtype_decl_variant_cache,test_sumtype_decl_variant_cache_records_concrete_generic_variants_only,test_generic_sumtype_match_uses_full_specialization_when_generic_base_repeats,test_flat_direct_generic_sumtype_match_uses_full_specialization_when_generic_base_repeats,test_generic_sumtype_match_smartcast_scans_full_specialization_body,test_flat_direct_generic_sumtype_match_smartcast_scans_full_specialization_body,test_nested_module_concrete_generic_sumtype_base_does_not_fall_back_to_local_tree,test_leaf_module_concrete_generic_sumtype_base_fallback_beats_parent_module_tree vlib/v2_toberemoved/transformer/monomorphize_test.v
./v test vlib/v2_toberemoved/builder/native_test.v vlib/v2_toberemoved/builder/target_os_test.v
./v test vlib/v2_toberemoved/ssa/optimize
V2_VERIFY_STRICT=1 ./v test vlib/v2_toberemoved/ssa/optimize
- name: backend x64 examples
if: ${{ false }} # Temporarily disabled.
run: |
set -e
tmp="$(mktemp -d)"
trap 'rm -rf "$tmp"' EXIT
check_empty_stderr() {
label="$1"
stderr="$2"
if [ -s "$stderr" ]; then
echo "::error::$label wrote to stderr"
cat "$stderr"
return 1
fi
}
check_stdout() {
label="$1"
expected="$2"
actual="$3"
if ! cmp -s "$expected" "$actual"; then
echo "::error::$label stdout mismatch"
echo "expected:"
cat "$expected"
echo "actual:"
cat "$actual"
return 1
fi
}
run_native_x64_example() {
source="$1"
name="$2"
expected="$3"
shift 3
./v -v2 -no-parallel -b x64 "$source" -o "$tmp/$name"
"$tmp/$name" "$@" > "$tmp/$name.out" 2> "$tmp/$name.err"
check_empty_stderr "$name" "$tmp/$name.err"
check_stdout "$name" "$expected" "$tmp/$name.out"
}
run_native_x64_example_with_stdin() {
source="$1"
name="$2"
input="$3"
expected="$4"
shift 4
./v -v2 -no-parallel -b x64 "$source" -o "$tmp/$name"
"$tmp/$name" "$@" < "$input" > "$tmp/$name.out" 2> "$tmp/$name.err"
check_empty_stderr "$name" "$tmp/$name.err"
check_stdout "$name" "$expected" "$tmp/$name.out"
}
run_native_x64_example_capture() {
source="$1"
name="$2"
shift 2
./v -v2 -no-parallel -b x64 "$source" -o "$tmp/$name"
"$tmp/$name" "$@" > "$tmp/$name.out" 2> "$tmp/$name.err"
check_empty_stderr "$name" "$tmp/$name.err"
}
check_random_ips_stdout() {
label="$1"
actual="$2"
python3 - "$label" "$actual" <<'PY'
import sys
label = sys.argv[1]
path = sys.argv[2]
lines = open(path, "r", encoding="utf-8").read().splitlines()
if len(lines) != 10:
raise SystemExit(f"{label}: expected 10 lines, got {len(lines)}")
rows = []
for line in lines:
parts = line.split(".")
if len(parts) != 4:
raise SystemExit(f"{label}: invalid IPv4 shape: {line!r}")
row = []
for part in parts:
if not part.isdigit():
raise SystemExit(f"{label}: non-numeric octet in {line!r}")
value = int(part)
if value < 0 or value > 254:
raise SystemExit(f"{label}: octet out of range in {line!r}")
row.append(value)
rows.append(tuple(row))
if len(set(rows)) < 3:
raise SystemExit(f"{label}: output has too little row diversity")
if all(row[1] == 0 for row in rows) and all(row[3] == 0 for row in rows):
raise SystemExit(f"{label}: suspicious old x.0.x.0 pattern")
PY
}
check_rule110_stdout() {
label="$1"
actual="$2"
width="$3"
python3 - "$label" "$actual" "$width" <<'PY'
import sys
label = sys.argv[1]
path = sys.argv[2]
width = int(sys.argv[3])
lines = open(path, "r", encoding="utf-8").read().splitlines()
title = "Rule 110 V Implementation"
title_lines = [idx for idx, line in enumerate(lines) if title in line]
if not title_lines:
raise SystemExit(f"{label}: missing title")
idx = title_lines[0]
generations = lines[idx + 1:]
if generations and generations[0] == "":
generations = generations[1:]
if len(generations) != width:
raise SystemExit(f"{label}: expected {width} generation lines, got {len(generations)}")
for line in generations:
if len(line) != width:
raise SystemExit(f"{label}: generation line has width {len(line)}, expected {width}: {line!r}")
if any(ch not in " *" for ch in line):
raise SystemExit(f"{label}: invalid generation chars: {line!r}")
if not any("*" in line for line in generations):
raise SystemExit(f"{label}: expected at least one live cell")
if len(set(generations)) < 3:
raise SystemExit(f"{label}: expected at least 3 distinct generation lines")
PY
}
write_v_run_expected() {
source="$1"
expected="$2"
shift 2
stderr="$tmp/$(basename "$expected").stderr"
./v run "$source" "$@" > "$expected" 2> "$stderr"
check_empty_stderr "v run $source $*" "$stderr"
}
write_v_run_expected_with_stdin() {
source="$1"
input="$2"
expected="$3"
shift 3
stderr="$tmp/$(basename "$expected").stderr"
./v run "$source" "$@" < "$input" > "$expected" 2> "$stderr"
check_empty_stderr "v run $source $*" "$stderr"
}
write_fizz_buzz_expected() {
i=1
while [ "$i" -le 100 ]; do
if [ $((i % 15)) -eq 0 ]; then
echo FizzBuzz
elif [ $((i % 3)) -eq 0 ]; then
echo Fizz
elif [ $((i % 5)) -eq 0 ]; then
echo Buzz
else
echo "$i"
fi
i=$((i + 1))
done
}
write_hanoi_expected() {
python3 - <<'PY'
def hanoi(n, a, b, c):
if n == 1:
print(f"Disc 1 from {a} to {c}...")
else:
hanoi(n - 1, a, c, b)
print(f"Disc {n} from {a} to {c}...")
hanoi(n - 1, b, a, c)
hanoi(7, "A", "B", "C")
PY
}
write_sudoku_expected() {
python3 - <<'PY'
import sys
puzzle = [
[0, 3, 0, 0, 7, 0, 0, 0, 0],
[0, 0, 0, 1, 3, 5, 0, 0, 0],
[0, 0, 1, 0, 0, 0, 0, 5, 0],
[1, 0, 0, 0, 6, 0, 0, 0, 3],
[4, 0, 0, 8, 0, 3, 0, 0, 1],
[7, 0, 0, 0, 2, 0, 0, 0, 6],
[0, 0, 0, 0, 0, 0, 2, 1, 0],
[0, 0, 0, 4, 1, 2, 0, 0, 5],
[0, 0, 0, 0, 0, 0, 0, 7, 4],
]
solution = [
[2, 3, 5, 6, 7, 8, 1, 4, 9],
[9, 4, 7, 1, 3, 5, 8, 6, 2],
[6, 8, 1, 2, 4, 9, 3, 5, 7],
[1, 2, 8, 7, 6, 4, 5, 9, 3],
[4, 5, 6, 8, 9, 3, 7, 2, 1],
[7, 9, 3, 5, 2, 1, 4, 8, 6],
[3, 6, 4, 9, 5, 7, 2, 1, 8],
[8, 7, 9, 4, 1, 2, 6, 3, 5],
[5, 1, 2, 3, 8, 6, 9, 7, 4],
]
def append_grid(lines, label, grid):
lines.append(label)
for i, row in enumerate(grid):
if i % 3 == 0 and i != 0:
lines.append("- - - - - - - - - - - -")
line = ""
for j, value in enumerate(row):
if j % 3 == 0 and j != 0:
line += " | "
line += f"{value} "
lines.append(line)
lines = []
append_grid(lines, "Sudoku Puzzle:", puzzle)
lines.append("Solving...")
append_grid(lines, "Solution:", solution)
out = ("\n".join(lines) + "\n").encode()
if len(out) != 582:
raise SystemExit(f"sudoku stdout oracle shape changed: {len(out)} bytes")
sys.stdout.buffer.write(out)
PY
}
write_tree_of_nodes_expected() {
cat <<'EOF'
tree structure:
Node{
value: 10
left: Tree(Node{
value: 30
left: Tree(Empty{})
right: Tree(Empty{})
})
right: Tree(Node{
value: 20
left: Tree(Empty{})
right: Tree(Empty{})
})
}
tree size: 3
EOF
}
write_js_hello_world_expected() {
printf 'Hello from V.js (0)\nHello from V.js (1)\nHello from V.js (2)\n'
}
write_vascii_expected() {
python3 - <<'PY'
from pathlib import Path
import sys
source = Path("examples/vascii.v").read_text(encoding="utf-8")
start_marker = "println('"
end_marker = "')"
if source.count(start_marker) != 1:
raise SystemExit("vascii stdout oracle expects one single-quoted println literal")
start = source.index(start_marker) + len(start_marker)
end = source.rindex(end_marker)
if source[end + len(end_marker):].strip() != "}":
raise SystemExit("vascii stdout oracle expects the println literal to be the final main statement")
out = bytearray()
literal = source[start:end]
i = 0
while i < len(literal):
ch = literal[i]
if ch == "\\":
i += 1
if i >= len(literal):
raise SystemExit("unterminated escape in vascii literal")
escaped = literal[i]
if escaped == "n":
out.append(10)
elif escaped == "t":
out.append(9)
elif escaped == "r":
out.append(13)
elif escaped == "\\":
out.append(92)
elif escaped == "'":
out.append(39)
elif escaped == '"':
out.append(34)
else:
out.extend(escaped.encode("utf-8"))
else:
out.extend(ch.encode("utf-8"))
i += 1
out.append(10)
sys.stdout.buffer.write(out)
PY
}
write_rune_expected() {
printf '\360\237\230\200\n@\n'
}
printf 'Hello, World!\n' > "$tmp/hello_world.expected"
write_fizz_buzz_expected > "$tmp/fizz_buzz.expected"
write_hanoi_expected > "$tmp/hanoi.expected"
write_sudoku_expected > "$tmp/sudoku.expected"
printf 'HELLO WORLD\nHELLO WORLD\nHELLO WORLD\n' > "$tmp/function_types.expected"
printf '5\n3\n' > "$tmp/submodule.expected"
printf '1\n1\n2\n3\n5\n8\n13\n21\n34\n55\n89\n' > "$tmp/fibonacci_10.expected"
printf '120\n' > "$tmp/dump_factorial.expected"
write_v_run_expected examples/primes.v "$tmp/primes_20.expected" 20
write_tree_of_nodes_expected > "$tmp/tree_of_nodes.expected"
write_js_hello_world_expected > "$tmp/js_hello_world.expected"
write_vascii_expected > "$tmp/vascii.expected"
write_rune_expected > "$tmp/rune.expected"
write_v_run_expected examples/graphs/bfs.v "$tmp/bfs.expected"
write_v_run_expected examples/graphs/bfs3.v "$tmp/bfs3.expected"
write_v_run_expected examples/graphs/dfs.v "$tmp/dfs.expected"
write_v_run_expected examples/graphs/dijkstra.v "$tmp/dijkstra.expected"
write_v_run_expected examples/graphs/topological_sorting_greedy.v "$tmp/topological_sorting_greedy.expected"
write_v_run_expected examples/graphs/topological_sorting_dfs.v "$tmp/topological_sorting_dfs.expected"
write_v_run_expected examples/graphs/dfs2.v "$tmp/dfs2.expected"
write_v_run_expected examples/graphs/minimal_spann_tree_prim.v "$tmp/minimal_spann_tree_prim.expected"
write_v_run_expected examples/graphs/bellman-ford.v "$tmp/bellman_ford.expected"
write_v_run_expected examples/binary_search_tree.v "$tmp/binary_search_tree.expected"
printf 'wrong format\nempty input\n' > "$tmp/errors.expected"
write_v_run_expected examples/custom_error.v "$tmp/custom_error.expected"
write_v_run_expected examples/spectral.v "$tmp/spectral_10.expected" 10
printf 'length of random array is 1000\nbefore quick sort whether array is sorted: false\nafter quick sort whether array is sorted: true\n' > "$tmp/quick_sort.expected"
printf 'hello\nworld\n' > "$tmp/get_raw_line.in"
write_v_run_expected_with_stdin examples/get_raw_line.v "$tmp/get_raw_line.in" "$tmp/get_raw_line.expected"
printf '3+4*2\nexit\n' > "$tmp/mini_calculator.in"
write_v_run_expected_with_stdin examples/mini_calculator.v "$tmp/mini_calculator.in" "$tmp/mini_calculator.expected"
printf '3+4*2\nexit\n' > "$tmp/mini_calculator_recursive_descent.in"
write_v_run_expected_with_stdin examples/mini_calculator_recursive_descent.v "$tmp/mini_calculator_recursive_descent.in" "$tmp/mini_calculator_recursive_descent.expected"
run_native_x64_example examples/hello_world.v hello_world "$tmp/hello_world.expected"
run_native_x64_example examples/fizz_buzz.v fizz_buzz "$tmp/fizz_buzz.expected"
run_native_x64_example examples/hanoi.v hanoi "$tmp/hanoi.expected"
run_native_x64_example examples/sudoku.v sudoku "$tmp/sudoku.expected"
run_native_x64_example examples/function_types.v function_types "$tmp/function_types.expected"
run_native_x64_example examples/submodule/main.v submodule "$tmp/submodule.expected"
run_native_x64_example examples/fibonacci.v fibonacci "$tmp/fibonacci_10.expected" 10
run_native_x64_example examples/dump_factorial.v dump_factorial "$tmp/dump_factorial.expected"
run_native_x64_example examples/primes.v primes "$tmp/primes_20.expected" 20
run_native_x64_example examples/tree_of_nodes.v tree_of_nodes "$tmp/tree_of_nodes.expected"
run_native_x64_example examples/js_hello_world.v js_hello_world "$tmp/js_hello_world.expected"
run_native_x64_example examples/vascii.v vascii "$tmp/vascii.expected"
run_native_x64_example examples/rune.v rune "$tmp/rune.expected"
run_native_x64_example examples/graphs/bfs.v bfs "$tmp/bfs.expected"
run_native_x64_example examples/graphs/bfs3.v bfs3 "$tmp/bfs3.expected"
run_native_x64_example examples/graphs/dfs.v dfs "$tmp/dfs.expected"
run_native_x64_example examples/graphs/dijkstra.v dijkstra "$tmp/dijkstra.expected"
run_native_x64_example examples/graphs/topological_sorting_greedy.v topological_sorting_greedy "$tmp/topological_sorting_greedy.expected"
run_native_x64_example examples/graphs/topological_sorting_dfs.v topological_sorting_dfs "$tmp/topological_sorting_dfs.expected"
run_native_x64_example examples/graphs/dfs2.v dfs2 "$tmp/dfs2.expected"
run_native_x64_example examples/graphs/minimal_spann_tree_prim.v minimal_spann_tree_prim "$tmp/minimal_spann_tree_prim.expected"
run_native_x64_example examples/graphs/bellman-ford.v bellman_ford "$tmp/bellman_ford.expected"
run_native_x64_example examples/binary_search_tree.v binary_search_tree "$tmp/binary_search_tree.expected"
run_native_x64_example examples/errors.v errors "$tmp/errors.expected"
run_native_x64_example examples/custom_error.v custom_error "$tmp/custom_error.expected"
run_native_x64_example examples/spectral.v spectral "$tmp/spectral_10.expected" 10
run_native_x64_example examples/quick_sort.v quick_sort "$tmp/quick_sort.expected"
run_native_x64_example_with_stdin examples/get_raw_line.v get_raw_line "$tmp/get_raw_line.in" "$tmp/get_raw_line.expected"
run_native_x64_example_with_stdin examples/mini_calculator.v mini_calculator "$tmp/mini_calculator.in" "$tmp/mini_calculator.expected"
run_native_x64_example_with_stdin examples/mini_calculator_recursive_descent.v mini_calculator_recursive_descent "$tmp/mini_calculator_recursive_descent.in" "$tmp/mini_calculator_recursive_descent.expected"
run_native_x64_example_capture examples/random_ips.v random_ips
check_random_ips_stdout random_ips "$tmp/random_ips.out"
run_native_x64_example_capture examples/rule110.v rule110 31
check_rule110_stdout rule110 "$tmp/rule110.out" 31
- name: All code is formatted
run: v run ci/linux_ci.vsh all_code_is_formatted_gcc
- name: Install dependencies for examples and tools
run: v run ci/linux_ci.vsh install_dependencies_for_examples_and_tools_gcc
- name: Recompile V with -cstrict and gcc
run: v run ci/linux_ci.vsh recompile_v_with_cstrict_gcc
- name: Valgrind v.c
run: v run ci/linux_ci.vsh valgrind_v_c_gcc
- name: Run sanitizers
run: v run ci/linux_ci.vsh run_sanitizers_gcc
- name: v self compilation
run: v run ci/linux_ci.vsh v_self_compilation_gcc
- name: v self compilation with -usecache
run: v run ci/linux_ci.vsh v_self_compilation_usecache_gcc
- name: Verify `v test` works
run: v run ci/linux_ci.vsh verify_v_test_works_gcc
- name: Test pure V math module
run: v run ci/linux_ci.vsh test_pure_v_math_module_gcc
- name: Self tests
run: v run ci/linux_ci.vsh self_tests_gcc
- name: Self tests (-prod)
run: v run ci/linux_ci.vsh self_tests_prod_gcc
- name: Self tests (-cstrict)
run: v run ci/linux_ci.vsh self_tests_cstrict_gcc
- name: Build examples
run: v run ci/linux_ci.vsh build_examples_gcc
- name: Build tetris with -autofree
run: v run ci/linux_ci.vsh build_tetris_autofree_gcc
- name: Build blog tutorial with -autofree
run: v run ci/linux_ci.vsh build_blog_autofree_gcc
- name: Build option_test.c.v with -autofree
run: v run ci/linux_ci.vsh build_option_test_autofree_gcc
- name: V self compilation with -parallel-cc
run: v run ci/linux_ci.vsh v_self_compilation_parallel_cc_gcc
- name: Build modules
run: v run ci/linux_ci.vsh build_modules_gcc
- name: compile vdoctor.v with -prod
run: v run ci/linux_ci.vsh compile_vdoctor_prod_gcc
- name: compile vup.v with -prod
run: v run ci/linux_ci.vsh compile_vup_prod_gcc
clang-linux:
runs-on: ubuntu-24.04
timeout-minutes: 121
env:
VFLAGS: -cc clang
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make -j4 && ./v symlink
- name: All code is formatted
run: v run ci/linux_ci.vsh all_code_is_formatted_clang
- name: Install dependencies for examples and tools
run: v run ci/linux_ci.vsh install_dependencies_for_examples_and_tools_clang
- name: Recompile V with -cstrict and clang
run: v run ci/linux_ci.vsh recompile_v_with_cstrict_clang
- name: Valgrind
run: v run ci/linux_ci.vsh valgrind_clang
- name: Run sanitizers
run: v run ci/linux_ci.vsh run_sanitizers_clang
- name: v self compilation
run: v run ci/linux_ci.vsh v_self_compilation_clang
- name: v self compilation with -usecache
run: v run ci/linux_ci.vsh v_self_compilation_usecache_clang
- name: Verify `v test` works
run: v run ci/linux_ci.vsh verify_v_test_works_clang
- name: Test pure V math module
run: v run ci/linux_ci.vsh test_pure_v_math_module_clang
- name: Self tests
run: v run ci/linux_ci.vsh self_tests_clang
- name: Self tests (vprod)
run: v run ci/linux_ci.vsh self_tests_vprod_clang
- name: Self tests (-cstrict)
run: v run ci/linux_ci.vsh self_tests_cstrict_clang
- name: Build examples
run: v run ci/linux_ci.vsh build_examples_clang
- name: Build examples with -autofree
run: v run ci/linux_ci.vsh build_examples_autofree_clang
- name: Build modules
run: v run ci/linux_ci.vsh build_modules_clang
+519
View File
@@ -0,0 +1,519 @@
name: CI macOS
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/macos_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/macos_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: macos-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
clang-macos:
strategy:
matrix:
os: [macos-14]
fail-fast: false
runs-on: ${{ matrix.os }}
timeout-minutes: 151
env:
VFLAGS: -cc clang
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- name: Cache Homebrew downloads
uses: actions/cache@v5
with:
path: ~/Library/Caches/Homebrew
key: brew-${{ matrix.os }}-${{ hashFiles('.github/workflows/macos_ci.yml', 'ci/macos_ci.vsh') }}
restore-keys: |
brew-${{ matrix.os }}-
- name: Build V
run: make -j4 && ./v symlink
- name: Test symlink
run: v run ci/macos_ci.vsh test_symlink
- name: v doctor
run: v run ci/macos_ci.vsh v_doctor
- name: Build v with -prealloc
run: v run ci/macos_ci.vsh build_v_with_prealloc
- name: Test cross compilation to Linux
run: v run ci/macos_ci.vsh test_cross_compilation
- name: Test inline assembly on macos
run: v run ci/macos_ci.vsh test_inline_assembly
- name: Build V with -cstrict
run: v run ci/macos_ci.vsh build_with_cstrict
- name: All code is formatted
run: v run ci/macos_ci.vsh all_code_is_formatted
- name: Run sanitizers
run: v run ci/macos_ci.vsh run_sanitizers
- name: Build V using V
run: v run ci/macos_ci.vsh build_using_v
- name: Verify `v test` works
run: v run ci/macos_ci.vsh verify_v_test_works
- name: Install iconv for encoding.iconv
run: v run ci/macos_ci.vsh install_iconv
- name: Test pure V math module
run: v run ci/macos_ci.vsh test_pure_v_math_module
- name: Self tests
run: v run ci/macos_ci.vsh self_tests
- name: Build examples
run: v run ci/macos_ci.vsh build_examples
- name: Build tetris with -autofree
run: v run ci/macos_ci.vsh build_tetris_autofree
- name: Build blog tutorial with -autofree
run: v run ci/macos_ci.vsh build_blog_autofree
- name: Build examples with -prod
run: v run ci/macos_ci.vsh build_examples_prod
- name: Build examples with V build with tcc
run: v run ci/macos_ci.vsh build_examples_v_compiled_with_tcc
## - name: V self compilation with -usecache
## run: v run ci/macos_ci.vsh v_self_compilation_usecache
- name: V self compilation with -parallel-cc
run: v run ci/macos_ci.vsh v_self_compilation_parallel_cc
- name: v2 test suite
if: ${{ false }} # Temporarily disabled.
run: v run cmd/v2/test_all.vsh -prod
- name: Test password input
run: v run ci/macos_ci.vsh test_password_input
- name: Test readline
run: v run ci/macos_ci.vsh test_readline
v2-x64-native-macos:
if: ${{ false }} # Temporarily disabled.
runs-on: macos-15-intel
timeout-minutes: 30
steps:
- uses: actions/checkout@v7
- name: Build V
run: make -j4
- name: backend x64 regressions
run: |
set -e
VJOBS=1 ./v test \
vlib/v2_toberemoved/abi \
vlib/v2_toberemoved/gen/x64/x64_abi_test.v \
vlib/v2_toberemoved/gen/x64/x64_backend_diagnostics_test.v \
vlib/v2_toberemoved/gen/x64/x64_object_format_test.v \
vlib/v2_toberemoved/gen/x64/x64_pe_linker_test.v \
vlib/v2_toberemoved/ssa/tree_sumtype_lowering_test.v
VJOBS=1 ./v test -run-only test_module_qualified_alias_array_field_index_has_alias_element_type,test_module_storage_legacy_direct_import_nested_module_selector_uses_declared_leaf_module,test_module_storage_flat_direct_import_nested_module_selector_uses_declared_leaf_module vlib/v2_toberemoved/ssa/module_storage_test.v
VJOBS=1 ./v test -run-only test_temporary_generic_receiver_init_maps_method_generic,test_temporary_generic_call_receiver_maps_method_generic,test_temporary_generic_selector_receiver_maps_method_generic,test_identifier_generic_receiver_from_call_maps_method_generic vlib/v2_toberemoved/types/checker_test.v
VJOBS=1 ./v test -run-only test_worker_clone_sees_sumtype_decl_variant_cache,test_sumtype_decl_variant_cache_records_concrete_generic_variants_only,test_generic_sumtype_match_uses_full_specialization_when_generic_base_repeats,test_flat_direct_generic_sumtype_match_uses_full_specialization_when_generic_base_repeats,test_generic_sumtype_match_smartcast_scans_full_specialization_body,test_flat_direct_generic_sumtype_match_smartcast_scans_full_specialization_body,test_nested_module_concrete_generic_sumtype_base_does_not_fall_back_to_local_tree,test_leaf_module_concrete_generic_sumtype_base_fallback_beats_parent_module_tree vlib/v2_toberemoved/transformer/monomorphize_test.v
VJOBS=1 ./v test -run-only test_x64_macos_windows_math_log_20_stdout_exact_bytes,test_x64_macos_windows_generic_sumtype_repeated_base_specialization_stdout_exact_bytes,test_x64_macos_windows_formatted_int_interpolation_stdout_exact_bytes,test_x64_macos_windows_formatted_int_width_100_interpolation_stdout_exact_bytes,test_x64_macos_windows_formatted_f64_interpolation_stdout_exact_bytes,test_x64_macos_windows_formatted_string_return_lifetime_stdout_exact_bytes,test_x64_macos_windows_spectral_reduced_formatted_stdout_exact_bytes,test_x64_macos_windows_bits_len32_stdout_exact_bytes,test_x64_macos_windows_rand_u32n_interface_result_stdout_exact_bytes,test_x64_macos_windows_rand_intn_range_interface_result_stdout_exact_bytes,test_x64_macos_windows_textscanner_embedded_parser_stdout_exact_bytes,test_x64_macos_windows_struct_positional_side_effect_stdout_exact_bytes,test_x64_macos_windows_struct_named_side_effect_stdout_exact_bytes,test_x64_macos_windows_unrelated_same_shape_struct_stdout_exact_bytes,test_x64_macos_windows_named_init_embedded_value_stdout_exact_bytes,test_x64_macos_windows_get_raw_line_example_stdin_stdout_exact_bytes,test_x64_macos_windows_mini_calculator_example_stdin_stdout_exact_bytes,test_x64_macos_windows_mini_calculator_recursive_descent_example_stdin_stdout_exact_bytes,test_x64_macos_external_c_flag_source_uses_hosted_link_with_compile_flags vlib/v2_toberemoved/gen/x64/x64_runtime_smoke_test.v
./v test vlib/v2_toberemoved/builder/native_test.v vlib/v2_toberemoved/builder/target_os_test.v
./v test vlib/v2_toberemoved/ssa/optimize
V2_VERIFY_STRICT=1 ./v test vlib/v2_toberemoved/ssa/optimize
- name: backend x64 examples
run: |
set -e
tmp="$(mktemp -d)"
trap 'rm -rf "$tmp"' EXIT
check_empty_stderr() {
label="$1"
stderr="$2"
if [ -s "$stderr" ]; then
echo "::error::$label wrote to stderr"
cat "$stderr"
return 1
fi
}
check_v_run_stderr() {
label="$1"
stderr="$2"
if [ ! -s "$stderr" ]; then
return 0
fi
if python3 - "$stderr" <<'PY'
import re
import sys
text = open(sys.argv[1], "rb").read().decode("utf-8", "replace")
text = re.sub(r"\x1b\[[0-?]*[ -/]*[@-~]", "", text).strip()
expected = "warning: tcc compilation failed, falling back to cc (this is much slower)"
raise SystemExit(0 if text == expected else 1)
PY
then
return 0
fi
echo "::error::$label wrote unexpected stderr"
cat "$stderr"
return 1
}
check_stdout() {
label="$1"
expected="$2"
actual="$3"
if ! cmp -s "$expected" "$actual"; then
echo "::error::$label stdout mismatch"
echo "expected:"
cat "$expected"
echo "actual:"
cat "$actual"
return 1
fi
}
run_native_x64_example() {
source="$1"
name="$2"
expected="$3"
shift 3
./v -v2 -no-parallel -b x64 "$source" -o "$tmp/$name"
"$tmp/$name" "$@" > "$tmp/$name.out" 2> "$tmp/$name.err"
check_empty_stderr "$name" "$tmp/$name.err"
check_stdout "$name" "$expected" "$tmp/$name.out"
}
run_native_x64_example_with_stdin() {
source="$1"
name="$2"
input="$3"
expected="$4"
shift 4
./v -v2 -no-parallel -b x64 "$source" -o "$tmp/$name"
"$tmp/$name" "$@" < "$input" > "$tmp/$name.out" 2> "$tmp/$name.err"
check_empty_stderr "$name" "$tmp/$name.err"
check_stdout "$name" "$expected" "$tmp/$name.out"
}
run_native_x64_example_capture() {
source="$1"
name="$2"
shift 2
./v -v2 -no-parallel -b x64 "$source" -o "$tmp/$name"
"$tmp/$name" "$@" > "$tmp/$name.out" 2> "$tmp/$name.err"
check_empty_stderr "$name" "$tmp/$name.err"
}
check_random_ips_stdout() {
label="$1"
actual="$2"
python3 - "$label" "$actual" <<'PY'
import sys
label = sys.argv[1]
path = sys.argv[2]
lines = open(path, "r", encoding="utf-8").read().splitlines()
if len(lines) != 10:
raise SystemExit(f"{label}: expected 10 lines, got {len(lines)}")
rows = []
for line in lines:
parts = line.split(".")
if len(parts) != 4:
raise SystemExit(f"{label}: invalid IPv4 shape: {line!r}")
row = []
for part in parts:
if not part.isdigit():
raise SystemExit(f"{label}: non-numeric octet in {line!r}")
value = int(part)
if value < 0 or value > 254:
raise SystemExit(f"{label}: octet out of range in {line!r}")
row.append(value)
rows.append(tuple(row))
if len(set(rows)) < 3:
raise SystemExit(f"{label}: output has too little row diversity")
if all(row[1] == 0 for row in rows) and all(row[3] == 0 for row in rows):
raise SystemExit(f"{label}: suspicious old x.0.x.0 pattern")
PY
}
check_rule110_stdout() {
label="$1"
actual="$2"
width="$3"
python3 - "$label" "$actual" "$width" <<'PY'
import sys
label = sys.argv[1]
path = sys.argv[2]
width = int(sys.argv[3])
lines = open(path, "r", encoding="utf-8").read().splitlines()
title = "Rule 110 V Implementation"
title_lines = [idx for idx, line in enumerate(lines) if title in line]
if not title_lines:
raise SystemExit(f"{label}: missing title")
idx = title_lines[0]
generations = lines[idx + 1:]
if generations and generations[0] == "":
generations = generations[1:]
if len(generations) != width:
raise SystemExit(f"{label}: expected {width} generation lines, got {len(generations)}")
for line in generations:
if len(line) != width:
raise SystemExit(f"{label}: generation line has width {len(line)}, expected {width}: {line!r}")
if any(ch not in " *" for ch in line):
raise SystemExit(f"{label}: invalid generation chars: {line!r}")
if not any("*" in line for line in generations):
raise SystemExit(f"{label}: expected at least one live cell")
if len(set(generations)) < 3:
raise SystemExit(f"{label}: expected at least 3 distinct generation lines")
PY
}
write_v_run_expected() {
source="$1"
expected="$2"
shift 2
stderr="$tmp/$(basename "$expected").stderr"
./v run "$source" "$@" > "$expected" 2> "$stderr"
check_v_run_stderr "v run $source $*" "$stderr"
}
write_v_run_expected_with_stdin() {
source="$1"
input="$2"
expected="$3"
shift 3
stderr="$tmp/$(basename "$expected").stderr"
./v run "$source" "$@" < "$input" > "$expected" 2> "$stderr"
check_v_run_stderr "v run $source $*" "$stderr"
}
write_fizz_buzz_expected() {
i=1
while [ "$i" -le 100 ]; do
if [ $((i % 15)) -eq 0 ]; then
echo FizzBuzz
elif [ $((i % 3)) -eq 0 ]; then
echo Fizz
elif [ $((i % 5)) -eq 0 ]; then
echo Buzz
else
echo "$i"
fi
i=$((i + 1))
done
}
write_hanoi_expected() {
python3 - <<'PY'
def hanoi(n, a, b, c):
if n == 1:
print(f"Disc 1 from {a} to {c}...")
else:
hanoi(n - 1, a, c, b)
print(f"Disc {n} from {a} to {c}...")
hanoi(n - 1, b, a, c)
hanoi(7, "A", "B", "C")
PY
}
write_sudoku_expected() {
python3 - <<'PY'
import sys
puzzle = [
[0, 3, 0, 0, 7, 0, 0, 0, 0],
[0, 0, 0, 1, 3, 5, 0, 0, 0],
[0, 0, 1, 0, 0, 0, 0, 5, 0],
[1, 0, 0, 0, 6, 0, 0, 0, 3],
[4, 0, 0, 8, 0, 3, 0, 0, 1],
[7, 0, 0, 0, 2, 0, 0, 0, 6],
[0, 0, 0, 0, 0, 0, 2, 1, 0],
[0, 0, 0, 4, 1, 2, 0, 0, 5],
[0, 0, 0, 0, 0, 0, 0, 7, 4],
]
solution = [
[2, 3, 5, 6, 7, 8, 1, 4, 9],
[9, 4, 7, 1, 3, 5, 8, 6, 2],
[6, 8, 1, 2, 4, 9, 3, 5, 7],
[1, 2, 8, 7, 6, 4, 5, 9, 3],
[4, 5, 6, 8, 9, 3, 7, 2, 1],
[7, 9, 3, 5, 2, 1, 4, 8, 6],
[3, 6, 4, 9, 5, 7, 2, 1, 8],
[8, 7, 9, 4, 1, 2, 6, 3, 5],
[5, 1, 2, 3, 8, 6, 9, 7, 4],
]
def append_grid(lines, label, grid):
lines.append(label)
for i, row in enumerate(grid):
if i % 3 == 0 and i != 0:
lines.append("- - - - - - - - - - - -")
line = ""
for j, value in enumerate(row):
if j % 3 == 0 and j != 0:
line += " | "
line += f"{value} "
lines.append(line)
lines = []
append_grid(lines, "Sudoku Puzzle:", puzzle)
lines.append("Solving...")
append_grid(lines, "Solution:", solution)
out = ("\n".join(lines) + "\n").encode()
if len(out) != 582:
raise SystemExit(f"sudoku stdout oracle shape changed: {len(out)} bytes")
sys.stdout.buffer.write(out)
PY
}
write_tree_of_nodes_expected() {
cat <<'EOF'
tree structure:
Node{
value: 10
left: Tree(Node{
value: 30
left: Tree(Empty{})
right: Tree(Empty{})
})
right: Tree(Node{
value: 20
left: Tree(Empty{})
right: Tree(Empty{})
})
}
tree size: 3
EOF
}
write_js_hello_world_expected() {
printf 'Hello from V.js (0)\nHello from V.js (1)\nHello from V.js (2)\n'
}
write_vascii_expected() {
python3 - <<'PY'
from pathlib import Path
import sys
source = Path("examples/vascii.v").read_text(encoding="utf-8")
start_marker = "println('"
end_marker = "')"
if source.count(start_marker) != 1:
raise SystemExit("vascii stdout oracle expects one single-quoted println literal")
start = source.index(start_marker) + len(start_marker)
end = source.rindex(end_marker)
if source[end + len(end_marker):].strip() != "}":
raise SystemExit("vascii stdout oracle expects the println literal to be the final main statement")
out = bytearray()
literal = source[start:end]
i = 0
while i < len(literal):
ch = literal[i]
if ch == "\\":
i += 1
if i >= len(literal):
raise SystemExit("unterminated escape in vascii literal")
escaped = literal[i]
if escaped == "n":
out.append(10)
elif escaped == "t":
out.append(9)
elif escaped == "r":
out.append(13)
elif escaped == "\\":
out.append(92)
elif escaped == "'":
out.append(39)
elif escaped == '"':
out.append(34)
else:
out.extend(escaped.encode("utf-8"))
else:
out.extend(ch.encode("utf-8"))
i += 1
out.append(10)
sys.stdout.buffer.write(out)
PY
}
write_rune_expected() {
printf '\360\237\230\200\n@\n'
}
printf 'Hello, World!\n' > "$tmp/hello_world.expected"
write_fizz_buzz_expected > "$tmp/fizz_buzz.expected"
write_hanoi_expected > "$tmp/hanoi.expected"
write_sudoku_expected > "$tmp/sudoku.expected"
printf 'HELLO WORLD\nHELLO WORLD\nHELLO WORLD\n' > "$tmp/function_types.expected"
printf '5\n3\n' > "$tmp/submodule.expected"
printf '1\n1\n2\n3\n5\n8\n13\n21\n34\n55\n89\n' > "$tmp/fibonacci_10.expected"
printf '120\n' > "$tmp/dump_factorial.expected"
write_v_run_expected examples/primes.v "$tmp/primes_20.expected" 20
write_tree_of_nodes_expected > "$tmp/tree_of_nodes.expected"
write_js_hello_world_expected > "$tmp/js_hello_world.expected"
write_vascii_expected > "$tmp/vascii.expected"
write_rune_expected > "$tmp/rune.expected"
write_v_run_expected examples/graphs/bfs.v "$tmp/bfs.expected"
write_v_run_expected examples/graphs/bfs3.v "$tmp/bfs3.expected"
write_v_run_expected examples/graphs/dfs.v "$tmp/dfs.expected"
write_v_run_expected examples/graphs/dijkstra.v "$tmp/dijkstra.expected"
write_v_run_expected examples/graphs/topological_sorting_greedy.v "$tmp/topological_sorting_greedy.expected"
write_v_run_expected examples/graphs/topological_sorting_dfs.v "$tmp/topological_sorting_dfs.expected"
write_v_run_expected examples/graphs/dfs2.v "$tmp/dfs2.expected"
write_v_run_expected examples/graphs/minimal_spann_tree_prim.v "$tmp/minimal_spann_tree_prim.expected"
write_v_run_expected examples/graphs/bellman-ford.v "$tmp/bellman_ford.expected"
write_v_run_expected examples/binary_search_tree.v "$tmp/binary_search_tree.expected"
printf 'wrong format\nempty input\n' > "$tmp/errors.expected"
write_v_run_expected examples/custom_error.v "$tmp/custom_error.expected"
write_v_run_expected examples/spectral.v "$tmp/spectral_10.expected" 10
printf 'length of random array is 1000\nbefore quick sort whether array is sorted: false\nafter quick sort whether array is sorted: true\n' > "$tmp/quick_sort.expected"
printf 'hello\nworld\n' > "$tmp/get_raw_line.in"
write_v_run_expected_with_stdin examples/get_raw_line.v "$tmp/get_raw_line.in" "$tmp/get_raw_line.expected"
printf '3+4*2\nexit\n' > "$tmp/mini_calculator.in"
write_v_run_expected_with_stdin examples/mini_calculator.v "$tmp/mini_calculator.in" "$tmp/mini_calculator.expected"
printf '3+4*2\nexit\n' > "$tmp/mini_calculator_recursive_descent.in"
write_v_run_expected_with_stdin examples/mini_calculator_recursive_descent.v "$tmp/mini_calculator_recursive_descent.in" "$tmp/mini_calculator_recursive_descent.expected"
run_native_x64_example examples/hello_world.v hello_world "$tmp/hello_world.expected"
run_native_x64_example examples/fizz_buzz.v fizz_buzz "$tmp/fizz_buzz.expected"
run_native_x64_example examples/hanoi.v hanoi "$tmp/hanoi.expected"
run_native_x64_example examples/sudoku.v sudoku "$tmp/sudoku.expected"
run_native_x64_example examples/function_types.v function_types "$tmp/function_types.expected"
run_native_x64_example examples/submodule/main.v submodule "$tmp/submodule.expected"
run_native_x64_example examples/fibonacci.v fibonacci "$tmp/fibonacci_10.expected" 10
run_native_x64_example examples/dump_factorial.v dump_factorial "$tmp/dump_factorial.expected"
run_native_x64_example examples/primes.v primes "$tmp/primes_20.expected" 20
run_native_x64_example examples/tree_of_nodes.v tree_of_nodes "$tmp/tree_of_nodes.expected"
run_native_x64_example examples/js_hello_world.v js_hello_world "$tmp/js_hello_world.expected"
run_native_x64_example examples/vascii.v vascii "$tmp/vascii.expected"
run_native_x64_example examples/rune.v rune "$tmp/rune.expected"
run_native_x64_example examples/graphs/bfs.v bfs "$tmp/bfs.expected"
run_native_x64_example examples/graphs/bfs3.v bfs3 "$tmp/bfs3.expected"
run_native_x64_example examples/graphs/dfs.v dfs "$tmp/dfs.expected"
run_native_x64_example examples/graphs/dijkstra.v dijkstra "$tmp/dijkstra.expected"
run_native_x64_example examples/graphs/topological_sorting_greedy.v topological_sorting_greedy "$tmp/topological_sorting_greedy.expected"
run_native_x64_example examples/graphs/topological_sorting_dfs.v topological_sorting_dfs "$tmp/topological_sorting_dfs.expected"
run_native_x64_example examples/graphs/dfs2.v dfs2 "$tmp/dfs2.expected"
run_native_x64_example examples/graphs/minimal_spann_tree_prim.v minimal_spann_tree_prim "$tmp/minimal_spann_tree_prim.expected"
run_native_x64_example examples/graphs/bellman-ford.v bellman_ford "$tmp/bellman_ford.expected"
run_native_x64_example examples/binary_search_tree.v binary_search_tree "$tmp/binary_search_tree.expected"
run_native_x64_example examples/errors.v errors "$tmp/errors.expected"
run_native_x64_example examples/custom_error.v custom_error "$tmp/custom_error.expected"
run_native_x64_example examples/spectral.v spectral "$tmp/spectral_10.expected" 10
run_native_x64_example examples/quick_sort.v quick_sort "$tmp/quick_sort.expected"
run_native_x64_example_with_stdin examples/get_raw_line.v get_raw_line "$tmp/get_raw_line.in" "$tmp/get_raw_line.expected"
run_native_x64_example_with_stdin examples/mini_calculator.v mini_calculator "$tmp/mini_calculator.in" "$tmp/mini_calculator.expected"
run_native_x64_example_with_stdin examples/mini_calculator_recursive_descent.v mini_calculator_recursive_descent "$tmp/mini_calculator_recursive_descent.in" "$tmp/mini_calculator_recursive_descent.expected"
run_native_x64_example_capture examples/random_ips.v random_ips
check_random_ips_stdout random_ips "$tmp/random_ips.out"
run_native_x64_example_capture examples/rule110.v rule110 31
check_rule110_stdout rule110 "$tmp/rule110.out" 31
@@ -0,0 +1,7 @@
fn test_ci_run_with_32bit_compiler() {
$if x64 && tinyc {
// TODO: uncomment that next assert when tcc32 vs tcc64 detection on windows works reliably
// assert false
assert true
}
}
@@ -0,0 +1,5 @@
fn test_ci_run_with_64bit_compiler() {
$if x32 {
assert false
}
}
+58
View File
@@ -0,0 +1,58 @@
name: vlib modules CI
on:
pull_request:
paths:
- 'vlib/**.v'
- 'vlib/**.md'
- 'cmd/tools/vdoc/**.v'
- 'cmd/tools/vdoc/theme/**.js'
- 'cmd/tools/vdoc/theme/**.css'
- 'cmd/tools/vdoc/theme/**.svg'
- 'cmd/tools/vdoc/theme/**.html'
- '**/module_docs_ci.yml'
push:
branches:
- master
paths:
- 'vlib/**.v'
- 'vlib/**.md'
- 'cmd/tools/vdoc/**.v'
- 'cmd/tools/vdoc/theme/**.js'
- 'cmd/tools/vdoc/theme/**.css'
- 'cmd/tools/vdoc/theme/**.svg'
- 'cmd/tools/vdoc/theme/**.html'
- '**/module_docs_ci.yml'
# Allow only one concurrent deployment, skipping runs queued between the run in-progress and latest queued.
# However, do NOT cancel in-progress runs as we want to allow these production deployments to complete.
concurrency:
group: module_docs-${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: ${{ !contains(github.ref, 'master')}}
jobs:
build-module-docs:
runs-on: ubuntu-24.04
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make -j4 && ./v symlink
- name: Update packages, before running apt install
run: .github/workflows/disable_azure_mirror.sh && v retry -- sudo apt update -y -qq
- name: Install dependencies (some modules wrap C libs)
run: v retry -- sudo apt install --quiet -y libpq-dev
libsodium-dev libasound2-dev libssl-dev \
sqlite3 libsqlite3-dev libfreetype6-dev \
libx11-dev libxi-dev freeglut3-dev \
libgl1-mesa-dri libxcursor-dev libgl-dev libxrandr-dev libegl-dev
- name: Install markdown from vpm
run: v retry -- v install markdown
- name: Test v doc
run: VJOBS=1 ./v test cmd/tools/vdoc/
- name: Build module documentation and check the examples in the comments
run: VJOBS=1 ./v doc -m -f html -unsafe-run-examples -time vlib/
- name: Deploy docs to vercel
if: github.event_name == 'push' && github.repository == 'vlang/v' && github.ref == 'refs/heads/master'
run: npx vercel --confirm --prod --name vmodules --token ${{ secrets.VERCEL_TOKEN }} vlib/_docs/ || true
+21
View File
@@ -0,0 +1,21 @@
name: Code CI vlib modules
on:
push:
branches:
- master
paths:
- '**/cmd/tools/vdoc/theme/**'
pull_request:
paths:
- '**/cmd/tools/vdoc/theme/**'
jobs:
lint-module-docs:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v7
- name: Check Formatting
uses: creyD/prettier_action@v4.6
with:
prettier_options: --check cmd/tools/vdoc/theme
@@ -0,0 +1,45 @@
name: More extensive but slower tests
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/more_extensive_but_slower_tests_ci.yml'
- 'examples/**'
- 'cmd/tools/**'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/more_extensive_but_slower_tests_ci.yml'
- 'examples/**'
- 'cmd/tools/**'
concurrency:
group: slower_tests-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
more-tests:
strategy:
matrix:
os: [ubuntu-latest, macos-14, windows-latest]
runs-on: ${{ matrix.os }}
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Build V
if: runner.os != 'Windows'
run: make -j4 && ./v symlink
- name: Build V (Windows)
if: runner.os == 'Windows'
run: ./makev.bat && ./v symlink
- name: Run additional crypto tests
run: |
v retry -- git clone --depth 1 https://github.com/vlang/slower_tests
v test slower_tests/
+103
View File
@@ -0,0 +1,103 @@
name: CI OpenBSD
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- 'cmd/tools/**'
- '!**/openbsd_ci.yml'
- '!ci/openbsd_ci.vsh'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- 'cmd/tools/**'
- '!**/openbsd_ci.yml'
- '!ci/openbsd_ci.vsh'
- '!cmd/tools/builders/**.v'
### See https://github.com/cross-platform-actions/action
### for a description of the used fields here
jobs:
tcc-openbsd:
runs-on: ubuntu-latest
timeout-minutes: 30
steps:
- uses: actions/checkout@v7
- name: Start OpenBSD VM for tcc
id: vm-openbsd-tcc
uses: cross-platform-actions/action@v1.2.0
with:
operating_system: openbsd
version: '7.8'
memory: 4G
sync_files: runner-to-vm
- name: Tests on OpenBSD with tcc
id: tests-openbsd-tcc
shell: cpa.sh {0}
run: |
sudo pkg_add git sqlite3 gmake boehm-gc libiconv
# Install packages needed to build examples
sudo pkg_add mariadb-client postgresql-client
# Mandatory: hostname not set in VM => some tests fail
sudo hostname -s openbsd-ci
echo "::group::OS infos"
uname -a
echo "::endgroup::"
echo "::group::Build V"
git config --global --add safe.directory .
gmake
sudo ./v symlink
export VTEST_SHOW_LONGEST_BY_RUNTIME=3
export VTEST_SHOW_LONGEST_BY_COMPTIME=3
export VTEST_SHOW_LONGEST_BY_TOTALTIME=3
export VFLAGS='-cc tcc -no-retry-compilation'
echo "::endgroup::"
./v run ci/openbsd_ci.vsh all
clang-openbsd:
runs-on: ubuntu-latest
timeout-minutes: 30
steps:
- uses: actions/checkout@v7
- name: Start OpenBSD VM for clang
id: vm-openbsd-clang
uses: cross-platform-actions/action@v1.2.0
with:
operating_system: openbsd
version: '7.8'
memory: 4G
sync_files: runner-to-vm
- name: Tests on OpenBSD with clang
id: tests-openbsd-clang
shell: cpa.sh {0}
run: |
sudo pkg_add git sqlite3 gmake boehm-gc libiconv
# Install packages needed to build examples
sudo pkg_add mariadb-client postgresql-client
# Mandatory: hostname not set in VM => some tests fail
sudo hostname -s openbsd-ci
echo "::group::OS infos"
uname -a
clang -v
echo "::endgroup::"
echo "::group::Build V"
git config --global --add safe.directory .
gmake
sudo ./v symlink
export VTEST_SHOW_LONGEST_BY_RUNTIME=3
export VTEST_SHOW_LONGEST_BY_COMPTIME=3
export VTEST_SHOW_LONGEST_BY_TOTALTIME=3
export VFLAGS='-cc clang'
echo "::endgroup::"
./v run ci/openbsd_ci.vsh all
+192
View File
@@ -0,0 +1,192 @@
name: Other CI
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/other_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/other_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: other-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
performance-compare-with-master:
runs-on: ubuntu-24.04
timeout-minutes: 30
steps:
- uses: actions/checkout@v7
with:
fetch-depth: 0
- name: Environment info
run: echo "$VFLAGS $GITHUB_SHA $GITHUB_REF"
- name: Name the local git branch
run: git checkout -b the_v_pr_branch
- name: Build local v
run: make && ./v symlink
- name: V version
run: ./v version
- name: Build the repeat tool
run: ./v cmd/tools/vrepeat.v
- name: Run compare_pr_to_master.v
run: VREPEAT_SILENT=1 ./v run .github/workflows/compare_pr_to_master.v
prevent-gpl-licenses:
runs-on: ubuntu-24.04
timeout-minutes: 20
steps:
- name: Checkout V ${{ github.head_ref }}
uses: actions/checkout@v7
with:
path: v
- name: Checkout V master
uses: actions/checkout@v7
with:
repository: vlang/v
path: vmaster
- name: Detect potentially added GPL licensed code
run: |
gpl_search_cmd="grep 'GPL' -r --exclude-dir=.git --exclude=*.yml --exclude=*.md --exclude=*.vv --exclude=*_test.v ."
cd vmaster
eval "$gpl_search_cmd" > ../gpl_res_vmaster
cd ../v
eval "$gpl_search_cmd" > ../gpl_res_vnew
cd ..
diff -d -a -U 2 --color=always gpl_res_vmaster gpl_res_vnew
code-formatting:
runs-on: ubuntu-24.04
timeout-minutes: 20
env:
VFLAGS: -cc gcc
steps:
- uses: actions/checkout@v7
- name: Environment info
run: echo "$VFLAGS $GITHUB_SHA $GITHUB_REF"
- name: Build local v
run: make -j4 && ./v symlink
- name: v test-cleancode
run: ./v -silent test-cleancode
- name: v test-fmt
run: ./v -silent test-fmt
performance-regressions:
runs-on: ubuntu-24.04
timeout-minutes: 20
env:
VFLAGS: -cc gcc
steps:
- uses: actions/checkout@v7
- name: Environment info
run: echo "$VFLAGS $GITHUB_SHA $GITHUB_REF"
- name: Build local v
run: make -j4 && ./v symlink
- name: Clone & Build previous vmaster/v
run: |
./v retry -- git clone --depth=1 https://github.com/vlang/v vmaster/
(cd vmaster; make -j4)
- name: V versions
run: ./v version && ./vmaster/v version
- name: Build the repeat tool
run: ./v cmd/tools/vrepeat.v
- name: Repeat -o hw.c examples/hello_world.v
run: ./v repeat --max_time 280 --series 3 --runs 20 --nmins 2 --nmaxs 5 --warmup 3 --fail_percent 10 -t 'cd {T} ; ./v -o hw.c examples/hello_world.v' . ./vmaster
- name: Repeat -o v.c cmd/v
run: ./v repeat --max_time 4000 --series 3 --runs 20 --nmins 2 --nmaxs 5 --warmup 3 --fail_percent 10 -t 'cd {T} ; ./v -o v.c cmd/v' . ./vmaster
misc-tooling:
runs-on: ubuntu-24.04
timeout-minutes: 20
env:
VFLAGS: -cc tcc -no-retry-compilation
steps:
- uses: actions/checkout@v7
with:
fetch-depth: 10
- uses: ./.github/actions/cache-apt-packages-action
- name: Build v
run: make -j4 && ./v symlink
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update
./v retry -- sudo apt install --quiet -y libsodium-dev libssl-dev sqlite3 libsqlite3-dev postgresql libpq-dev valgrind
./v retry -- sudo apt install --quiet -y libfreetype6-dev libxi-dev libxcursor-dev libgl-dev libxrandr-dev libasound2-dev xfonts-75dpi xfonts-base libegl-dev
./v retry -- sudo apt install --quiet -y g++-9 g++-10
- name: g++-9 version
run: g++-9 --version
- name: V self compilation with g++ and -std=c++11
run: ./v -cc g++-9 -no-std -cflags -std=c++11 -o v2 cmd/v && ./v2 -cc g++-9 -no-std -cflags -std=c++11 -o v3 cmd/v
- name: g++-10 version
run: g++-10 --version
- name: V self compilation with g++ and -std=c++20
run: ./v -cc g++-10 -no-std -cflags -std=c++20 -o v2 cmd/v && ./v2 -cc g++-10 -no-std -cflags -std=c++20 -o v3 cmd/v
# TODO: re-enable once autofree is fixed; see https://github.com/vlang/v/issues/27116
# - name: Ensure V can be compiled with -autofree
# run: ./v -autofree cmd/v
- name: Ensure V can be compiled with -no-closures
run: ./v -no-closures cmd/v
- name: Shader examples can be built
run: |
.github/workflows/compile_shaders_in_examples.sh
./v should-compile-all examples/sokol/*.v examples/sokol/0?*/*.v
parser-silent:
runs-on: ubuntu-24.04
timeout-minutes: 30
steps:
- uses: actions/checkout@v7
- name: Build local v
run: |
make -j4 && ./v symlink
./v -g -d trace_parse_stmt cmd/tools/vtest-parser.v
- name: Install zzuf
run: ./v retry -- sudo apt install -qq zzuf
- name: Run test-parser
run: |
./v test-parser --show_source --linear examples/hello_world.v
./v test-parser --show_source --linear examples/hanoi.v
./v test-parser --show_source --linear examples/fibonacci.v
./v test-parser --show_source --linear examples/cli.v
./v test-parser --show_source --linear examples/json.v
./v test-parser --show_source --linear examples/vmod.v
./v test-parser --show_source --linear examples/regex/regex_example.v
./v test-parser --show_source --linear examples/2048/2048.v
- name: Run test-parser over fuzzed files
run: |
zzuf -R '\x00-\x20\x7f-\xff' -r0.01 < examples/hello_world.v > examples/hello_world_fuzz.v
zzuf -R '\x00-\x20\x7f-\xff' -r0.01 < examples/hanoi.v > examples/hanoi_fuzz.v
zzuf -R '\x00-\x20\x7f-\xff' -r0.01 < examples/fibonacci.v > examples/fibonacci_fuzz.v
zzuf -R '\x00-\x20\x7f-\xff' -r0.01 < examples/cli.v > examples/cli_fuzz.v
zzuf -R '\x00-\x20\x7f-\xff' -r0.01 < examples/json.v > examples/json_fuzz.v
zzuf -R '\x00-\x20\x7f-\xff' -r0.01 < examples/vmod.v > examples/vmod_fuzz.v
zzuf -R '\x00-\x20\x7f-\xff' -r0.01 < examples/regex/regex_example.v > examples/regex_example_fuzz.v
zzuf -R '\x00-\x20\x7f-\xff' -r0.01 < examples/2048/2048.v > examples/2048/2048_fuzz.v
./v test-parser --show_source --linear examples/hello_world_fuzz.v
./v test-parser --show_source --linear examples/fibonacci_fuzz.v
./v test-parser --show_source --linear examples/hanoi_fuzz.v
./v test-parser --show_source --linear examples/cli_fuzz.v
./v test-parser --show_source --linear examples/json_fuzz.v
./v test-parser --show_source --linear examples/vmod_fuzz.v
./v test-parser --show_source --linear examples/regex_example_fuzz.v
./v test-parser --show_source --linear examples/2048/2048_fuzz.v
+117
View File
@@ -0,0 +1,117 @@
name: Path Testing CI
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/paths_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/paths_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: paths-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
space-paths-linux:
runs-on: ubuntu-24.04
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
with:
persist-credentials: false
path: '你好 my $path, @с интервали'
- name: Build V
run: |
# shellcheck disable=SC2016
echo '你好 my $path, @с интервали'
ls -la
# shellcheck disable=SC2016
cd '你好 my $path, @с интервали'
ls -la
make
- name: v doctor
run: |
# shellcheck disable=SC2016
cd '你好 my $path, @с интервали'
./v doctor
- name: v tests
run: |
# shellcheck disable=SC2016
cd '你好 my $path, @с интервали'
./v test vlib/builtin vlib/os
space-paths-macos:
runs-on: macos-14
timeout-minutes: 30
steps:
- uses: actions/checkout@v7
with:
path: '你好 my $path, @с интервали'
persist-credentials: false
- name: Build V
run: |
# shellcheck disable=SC2016
echo '你好 my $path, @с интервали'
ls -la
# shellcheck disable=SC2016
cd '你好 my $path, @с интервали'
ls -la
make
## prebuild cmd/tools/builders/js_builder, to minimise the
## chances of a sporadic "Killed" when running the tests later
./v -b js run examples/hello_world.v
- name: v doctor
run: |
# shellcheck disable=SC2016
cd '你好 my $path, @с интервали'
./v doctor
- name: v tests
run: |
# shellcheck disable=SC2016
cd '你好 my $path, @с интервали'
./v test vlib/builtin vlib/os
space-paths-windows:
runs-on: windows-2022
timeout-minutes: 30
## NB: the following paths do not work for now:
##### MY_V_PATH: '你好 my $path, @с интервали'
##### MY_V_PATH: 'path with some $punctuation, and some spaces '
## tcc has a problem interpreting paths with non latin letters in them,
## by default, but that can be solved with passing -Bthirdparty/tcc
## but after that V fails self building with:
####### builder error: cannot write to folder
####### D:\a\v\v\你好 my $path, @с интервали: No such file or directory
## and that happens even for gcc builds, not just tcc ones
steps:
- uses: actions/checkout@v7
with:
path: 'path with some $punctuation, and some spaces'
persist-credentials: false
- name: Build V
run: |
echo 'path with some $punctuation, and some spaces'
dir
cd 'path with some $punctuation, and some spaces'
dir
.\makev.bat -tcc
- name: v doctor
run: |
cd 'path with some $punctuation, and some spaces'
./v doctor
- name: v tests
run: |
cd 'path with some $punctuation, and some spaces'
./v test vlib/builtin vlib/os
+42
View File
@@ -0,0 +1,42 @@
name: Periodic CI
on:
schedule:
- cron: '0 */6 * * *'
push:
branches:
- master
paths:
- '**/periodic_ci.yml'
pull_request:
paths:
- '**/periodic_ci.yml'
jobs:
periodic-network:
strategy:
matrix:
include:
- os: ubuntu-latest
cc: tcc
- os: windows-latest
cc: msvc
- os: macos-latest
cc: clang
fail-fast: false
runs-on: ${{ matrix.os }}
if: github.event_name != 'schedule' || (github.ref == 'refs/heads/master' && github.repository == 'vlang/v')
timeout-minutes: 30
env:
VFLAGS: -cc ${{ matrix.cc }}
V_CI_PERIODIC: 1
steps:
- uses: actions/checkout@v7
- name: Build
if: runner.os != 'Windows'
run: make -j4 && ./v -showcc -o v cmd/v && ./v doctor
- name: Build V (Windows)
if: runner.os == 'Windows'
run: ./makev.bat -msvc && ./v -o v2.exe cmd/v && ./v2 -showcc -o v.exe cmd/v && ./v doctor
- name: Test
run: ./v -d network -silent test-self vlib/net
+71
View File
@@ -0,0 +1,71 @@
name: Test prebuilt binaries
on:
workflow_dispatch:
release:
types: [edited, published]
jobs:
prebuilt-linux:
runs-on: ubuntu-24.04
timeout-minutes: 5
steps:
- name: Download V
run: |
.github/workflows/retry.sh wget https://github.com/vlang/v/releases/latest/download/v_linux.zip
unzip v_linux.zip
cd v
./v -version
- name: Test V
run: |
cd v
./v run examples/hello_world.v
./v -showcc -gc none -cc tcc -no-retry-compilation run examples/hello_world.v
prebuilt-macos-arm64:
## macos-14 is a m1 runner
runs-on: macos-14
timeout-minutes: 5
steps:
- name: Download V
run: |
.github/workflows/retry.sh wget https://github.com/vlang/v/releases/latest/download/v_macos_arm64.zip
unzip v_macos_arm64.zip
cd v
./v -version
- name: Test V
run: |
cd v
./v run examples/hello_world.v
./v -showcc -gc none -cc tcc -no-retry-compilation run examples/hello_world.v
prebuilt-macos-x86_64:
runs-on: macos-latest
timeout-minutes: 5
steps:
- name: Download V
run: |
.github/workflows/retry.sh wget https://github.com/vlang/v/releases/latest/download/v_macos_x86_64.zip
unzip v_macos_x86_64.zip
cd v
./v -version
- name: Test V
run: |
cd v
./v run examples/hello_world.v
prebuilt-windows:
runs-on: windows-latest
timeout-minutes: 5
steps:
- name: Download V
run: |
curl -L https://github.com/vlang/v/releases/latest/download/v_windows.zip -o v_windows.zip
unzip .\v_windows.zip
cd v
.\v.exe -version
- name: Test V
run: |
cd v
.\v.exe run .\examples\hello_world.v
.\v.exe -showcc -gc none -cc tcc -no-retry-compilation run .\examples/hello_world.v
+62
View File
@@ -0,0 +1,62 @@
name: Shy and PV CI
on:
workflow_dispatch:
push:
branches:
- master
paths:
- 'vlib/v/checker/**.v'
- 'vlib/v/gen/c/**.v'
- 'thirdparty/**'
- 'cmd/tools/builders/**.v'
- 'cmd/tools/vshader.v'
- '**/puzzle_vibes_ci.yml'
- '!**_test.v'
- '!**.md'
pull_request:
paths:
- 'vlib/v/checker/**'
- 'vlib/v/gen/c/**'
- 'thirdparty/**'
- 'cmd/tools/builders/**.v'
- 'cmd/tools/vshader.v'
- '**/puzzle_vibes_ci.yml'
- '!**_test.v'
- '!**.md'
concurrency:
group: puzzle_vibes-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
v-compiles-puzzle-vibes:
runs-on: ubuntu-24.04
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make && ./v symlink
- name: Install & Setup SDL
run: v retry -- v install sdl && v ~/.vmodules/sdl/setup.vsh
- name: Install Shy
run: v retry -- v install https://github.com/medvednikov/shy
- name: Clone Puzzle Vibes
run: v retry -- git clone https://github.com/medvednikov/puzzle_vibes/
- name: Check PV compiles with -g
run: cd puzzle_vibes && v -g .
- name: Check PV compiles
run: cd puzzle_vibes && v .
- name: Check PV compiles with -prod
run: cd puzzle_vibes && v -prod -no-prod-options .
- name: Check PV compiles with -prod and -g
run: cd puzzle_vibes && v -prod -g -no-prod-options .
+128
View File
@@ -0,0 +1,128 @@
name: Release CI
on:
workflow_dispatch:
pull_request:
paths:
- '.github/workflows/release_ci.yml'
push:
paths:
- '.github/workflows/release_ci.yml'
tags:
- weekly.**
- 0.**
concurrency:
group: release-${{ github.workflow }}-${{ github.ref }}
cancel-in-progress: ${{ github.ref_type != 'tag' }}
permissions:
contents: write
jobs:
release-build:
runs-on: ${{ matrix.os }}
strategy:
matrix:
os:
[
ubuntu-22.04,
ubuntu-22.04-arm,
macos-15-intel,
macos-15,
windows-latest,
]
include:
- os: ubuntu-22.04
cc: gcc
target: linux
artifact: v_linux.zip
- os: ubuntu-22.04-arm
cc: gcc
target: linux_arm64
artifact: v_linux_arm64.zip
- os: macos-15-intel
cc: clang
target: macos_x86_64
artifact: v_macos_x86_64.zip
- os: macos-15
cc: clang
target: macos_arm64
artifact: v_macos_arm64.zip
- os: windows-latest
cc: msvc
target: windows
artifact: v_windows.zip
fail-fast: false
steps:
- uses: actions/checkout@v7
- name: Compile release binaries
if: runner.os != 'Windows'
run: |
make
./v -cc ${{ matrix.cc }} ${{ matrix.cflags }} -prod -o v cmd/v
./v -cc ${{ matrix.cc }} ${{ matrix.cflags }} -prod cmd/tools/vup.v
./v -cc ${{ matrix.cc }} ${{ matrix.cflags }} -prod cmd/tools/vdoctor.v
- name: Compile release binaries (Windows)
if: runner.os == 'Windows'
run: |
./makev.bat -msvc
./v -prod -cc msvc -o cmd/vprod.exe cmd/v
./v -prod -cc msvc cmd/tools/vup.v
./v -prod -cc msvc cmd/tools/vdoctor.v
del ./*.exe
del ./*.tmp.obj
move cmd/vprod.exe v.exe
- name: Prepare artifact
shell: bash
run: |
if [[ ${{ matrix.os }} == 'macos-14' ]]; then
rm -rf thirdparty/tcc
git clone --branch thirdparty-macos-arm64 --depth=1 https://github.com/vlang/tccbin thirdparty/tcc
fi
# Remove excluded
if [[ $RUNNER_OS == 'Windows' ]]; then
find . -type f \( -name "*.ilk" -o -name "*.pdb" \) -exec rm -rf {} +
rm -rf v_old.exe
fi
find . -type d -name ".git" -exec rm -rf {} +
rm -rf vc/
rm -rf v_old
rm -rf vlib/v/tests/bench/gcboehm/*.svg.xz
- name: Create ZIP archive
shell: bash
run: |
cd ..
if [[ $RUNNER_OS == 'Windows' ]]; then
7z a -tzip ${{ matrix.artifact }} v/
else
zip -r9 --symlinks ${{ matrix.artifact }} v/
fi
zipinfo ${{ matrix.artifact }}
mv ${{ matrix.artifact }} v/
cd v/
- name: Create artifact
uses: actions/upload-artifact@v7
with:
name: ${{ matrix.target }}
path: ${{ matrix.artifact }}
release-publish:
if: github.ref_type == 'tag'
needs: release-build
runs-on: ubuntu-latest
steps:
- uses: actions/download-artifact@v8
- name: Create release
uses: ncipollo/release-action@v1
with:
artifacts: |
~/work/v/v/windows/v_windows.zip
~/work/v/v/linux/v_linux.zip
~/work/v/v/linux_arm64/v_linux_arm64.zip
~/work/v/v/macos_arm64/v_macos_arm64.zip
~/work/v/v/macos_x86_64/v_macos_x86_64.zip
tag: ${{ github.ref_name }}
name: ${{ github.ref_name }}
draft: false
prerelease: false
+22
View File
@@ -0,0 +1,22 @@
#!/usr/bin/env bash
cmd=$@
function elog() {
message=$1
printf "%(%Y/%m/%d %H:%M:%S)T | retry.sh $1\n"
}
declare -i iteration=0
declare -i max_iterations=9
for((iteration=1;iteration<=max_iterations;iteration++)); do
elog "iteration: $iteration/$max_iterations, cmd: $cmd"
if $cmd; then
exit 0
fi
elog "command failed, retrying ...";
sleep 1;
done;
elog "failed doing $max_iterations iterations of command: $cmd"
exit 1
+56
View File
@@ -0,0 +1,56 @@
name: riscv64 CI
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/riscv64_linux_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/riscv64_linux_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
jobs:
riscv64_linux:
# The host should always be Linux
runs-on: ubuntu-24.04
timeout-minutes: 30
name: Build on ubuntu-24.04 riscv64
steps:
- uses: actions/checkout@v7
- uses: uraimo/run-on-arch-action@v3
name: Run commands
id: runcmd
with:
arch: riscv64
distro: ubuntu24.04
base_image: --platform=linux/riscv64 riscv64/ubuntu:24.04
# The token tag here is not required, but speeds up builds,
# by allowing caching of the installed dependencies, which is ~2.5min:
githubToken: ${{ github.token }}
shell: /bin/bash
install: |
apt-get update -q -y
apt-get install -q -y make gcc git file coreutils binutils
run: |
uname -a
make --version
gcc --version
ls -la
export LDFLAGS="-latomic"
export VFLAGS="-gc none -no-retry-compilation -cc cc"
make
file ./v
ls -la ./v
./v test vlib/builtin vlib/os vlib/encoding/binary
./v test vlib/v/slow_tests/assembly
VTEST_ONLY=closure ./v test vlib/v/tests
+25
View File
@@ -0,0 +1,25 @@
#!/usr/bin/env bash
export PS4='\033[0;33m+ >>>>> (${BASH_SOURCE}:${LINENO}): ${FUNCNAME[0]:+${FUNCNAME[0]}(): }\033[0m'
set -xe
echo " Setup environment ..."
export DEBUG_OPTS=${DEBUG_OPTS:-"-keepc -cg -cflags -fno-omit-frame-pointer"}
export VFLAGS=${VFLAGS:-"-cc clang"}
v version
v -show-c-output -cflags --version -e ';' || true
echo " Compile and run sanitizers ..."
v ${VFLAGS} ${DEBUG_OPTS} -o v2 cmd/v -cflags -fsanitize=memory
UBSAN_OPTIONS="print_stacktrace=1:halt_on_error=1" ./v2 -o v.c cmd/v
v ${VFLAGS} ${DEBUG_OPTS} -o v3 cmd/v -cflags -fsanitize=thread
TSAN_OPTIONS="suppressions=.github/workflows/run_sanitizers_thread.suppressions" UBSAN_OPTIONS="print_stacktrace=1:halt_on_error=1" ./v3 -o v.c cmd/v
v ${VFLAGS} ${DEBUG_OPTS} -o v4 cmd/v -cflags -fsanitize=undefined
UBSAN_OPTIONS="suppressions=.github/workflows/run_sanitizers_undefined.suppressions:print_stacktrace=1:halt_on_error=1" ./v4 -o v.c cmd/v
v ${VFLAGS} ${DEBUG_OPTS} -o v5 cmd/v -cflags -fsanitize=address,pointer-compare,pointer-subtract
ASAN_OPTIONS="detect_leaks=0" UBSAN_OPTIONS="print_stacktrace=1:halt_on_error=1" ./v5 -o v.c cmd/v
@@ -0,0 +1,16 @@
# websocket/ssl tests
leak:mbedtls_ssl_setup
leak:mbedtls_ssl_tls13_compute_application_transform
leak:rsa_alloc_wrap
leak:mbedtls_pk_parse
# sqlite tests
leak:*sqlite*
# v
leak:v__*
leak:os__*
leak:string__plus
leak:malloc_uncollectable
leak:new_array_from_c_array
leak:_vinit
@@ -0,0 +1,5 @@
## See https://github.com/google/sanitizers/wiki/ThreadSanitizerSuppressions
## and https://clang.llvm.org/docs/ThreadSanitizer.html
## The sync__stdatomic__add_i64 and sync__stdatomic__sub_i64 suppressions below, are needed for clang-10 to clang-12; clang-18 is fine without them
race:sync__stdatomic__add_i64
race:sync__stdatomic__sub_i64
@@ -0,0 +1,186 @@
## See https://clang.llvm.org/docs/UndefinedBehaviorSanitizer.html
## Most of the supressed functions here use asserts, that in turn use an indirection through an interface. TODO: if that is solved, most of these can be removed.
## Usually they contain a __test_ in their name, but not always (see the x.ttf ones like vlib/x/ttf/ttf_test.v ).
## TODO: extract the common part of the assertions to a VDO_ function (1 for pass and 1 for failure), so that they can be whitelisted here just once.
function:map_exists
function:map_get
function:IError_str
shift-exponent:math__bits__rotate_left_64
shift-exponent:math__bits__div_64
function:math__big__Integer_general_radix_str
function:math__big__Integer_div_mod_internal
function:math__bits__test_bits
function:math__bits__test_div_64_edge_cases
function:math__test_nan
alignment:rand__read_64
function:rand__internal_ulid_at_millisecond
function:rand__internal_string_from_set
function:rand__internal_uuid_v4
function:rand__deinit
function:rand__read_internal
function:rand__read_64
function:rand__PRNG_f64
function:rand__cuid2__test_cuid2
function:sync__pool__process_in_thread
function:sync__Once_do_slow_with_param
function:v__gen__c__FunctionDeferCollector_visit
function:v__gen__c__collect_function_defer_stmts
function:v__type_resolver__TypeResolver_resolve_fn_generic_args
function:v__type_resolver__TypeResolver_unwrap_generic_expr
function:v__type_resolver__TypeResolver_get_type
## these have asserts in them, and trigger due to the used indirection; TODO: remove them, when a more general solution is found for all interfaces
function:x__ttf__TTF_File_get_glyph_offset
function:x__ttf__TTF_File_get_horizontal_metrics
function:x__ttf__TTF_File_glyph_count
function:x__ttf__TTF_File_read_glyph
function:x__ttf__TTF_File_read_simple_glyph
function:x__ttf__TTF_File_read_kern_table
function:x__ttf__TTF_File_read_hhea_table
function:x__ttf__TTF_File_read_cmap_table
function:x__ttf__TTF_File_read_name_table
function:x__ttf__TTF_File_read_head_table
function:x__ttf__TTF_File_read_offset_tables
function:net__unix__select_deadline
function:net__select_deadline
function:net__socks__test_parse_ipv4
function:net__http__download_file_with_progress
function:net__http__download_progres_cb
function:net__http__check_headers
function:net__http__test_str
function:net__http__test_int
function:net__http__test_is_valid
function:net__http__test_is_error
function:net__http__test_is_success
function:net__http__test_parse_response_with_weird_cookie
function:net__http__test_parse_response_with_cookies
function:net__http__test_parse_response
function:net__http__test_response_bytestr_1
function:net__http__test_response_bytestr_2
function:net__http__test_parse_large_body
function:net__http__test_multipart_form_body
function:net__http__test_parse_multipart_form2
function:net__http__test_parse_request_no_headers
function:net__http__test_parse_multipart_form
function:net__http__test_parse_form
function:net__http__test_parse_request_line
function:net__http__test_parse_request_body
function:net__http__test_parse_request_two_header_values
function:net__http__test_parse_request_no_headers
function:net__http__test_parse_request_two_headers
function:net__http__test_proxy_fields
function:net__http__test_proxy_headers
function:net__http__test_set_cookie
function:net__http__test_parse_headers
function:net__http__parse_headers_test
function:net__http__test_header_join
function:net__http__test_header_from_map
function:net__http__test_custom_header_from_map
function:net__http__test_render_coerce_canonicalize
function:net__http__test_render_canonicalize
function:net__http__test_render_version
function:net__http__test_coerce_canonicalize_custom
function:net__http__test_coerce_custom
function:net__http__test_coerce_canonicalize
function:net__http__test_coerce
function:net__http__test_custom_values
function:net__http__test_starting_with
function:net__http__test_get_custom
function:net__http__test_contains_custom
function:net__http__test_custom_header
function:net__http__test_delete_header
function:net__http__test_header_delete_not_existing
function:net__http__test_header_delete
function:net__http__test_header_set
function:net__http__test_header_get
function:net__http__test_header_adds_multiple
function:net__http__test_header_new
function:net__test_ip6_str
function:net__test_ip_str
function:net__test_sizes_unix
function:net__test_sizes_ipv4
function:net__test_sizes_ipv6
function:net__test_offsets_unix
function:net__test_offsets_ipv4
function:net__test_offsets_ipv6
function:net__test_sizes_unix_sun_path
function:net__test_diagnostics
function:net__test_ip_port
function:net__websocket__delete_client_cb
function:net__websocket__Server_listen
function:net__websocket__Server_serve_client
function:net__websocket__Server_parse_client_handshake
function:net__websocket__Client_listen
function:net__websocket__Client_send_message_event
function:net__websocket__Client_send_close_event
function:net__websocket__Client_debug_log
function:net__websocket__Client_connect
function:io__BufferedReader_fill_buffer
function:io__read_all
function:log__info
function:log__debug
function:log__warn
function:log__error
function:log__set_level
function:log__Log_log_stream
function:log__free_logger
function:picoev__Picoev_poll_once
function:picoev__Picoev_set_timeout
function:picoev__Picoev_update_events
function:picoev__test_if_all_file_descriptors_are_properly_initialized
function:veb__RoutePair_test_param
function:veb__test_load_files_translations
## needed for tests; TODO: move the test specific setup code into its own separate VDO_tests function, so only it can be added here
function:main
function:crypto__sha3__test_0_length_hash
function:crypto__sha3__test_0_length_xof
function:crypto__sha3__test_200_length_hash
function:crypto__sha3__test_200_length_xof
function:crypto__sha3__test_2_x_24_rounds_on_zero
function:crypto__sha3__test_stepping_functions_on_zero
function:crypto__sha3__test_zero_state
function:crypto__sha3__test_rho_offsets
function:crypto__sha3__test_to_from_bytes
function:crypto__sha3__test_round_constants
function:crypto__pem__test_decode_rfc1421
function:crypto__pem__test_decode
function:crypto__pem__test_encode_rfc1421
function:crypto__pem__test_encode
function:crypto__hmac__test_hmac_equal
function:crypto__hmac__test_hmac_sha3_224
function:crypto__hmac__test_hmac_sha3_256
function:crypto__hmac__test_hmac_sha3_384
function:crypto__hmac__test_hmac_sha3_512
function:crypto__hmac__test_hmac_blake3_256
function:crypto__hmac__test_hmac_blake2b_160
function:crypto__hmac__test_hmac_blake2b_256
function:crypto__hmac__test_hmac_blake2b_384
function:crypto__hmac__test_hmac_blake2b_512
function:crypto__hmac__test_hmac_blake2s_128
function:crypto__hmac__test_hmac_blake2s_160
function:crypto__hmac__test_hmac_blake2s_224
function:crypto__hmac__test_hmac_blake2s_256
function:crypto__hmac__test_hmac_sha512
function:crypto__hmac__test_hmac_sha384
function:crypto__hmac__test_hmac_sha256
function:crypto__hmac__test_hmac_sha224
function:crypto__hmac__test_hmac_sha1
function:crypto__hmac__test_hmac_md5
function:crypto__ed25519__internal__edwards25519__sc_reduce
function:crypto__ed25519__internal__edwards25519__sc_reduce
+53
View File
@@ -0,0 +1,53 @@
name: s390 CI
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/s390x_linux_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/s390x_linux_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
jobs:
s390x_linux:
# The host should always be Linux
runs-on: ubuntu-22.04
timeout-minutes: 30
name: Build on ubuntu-22.04 s390x
steps:
- uses: actions/checkout@v7
- uses: uraimo/run-on-arch-action@v3
name: Run commands
id: runcmd
with:
arch: s390x
distro: ubuntu22.04
base_image: --platform=linux/s390x s390x/ubuntu:22.04
# The token tag here is not required, but speeds up builds,
# by allowing caching of the installed dependencies, which is ~2.5min:
githubToken: ${{ github.token }}
shell: /bin/bash
install: |
apt-get update -q -y
apt-get install -q -y make gcc git file coreutils binutils
run: |
uname -a
make --version
gcc --version
ls -la
make
file ./v
ls -la ./v
./v test vlib/builtin vlib/os vlib/encoding/binary
./v test vlib/v/tests/fns/closure_test.v
+327
View File
@@ -0,0 +1,327 @@
name: Sanitized CI
## Running these jobs is slow (over ~1 hour, sometimes even 2)
## so we run them only when there is a chance that the generated
## C code could have changed, or for some critical vlib modules,
## like `builtin`, `os`, `sync`, where they have demonstrated
## their usefulness by catching actual very hard to find bugs.
## The cost of this selective running is delayed feedback when
## there are bugs in other V modules.
## The positive is *much faster CI runs* for most V contributors,
## that make PRs that are not concerning V itself, or the critical
## V modules.
on:
workflow_dispatch:
push:
branches:
- master
paths:
- '!**'
- '!**.md'
- '!**.yml'
- 'vlib/builtin/**.v'
- 'vlib/strconv/**.v'
- 'vlib/strings/**.v'
- 'vlib/math/**.v'
- 'vlib/math/big/**.v'
- 'vlib/arrays/**.v'
- 'vlib/crypto/ecdsa/**.v'
- 'vlib/datatypes/**.v'
- 'vlib/os/**.v'
- 'vlib/sync/**.v'
- 'vlib/v/tests/**.v'
- 'vlib/v/ast/**.v'
- 'vlib/v/scanner/**.v'
- 'vlib/v/parser/**.v'
- 'vlib/v/checker/**.v'
- 'vlib/v/gen/c/**.v'
- 'vlib/v/builder/**.v'
- 'vlib/v/cflag/**.v'
- 'vlib/v/live/**.v'
- 'vlib/v/util/**.v'
- 'vlib/v/markused/**.v'
- 'vlib/v/preludes/**.v'
- 'vlib/v/embed_file/**.v'
- 'vlib/x/json2/**.v'
- '**/sanitized_ci.yml'
pull_request:
paths:
- '!**'
- 'vlib/builtin/**.v'
- 'vlib/strconv/**.v'
- 'vlib/strings/**.v'
- 'vlib/math/**.v'
- 'vlib/math/big/**.v'
- 'vlib/arrays/**.v'
- 'vlib/crypto/ecdsa/**.v'
- 'vlib/datatypes/**.v'
- 'vlib/os/**.v'
- 'vlib/sync/**.v'
- 'vlib/v/tests/**.v'
- 'vlib/v/ast/**.v'
- 'vlib/v/scanner/**.v'
- 'vlib/v/parser/**.v'
- 'vlib/v/checker/**.v'
- 'vlib/v/gen/c/**.v'
- 'vlib/v/builder/**.v'
- 'vlib/v/cflag/**.v'
- 'vlib/v/live/**.v'
- 'vlib/v/util/**.v'
- 'vlib/v/markused/**.v'
- 'vlib/v/preludes/**.v'
- 'vlib/v/embed_file/**.v'
- 'vlib/x/json2/**.v'
- '**/sanitized_ci.yml'
concurrency:
group: sanitized-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
sanitize-undefined-clang:
runs-on: ubuntu-22.04
timeout-minutes: 120
env:
VFLAGS: -cc clang -cflags -fno-omit-frame-pointer
VJOBS: 1
UBSAN_OPTIONS: print_stacktrace=1:halt_on_error=1:print_suppressions=0:suppressions=/home/runner/work/v/v/.github/workflows/run_sanitizers_undefined.suppressions
VNATIVE_SKIP_LIBC_VV: 1
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make -j4 && ./v symlink
- name: V doctor
run: ./v doctor
- name: Ensure code is well formatted
run: ./v -silent test-cleancode
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update
./v retry -- sudo apt install --quiet -y postgresql libpq-dev libssl-dev sqlite3 libsqlite3-dev valgrind
./v retry -- sudo apt install --quiet -y libfreetype6-dev libxi-dev libxcursor-dev libgl-dev libxrandr-dev libasound2-dev libegl-dev
./v retry -- sudo apt install clang
- name: Recompile V with -cstrict
run: ./v -cg -cstrict -o v cmd/v
- name: Self tests (-fsanitize=undefined)
run: |
./v -cflags -fsanitize=undefined -o v2 cmd/v
./v2 -cflags -fsanitize=undefined -silent test-self vlib
- name: Build examples (V compiled with -fsanitize=undefined)
run: ./v2 -silent build-examples
sanitize-undefined-gcc:
runs-on: ubuntu-22.04
timeout-minutes: 120
env:
VFLAGS: -cc gcc -cflags -fno-omit-frame-pointer
VJOBS: 1
UBSAN_OPTIONS: print_stacktrace=1:halt_on_error=1:print_suppressions=0:suppressions=/home/runner/work/v/v/.github/workflows/run_sanitizers_undefined.suppressions
VNATIVE_SKIP_LIBC_VV: 1
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make -j4 && ./v symlink
- name: V doctor
run: ./v doctor
- name: Ensure code is well formatted
run: ./v -silent test-cleancode
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update
./v retry -- sudo apt install --quiet -y postgresql libpq-dev libssl-dev sqlite3 libsqlite3-dev valgrind
./v retry -- sudo apt install --quiet -y libfreetype6-dev libxi-dev libxcursor-dev libgl-dev libxrandr-dev libasound2-dev libegl-dev
- name: Recompile V with -cstrict
run: ./v -cg -cstrict -o v cmd/v
- name: Self tests (-fsanitize=undefined)
run: |
./v -cflags -fsanitize=undefined -o v2 cmd/v
./v2 -cflags -fsanitize=undefined -silent test-self vlib
- name: Build examples (V compiled with -fsanitize=undefined)
run: ./v2 -silent build-examples
sanitize-address-clang:
runs-on: ubuntu-22.04
timeout-minutes: 300
env:
VFLAGS: -cc clang -cflags -fno-omit-frame-pointer
VJOBS: 1
ASAN_OPTIONS: detect_leaks=1
LSAN_OPTIONS: max_leaks=1:print_suppressions=0:suppressions=/home/runner/work/v/v/.github/workflows/run_sanitizers_leak.suppressions
VNATIVE_SKIP_LIBC_VV: 1
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make -j4 && ./v symlink
- name: V doctor
run: ./v doctor
- name: Ensure code is well formatted
run: ./v -silent test-cleancode
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update
./v retry -- sudo apt install --quiet -y postgresql libpq-dev libssl-dev sqlite3 libsqlite3-dev valgrind
./v retry -- sudo apt install --quiet -y libfreetype6-dev libxi-dev libxcursor-dev libgl-dev libxrandr-dev libasound2-dev libegl-dev
./v retry -- sudo apt install clang
- name: Recompile V with -cstrict
run: ./v -cg -cstrict -o v cmd/v
- name: Self tests (-fsanitize=address)
run: ./v -cflags -fsanitize=address,pointer-compare,pointer-subtract -silent test-self vlib
- name: Test vlib/v/tests/ (V compiled with -fsanitize=address)
run: |
./v -cflags -fsanitize=address -o v cmd/v
./v -cc tcc -silent test-self -asan-compiler vlib/v/tests/
- name: Build examples (V compiled with -fsanitize=address)
run: ./v -silent build-examples
sanitize-address-msvc:
runs-on: windows-2025
timeout-minutes: 30
env:
VFLAGS: -cc msvc
VJOBS: 1
VNATIVE_SKIP_LIBC_VV: 1
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- name: Build
run: |
echo %VFLAGS%
echo $VFLAGS
.\makev.bat -msvc
.\v.exe self
- name: V doctor
run: .\v.exe doctor
- name: Ensure code is well formatted
run: .\v.exe -silent test-cleancode
# - name: Install dependencies
# run: |
# .\v.exe setup-freetype
# .\.github\workflows\windows-install-sqlite.bat
# - name: Self tests (/fsanitize=address) # TODO:
# run: .\v.exe -cflags "/fsanitize=address" -silent test-self vlib
sanitize-address-gcc:
runs-on: ubuntu-22.04
timeout-minutes: 300
env:
VFLAGS: -cc gcc -cflags -fno-omit-frame-pointer
VJOBS: 1
ASAN_OPTIONS: detect_leaks=1
LSAN_OPTIONS: max_leaks=1:print_suppressions=0:suppressions=/home/runner/work/v/v/.github/workflows/run_sanitizers_leak.suppressions
VNATIVE_SKIP_LIBC_VV: 1
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make -j4 && ./v symlink
- name: V doctor
run: ./v doctor
- name: Ensure code is well formatted
run: ./v -silent test-cleancode
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update
./v retry -- sudo apt install --quiet -y postgresql libpq-dev libssl-dev sqlite3 libsqlite3-dev valgrind
./v retry -- sudo apt install --quiet -y libfreetype6-dev libxi-dev libxcursor-dev libgl-dev libxrandr-dev libasound2-dev libegl-dev
./v retry -- sudo apt install clang
- name: Recompile V with -cstrict
run: ./v -cg -cstrict -o v cmd/v
- name: Self tests (-fsanitize=address)
run: ./v -cflags -fsanitize=address -silent test-self vlib
- name: Test vlib/v/tests/ (V compiled with -fsanitize=address)
run: |
./v -cflags -fsanitize=address,pointer-compare,pointer-subtract -o v cmd/v
./v -cc tcc -silent test-self -asan-compiler vlib/v/tests/
- name: Build examples (V compiled with -fsanitize=address)
run: ./v -silent build-examples
sanitize-memory-clang:
runs-on: ubuntu-22.04
timeout-minutes: 300
env:
VFLAGS: -cc clang -gc none -cflags -fno-omit-frame-pointer
VJOBS: 1
VNATIVE_SKIP_LIBC_VV: 1
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make -j4 && ./v symlink
- name: V doctor
run: ./v doctor
- name: Ensure code is well formatted
run: ./v -silent test-cleancode
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update
./v retry -- sudo apt install --quiet -y postgresql libpq-dev libssl-dev sqlite3 libsqlite3-dev valgrind
./v retry -- sudo apt install --quiet -y libfreetype6-dev libxi-dev libxcursor-dev libgl-dev libxrandr-dev libasound2-dev libegl-dev
./v retry -- sudo apt install clang
- name: Recompile V with clang and -cstrict
run: ./v -cc clang -cg -cstrict -o v cmd/v
- name: Self tests (-fsanitize=memory)
run: ./v -cflags -fsanitize=memory -silent test-self -msan-compiler vlib
- name: Test vlib/v/tests/ (V compiled with -fsanitize=memory)
run: |
./v -cflags -fsanitize=memory -o v cmd/v
./v -cc tcc -silent test-self -msan-compiler vlib/v/tests/
- name: Build examples (V compiled with -fsanitize=memory)
run: ./v -silent build-examples
sanitize-address-clang-without-gc:
runs-on: ubuntu-22.04
timeout-minutes: 300
env:
VFLAGS: -cc clang -gc none -cflags -fno-omit-frame-pointer
VJOBS: 1
LSAN_OPTIONS: detect_leaks=0
VNATIVE_SKIP_LIBC_VV: 1
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make -j4 && ./v symlink
- name: V doctor
run: ./v doctor
- name: Ensure code is well formatted
run: ./v -silent test-cleancode
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
./v retry -- sudo apt update
./v retry -- sudo apt install --quiet -y postgresql libpq-dev libssl-dev sqlite3 libsqlite3-dev valgrind
./v retry -- sudo apt install --quiet -y libfreetype6-dev libxi-dev libxcursor-dev libgl-dev libxrandr-dev libasound2-dev libegl-dev
./v retry -- sudo apt install clang
- name: Recompile V with -cstrict
run: ./v -cg -cstrict -o v cmd/v
- name: Self tests (-fsanitize=address)
run: ./v -cflags -fsanitize=address -silent test-self vlib
+76
View File
@@ -0,0 +1,76 @@
name: sdl CI
on:
workflow_dispatch:
push:
branches:
- master
paths:
- 'vlib/**'
- 'thirdparty/**'
- 'cmd/tools/builders/**.v'
- 'cmd/tools/vshader.v'
- '**/sdl_ci.yml'
- '!**.md'
pull_request:
paths:
- 'vlib/**'
- 'thirdparty/**'
- 'cmd/tools/builders/**.v'
- 'cmd/tools/vshader.v'
- '**/sdl_ci.yml'
- '!**.md'
concurrency:
group: sdl-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
v-compiles-sdl-examples:
runs-on: ubuntu-24.04
timeout-minutes: 20
env:
VFLAGS: -cc tcc
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build V
run: make && sudo ./v symlink
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
v retry 'sudo apt update'
v retry 'sudo apt install -y libsdl2-dev libsdl2-ttf-dev'
v retry 'sudo apt install -y libsdl2-mixer-dev libsdl2-image-dev'
- name: Clone sdl into .vmodules
run: |
v retry 'git clone --filter=blob:none https://github.com/vlang/sdl'
cd sdl
mkdir -p ~/.vmodules
ln -s "$(pwd)" ~/.vmodules/sdl
- name: Ensure SDL setup works
run: ./v ~/.vmodules/sdl/setup.vsh
- name: Run tests
run: ./v test sdl
- name: Build sdl shared
run: ./v -shared -g sdl
- name: Build sdl examples
run: |
v shader sdl/examples/sdl_opengl_and_sokol
v should-compile-all sdl/examples/
~/.vmodules/sdl/examples/versions/main
- name: Check SDL works, when installed through vpm
run: |
rm -rf sdl/
rm -rf ~/.vmodules/sdl
v retry 'v install sdl'
ls -la ~/.vmodules/sdl/
v ~/.vmodules/sdl/setup.vsh
v run ~/.vmodules/sdl/examples/versions
+47
View File
@@ -0,0 +1,47 @@
module main
import os
import time
import term
fn iso_week_year(t time.Time) int {
// ISO 8601 assigns a date to the year of the Thursday in its week.
return t.add_days(4 - t.day_of_week()).year
}
fn default_release_tag_for(t time.Time) string {
return 'weekly.${iso_week_year(t):04}.${t.week_of_year():02}'
}
fn release_time() time.Time {
now_override := os.getenv('V_RELEASE_TAG_NOW')
if now_override != '' {
return time.parse(now_override) or {
panic('invalid V_RELEASE_TAG_NOW `${now_override}`: ${err}')
}
}
return time.now()
}
fn main() {
now := release_time()
mut remote_name := 'origin'
mut release_tag := default_release_tag_for(now)
if os.args.len > 1 {
remote_name = os.args[1]
}
if os.args.len > 2 {
release_tag = os.args[2]
}
println('## Usage: show_manual_release_cmd.vsh [REMOTE] [TAGNAME]')
println('## current remote_name: ${remote_name}')
println('## current release_tag: ${release_tag}')
println('## ▼▼▼ ${term.ecolorize(term.yellow,
'run the following, to make a new github release')} ▼▼▼ ')
git_cmd := 'git tag -s -m "releases: ${release_tag}" ${release_tag} && git push --atomic ${remote_name} ${release_tag}'
println(git_cmd)
}
+48
View File
@@ -0,0 +1,48 @@
name: SSA backends CI
on:
push:
paths:
- 'vlib/v2_toberemoved/**'
- 'cmd/tinyv/**'
- '.github/workflows/ssa_backends_ci.yml'
pull_request:
paths:
- 'vlib/v2_toberemoved/**'
- 'cmd/tinyv/**'
- '.github/workflows/ssa_backends_ci.yml'
concurrency:
group: ssa_backends-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
ssa-backends-linux:
runs-on: ubuntu-24.04
env:
VJOBS: 1
steps:
- uses: actions/checkout@v6
- name: Build V
run: make && ./v symlink
- name: Test native x64 backend
run: v run cmd/tinyv/test_ssa_backends.v
- name: Test cleanc backend
run: v run cmd/tinyv/test_ssa_backends.v cleanc
- name: Test c-ssa backend
run: v run cmd/tinyv/test_ssa_backends.v c
ssa-backends-macos:
runs-on: macos-14
env:
VJOBS: 1
steps:
- uses: actions/checkout@v6
- name: Build V
run: make -j4 && ./v symlink
- name: Test native arm64 backend
run: v run cmd/tinyv/test_ssa_backends.v
- name: Test cleanc backend
run: v run cmd/tinyv/test_ssa_backends.v cleanc
- name: Test c-ssa backend
run: v run cmd/tinyv/test_ssa_backends.v c
+79
View File
@@ -0,0 +1,79 @@
name: Symlink CI
on:
workflow_dispatch:
push:
branches:
- master
paths:
- 'cmd/tools/vsymlink/**.v'
- '.github/workflows/symlink_ci.yml'
pull_request:
paths:
- 'cmd/tools/vsymlink/**.v'
- '.github/workflows/symlink_ci.yml'
concurrency:
group: symlink-${{ github.workflow }}-${{ github.ref_name == 'master' && github.sha || github.ref_name }}
cancel-in-progress: true
jobs:
symlink-unix:
runs-on: ${{ matrix.os }}
strategy:
matrix:
os: [ubuntu-latest, macos-latest]
fail-fast: false
steps:
- uses: actions/checkout@v7
- name: Build V
run: make -j4
- name: Symlink
run: |
./v symlink
cd /tmp/ && v version
cd ~ && v version
echo 'println(123)' > hi.v
v run hi.v
- name: Unlink
run: |
rm "$(which v)"
v --version && exit 1 || exit 0
- name: Symlink (sudo)
run: |
sudo ./v symlink
cd /tmp/ && v version
cd ~ && v version
echo 'println(123)' > hi.v
v run hi.v
- name: Unlink
run: |
rm "$(which v)"
v --version && exit 1 || exit 0
- name: Symlink (-githubci)
run: ./v symlink -githubci
- name: Test after symlink with -githubci (in a separate script)
run: |
cd /tmp/ && v version
cd ~ && v version
echo 'println(123)' > hi.v
v run hi.v
symlink-windows:
runs-on: windows-2025
strategy:
matrix:
flags: ['', '-githubci']
fail-fast: false
steps:
- uses: actions/checkout@v7
- name: Build V
run: ./makev.bat
- name: Symlink
run: ./v symlink ${{ matrix.flags }}
- name: Check if V is usable
run: |
cd $RUNNER_TEMP && pwd && v version
cd ~ && pwd && v version
echo 'println(123)' > hi.v
v run hi.v
+129
View File
@@ -0,0 +1,129 @@
name: CI Termux
on:
workflow_dispatch:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/termux_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/termux_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
jobs:
termux-build:
runs-on: ubuntu-latest
timeout-minutes: 30
steps:
- uses: actions/checkout@v7
- name: Build and test in Termux
run: |
set -o xtrace
echo "$PWD"
whoami
touch outside_docker.txt
git log -n4
echo "running docker ..."
docker run --rm --mount type=bind,source=/home/runner/work/v/v,destination=/src -w /src termux/termux-docker:latest bash -c '
set -o xtrace
echo "running inside docker"
whoami
cp -r /src ~/vproject; cd ~/vproject
touch inside_docker.txt
ls -la
echo "previous TERMUX_VERSION: $TERMUX_VERSION"
export TERMUX_VERSION=0.118.3
echo "explicit TERMUX_VERSION: $TERMUX_VERSION"
bash .github/workflows/retry.sh pkg update -y
bash .github/workflows/retry.sh pkg install -y clang libexecinfo libgc libgc-static make git
git log -n4
VFLAGS="-cc cc" make
./v symlink
export PATH="$HOME/.local/bin:/usr/local/bin:$PATH"
v run examples/hello_world.v
v run examples/primes.v
v -e "import os; dump( os.user_os() )"
'
termux-build-arm64-tcc:
# Diagnostic job for vlang/v#27207: reproduces the Termux/AArch64 tcc
# bootstrap failure on a real arm64 runner so we can collect logs without
# local hardware. Allowed to fail until the upstream tcc AArch64 bug is
# resolved.
runs-on: ubuntu-24.04-arm
continue-on-error: true
timeout-minutes: 45
steps:
- uses: actions/checkout@v7
- name: Build in Termux (arm64, default tcc)
run: |
set -o xtrace
uname -a
docker run --rm --platform=linux/arm64 --mount type=bind,source=/home/runner/work/v/v,destination=/src -w /src termux/termux-docker:aarch64 bash -c '
set -o xtrace
uname -a
cp -r /src ~/vproject; cd ~/vproject
export TERMUX_VERSION=0.118.3
bash .github/workflows/retry.sh pkg update -y
bash .github/workflows/retry.sh pkg install -y clang libexecinfo libgc libgc-static make git gdb file
git log -n4
ulimit -c unlimited || true
# Explicit `-cc tcc` is required: on Linux arm64 the Makefile
# otherwise injects `-cc "$(CC)"` (see GNUmakefile:149-155) and
# the bundled tcc path would never run — defeating the purpose
# of this diagnostic job for #27207. Capture every invocation
# via -showcc and the full build output to build.log.
set +e
VFLAGS="-cc tcc -showcc -stats" make 2>&1 | tee build.log
rc=${PIPESTATUS[0]}
set -e
echo "make exit code: $rc"
# Always copy the log back to the bind-mounted dir so the runner
# step that uploads the artifact can find it.
cp build.log /src/build.log || true
if [ "$rc" -ne 0 ] || [ ! -x ./v ]; then
echo "===== bootstrap failed; collecting diagnostics ====="
echo "--- tcc binary ---"
ls -la thirdparty/tcc/ 2>/dev/null || true
for t in thirdparty/tcc/tcc.exe thirdparty/tcc/tcc; do
if [ -x "$t" ]; then "$t" -v || true; fi
done
echo "--- last 120 lines of build.log ---"
tail -n 120 build.log || true
echo "--- v1/v2/v file info ---"
file v1 v2 v 2>/dev/null || true
echo "--- last tcc invocations from build.log ---"
grep -E "tcc(\.exe)? " build.log | tail -n10 || true
echo "--- core files (if any) ---"
ls -la core* 2>/dev/null || true
for c in core core.*; do
if [ -f "$c" ] && [ -x ./v2 ]; then
echo "--- gdb backtrace from $c against v2 ---"
gdb --batch --ex bt --ex "info registers" ./v2 "$c" || true
fi
done
# If make exited 0 but ./v is missing, force a nonzero exit so
# the diagnostic job does not go green without a usable compiler.
if [ "$rc" -eq 0 ]; then rc=1; fi
exit "$rc"
fi
echo "===== bootstrap succeeded ====="
./v -version
./v run examples/hello_world.v
'
- name: Upload build log
if: always()
uses: actions/upload-artifact@v7
with:
name: termux-arm64-build-log
path: build.log
if-no-files-found: ignore
+73
View File
@@ -0,0 +1,73 @@
name: Time CI
on:
push:
branches:
- master
paths:
- 'vlib/**'
- 'cmd/tools/builders/**.v'
- '**/time_ci.yml'
- '!**.md'
pull_request:
paths:
- 'vlib/**'
- 'cmd/tools/builders/**.v'
- '**/time_ci.yml'
- '!**.md'
concurrency:
group: time-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
time-linux:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v7
- name: Build V
run: make
- name: Test time functions in a timezone UTC-12
run: TZ=Etc/GMT+12 ./v test vlib/time/
- name: Test time functions in a timezone UTC-3
run: TZ=Etc/GMT+3 ./v test vlib/time/
- name: Test time functions in a timezone UTC+3
run: TZ=Etc/GMT-3 ./v test vlib/time/
- name: Test time functions in a timezone UTC+12
run: TZ=Etc/GMT-12 ./v test vlib/time/
- name: Test in a timezone using daylight saving (Europe/Paris)
run: TZ=Europe/Paris ./v test vlib/time/
time-macos:
runs-on: macos-14
steps:
- uses: actions/checkout@v7
- name: Build V
run: make
- name: Test time functions in a timezone UTC-12
run: TZ=Etc/GMT+12 ./v test vlib/time/
- name: Test time functions in a timezone UTC-3
run: TZ=Etc/GMT+3 ./v test vlib/time/
- name: Test time functions in a timezone UTC+3
run: TZ=Etc/GMT-3 ./v test vlib/time/
- name: Test time functions in a timezone UTC+12
run: TZ=Etc/GMT-12 ./v test vlib/time/
- name: Test in a timezone using daylight saving (Europe/Paris)
run: TZ=Europe/Paris ./v test vlib/time/
time-windows:
runs-on: windows-2025
steps:
- uses: actions/checkout@v7
- name: Build V
run: .\makev.bat
- name: Test time functions in a timezone UTC-12
run: tzutil /s "Dateline Standard Time" && ./v test vlib/time/
- name: Test time functions in a timezone UTC-3
run: tzutil /s "Greenland Standard Time" && ./v test vlib/time/
- name: Test time functions in a timezone UTC+3
run: tzutil /s "Russian Standard Time" && ./v test vlib/time/
- name: Test time functions in a timezone UTC+12
run: tzutil /s "New Zealand Standard Time" && ./v test vlib/time/
- name: Test in a timezone using daylight saving (Europe/Paris)
run: tzutil /s "W. Europe Standard Time" && ./v test vlib/time/
+42
View File
@@ -0,0 +1,42 @@
name: toml CI
on:
push:
branches:
- master
paths:
- 'vlib/**'
- '**/toml_ci.yml'
- '!**.md'
pull_request:
paths:
- 'vlib/**'
- '**/toml_ci.yml'
- '!**.md'
concurrency:
group: toml-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
toml-module-pass-external-test-suites:
runs-on: ubuntu-latest
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Build V
run: make -j4 && ./v symlink
- name: Install dependencies
run: |
v retry -- v download https://github.com/jqlang/jq/releases/download/jq-1.6/jq-linux64
sudo chmod 755 jq-linux64
sudo mv jq-linux64 /usr/bin/jq
- name: Show JQ Version
run: jq --version
- name: Download more TOML testsuits
run: .github/workflows/download_full_toml_test_suites.sh
- name: Run TOML tests
run: VTEST_TOML_DO_YAML_CONVERSION=1 VTEST_TOML_DO_LARGE_FILES=1 ./v test vlib/toml
+258
View File
@@ -0,0 +1,258 @@
name: Tools CI
on:
push:
branches:
- master
paths:
- 'cmd/**'
- '!cmd/tools/vpm/**'
- 'vlib/**'
- 'thirdparty/**'
- '!**.md'
- '**/tools_ci.yml'
pull_request:
paths:
- 'cmd/**'
- '!cmd/tools/vpm/**'
- 'vlib/**'
- 'thirdparty/**'
- '!**.md'
- '**/tools_ci.yml'
concurrency:
group: tools-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
tools-linux:
runs-on: ubuntu-22.04
timeout-minutes: 20
strategy:
matrix:
cc: [tcc, gcc, clang]
fail-fast: false
env:
VFLAGS: -cc ${{ matrix.cc }}
steps:
- uses: actions/checkout@v7
- name: Build V
run: make && ./v -showcc -o v cmd/v && ./v symlink && ./v doctor
- name: Code in cmd/ is formatted
run: ./v fmt -verify cmd/
- name: Check build-tools
run: ./v -silent -N -W -check build-tools
- name: Test tools
run: ./v -silent test-self cmd
- name: Test tools (-cstrict)
if: ${{ matrix.cc != 'tcc' }}
run: ./v -silent -W -cstrict test-self cmd
- name: Test sanitized
if: ${{ matrix.cc != 'tcc' }}
run: |
export VNATIVE_SKIP_LIBC_VV=1
if [[ ${{ matrix.cc }} == "clang" ]]; then
cmd="./v -silent -cc clang -cflags -fsanitize=undefined test-self -ubsan-compiler cmd"
echo "$cmd" && $cmd
cmd="./v -silent -gc none -cc clang -cflags -fsanitize=memory test-self -msan-compiler cmd"
echo "$cmd" && $cmd
else
cmd="./v -silent -cc gcc -cflags -fsanitize=thread test-self cmd"
echo "$cmd" && $cmd
cmd="./v -silent -cc gcc -cflags -fsanitize=address,leak,undefined,shift,shift-exponent,shift-base,integer-divide-by-zero,unreachable,vla-bound,null,return,signed-integer-overflow,bounds,bounds-strict,alignment,object-size,float-divide-by-zero,float-cast-overflow,nonnull-attribute,returns-nonnull-attribute,bool,enum,vptr test-self -asan-compiler cmd/tools"
echo "$cmd" && $cmd
## cmd="./v -silent -cc gcc -cflags -fsanitize=kernel-address test-self -asan-compiler cmd"
## echo "$cmd" && $cmd
fi
tools-macos:
runs-on: macos-14
timeout-minutes: 20
strategy:
matrix:
cc: [clang]
fail-fast: false
env:
VFLAGS: -cc ${{ matrix.cc }}
steps:
- uses: actions/checkout@v7
- name: Build V
run: make && ./v -showcc -o v cmd/v && ./v symlink && ./v doctor
- name: Check build-tools
run: ./v -silent -N -W -check build-tools
- name: Test tools
run: ./v -silent test-self cmd
- name: Test tools (-cstrict)
run: ./v -silent -W -cstrict test-self cmd
tools-windows:
runs-on: windows-2025
timeout-minutes: 20
strategy:
matrix:
cc: [tcc, gcc, msvc]
fail-fast: false
env:
VFLAGS: -cc ${{ matrix.cc }}
steps:
- uses: actions/checkout@v7
- name: Build V
run: ./makev.bat -${{ matrix.cc }} && ./v -o v2.exe cmd/v && ./v2 -showcc -o v.exe cmd/v && ./v symlink && ./v doctor
- name: Install SQLite (needed by vsqlite tool)
run: .\.github\workflows\windows-install-sqlite.bat
- name: Check build tools
run: ./v build-tools
- name: Test tools
run: ./v -silent test-self cmd
- name: Test tools (-cstrict)
if: ${{ matrix.cc == 'msvc' }}
run: ./v -silent -W -cstrict test-self cmd
tools-docker-ubuntu-musl:
runs-on: ubuntu-24.04
timeout-minutes: 20
container:
image: thevlang/vlang:ubuntu-build
env:
V_CI_MUSL: 1
V_CI_UBUNTU_MUSL: 1
VFLAGS: -cc musl-gcc -gc none
volumes:
- ${{github.workspace}}:/opt/vlang
steps:
- name: Checkout
uses: actions/checkout@v7
- name: Build V
run: make && ./v -cg -o v cmd/v && ./v symlink
- name: Ensure git commands can be used with no prompts on modern Git versions
run: git config --global --add safe.directory /__w/v/v
- name: Verify `v test` works
run: |
./v cmd/tools/test_if_v_test_system_works.v
./cmd/tools/test_if_v_test_system_works
- name: Check build tools
run: ./v -silent -N -W -check build-tools
- name: Test tools
run: ./v -silent test-self cmd
- name: Test tools (-cstrict)
run: ./v -silent -W -cstrict test-self cmd
tools-freebsd:
runs-on: ubuntu-latest
timeout-minutes: 20
strategy:
matrix:
cc: [tcc, gcc, clang]
fail-fast: false
env:
VFLAGS: -cc ${{ matrix.cc }}
steps:
- uses: actions/checkout@v7
- name: Start FreeBSD VM with ${{ matrix.cc }}
uses: cross-platform-actions/action@v1.2.0
with:
operating_system: freebsd
version: '15.0'
memory: 4G
shell: sh
sync_files: runner-to-vm
environment_variables: VFLAGS
- name: Tests tools on FreeBSD with ${{ matrix.cc }}
shell: cpa.sh {0}
run: |
sudo pkg install -y git sqlite3 gmake boehm-gc-threaded libiconv
if [ "$VFLAGS" = "-cc gcc" ]; then
sudo pkg install -y gcc
fi
# Mandatory: hostname not set in VM => some tests fail
sudo hostname -s freebsd-ci
echo "::group::OS infos"
uname -a
echo "::endgroup::"
# Build V
echo "::group::Build V"
git config --global --add safe.directory .
printf "VFLAGS = %s\n" "$VFLAGS"
gmake && ./v -showcc -o v cmd/v && sudo ./v symlink
echo "::endgroup::"
echo "::group::v doctor"
./v doctor
echo "::endgroup::"
# Code in cmd/ is formatted
echo "::group::Check code in cmd/ is formatted"
./v fmt -verify cmd/
echo "::endgroup::"
# Check build-tools
echo "::group::Check build tools"
./v -silent -N -W -check build-tools
echo "::endgroup::"
# Test tools
echo "::group::Test tools"
./v -silent test-self cmd
echo "::endgroup::"
# Test tools (-cstrict)
if [ "$VFLAGS" != "-cc tcc" ]; then
echo "::group::Test tools (-cstrict)"
./v -silent -W -cstrict test-self cmd
echo "::endgroup::"
fi
tools-openbsd:
runs-on: ubuntu-latest
timeout-minutes: 20
strategy:
matrix:
cc: [tcc, clang]
fail-fast: false
env:
VFLAGS: -cc ${{ matrix.cc }}
steps:
- uses: actions/checkout@v7
- name: Start OpenBSD VM with ${{ matrix.cc }}
uses: cross-platform-actions/action@v1.2.0
with:
operating_system: openbsd
version: '7.8'
memory: 4G
sync_files: runner-to-vm
environment_variables: VFLAGS
- name: Tests tools on OpenBSD with ${{ matrix.cc }}
shell: cpa.sh {0}
run: |
sudo pkg_add git sqlite3 gmake boehm-gc libiconv
# Mandatory: hostname not set in VM => some tests fail
sudo hostname -s openbsd-ci
echo "::group::OS infos"
uname -a
echo "::endgroup::"
# Build V
echo "::group::Build V"
git config --global --add safe.directory .
printf "VFLAGS = %s\n" "$VFLAGS"
gmake && ./v -showcc -o v cmd/v && sudo ./v symlink
echo "::endgroup::"
echo "::group::v doctor"
./v doctor
echo "::endgroup::"
# Code in cmd/ is formatted
echo "::group::Check code in cmd/ is formatted"
./v fmt -verify cmd/
echo "::endgroup::"
# Check build-tools
echo "::group::Check build tools"
./v -silent -N -W -check build-tools
echo "::endgroup::"
# Test tools
echo "::group::Test tools"
./v -silent test-self cmd
echo "::endgroup::"
# Test tools (-cstrict)
if [ "$VFLAGS" != "-cc tcc" ]; then
echo "::group::Test tools (-cstrict)"
./v -silent -W -cstrict test-self cmd
echo "::endgroup::"
fi
+216
View File
@@ -0,0 +1,216 @@
name: Update tccbin
on:
workflow_dispatch:
inputs:
tcc_commit:
description: 'TinyCC ref, branch, or commit to build'
required: false
default: mob
publish:
description: 'Push the rebuilt bundle to vlang/tccbin'
type: boolean
required: false
default: false
force_rebuild:
description: 'Rebuild even when tccbin already records the same TinyCC hash'
type: boolean
required: false
default: false
schedule:
- cron: '17 3 1 * *'
permissions:
contents: read
concurrency:
group: update-tccbin-${{ github.ref }}
cancel-in-progress: false
jobs:
update-tccbin-hosted:
if: github.repository == 'vlang/v' && (github.event_name != 'schedule' || github.ref == 'refs/heads/master')
strategy:
fail-fast: false
matrix:
include:
- id: linux-amd64
os: ubuntu-latest
branch: thirdparty-linux-amd64
script: thirdparty/build_scripts/thirdparty-linux-amd64_tcc.sh
- id: macos-amd64
os: macos-15-intel
branch: thirdparty-macos-amd64
script: thirdparty/build_scripts/thirdparty-macos-amd64_tcc.sh
- id: macos-arm64
os: macos-latest
branch: thirdparty-macos-arm64
script: thirdparty/build_scripts/thirdparty-macos-arm64_tcc.sh
runs-on: ${{ matrix.os }}
env:
TCC_COMMIT: ${{ github.event.inputs.tcc_commit || 'mob' }}
TCCBIN_REPO: vlang/tccbin
PUBLISH: ${{ github.event_name == 'schedule' || github.event.inputs.publish == 'true' }}
FORCE_REBUILD: ${{ github.event.inputs.force_rebuild == 'true' }}
steps:
- uses: actions/checkout@v7
- name: Install macOS build dependencies
if: runner.os == 'macOS'
run: brew install make
- name: Resolve TinyCC source hash
id: tinycc
shell: bash
run: |
set -euo pipefail
git clone --quiet https://repo.or.cz/tinycc.git /tmp/tinycc-ref
git -C /tmp/tinycc-ref checkout --quiet "$TCC_COMMIT"
hash="$(git -C /tmp/tinycc-ref rev-parse HEAD)"
echo "hash=$hash" >> "$GITHUB_OUTPUT"
echo "TinyCC $TCC_COMMIT resolves to $hash"
- name: Clone tccbin branch
shell: bash
env:
TCCBIN_TOKEN: ${{ secrets.VLANG_BOT_SECRET }}
run: |
set -euo pipefail
git clone --branch "${{ matrix.branch }}" --depth=1 \
"https://github.com/${TCCBIN_REPO}.git" thirdparty/tcc
if [ "$PUBLISH" = 'true' ]; then
if [ -z "$TCCBIN_TOKEN" ]; then
echo "::error::VLANG_BOT_SECRET is required to publish to ${TCCBIN_REPO}"
exit 1
fi
git -C thirdparty/tcc remote set-url origin \
"https://vlang-bot:${TCCBIN_TOKEN}@github.com/${TCCBIN_REPO}.git"
fi
- name: Check whether rebuild is needed
id: rebuild
shell: bash
run: |
set -euo pipefail
if [ "$FORCE_REBUILD" != 'true' ] \
&& [ -f thirdparty/tcc/build_source_hash.txt ] \
&& [ "$(cat thirdparty/tcc/build_source_hash.txt)" = "${{ steps.tinycc.outputs.hash }}" ]; then
echo "skip=true" >> "$GITHUB_OUTPUT"
echo "tccbin/${{ matrix.branch }} already has TinyCC ${{ steps.tinycc.outputs.hash }}"
else
echo "skip=false" >> "$GITHUB_OUTPUT"
fi
- name: Configure git identity
if: steps.rebuild.outputs.skip != 'true'
run: |
git config --global user.name vlang-bot
git config --global user.email vlang-bot@users.noreply.github.com
- name: Build TCC bundle
if: steps.rebuild.outputs.skip != 'true'
shell: bash
env:
BUILD_CMD: TCC_COMMIT=${{ env.TCC_COMMIT }} TCC_FOLDER=thirdparty/tcc bash ${{ matrix.script }}
run: |
set -euo pipefail
TCC_FOLDER=thirdparty/tcc bash "${{ matrix.script }}"
test "$(cat thirdparty/tcc/build_source_hash.txt)" = "${{ steps.tinycc.outputs.hash }}"
thirdparty/tcc/tcc.exe --version
thirdparty/tcc/tcc.exe -v -v
- name: Upload TCC bundle artifact
if: steps.rebuild.outputs.skip != 'true'
uses: actions/upload-artifact@v7
with:
name: tccbin-${{ matrix.id }}
path: thirdparty/tcc
- name: Push tccbin branch
if: steps.rebuild.outputs.skip != 'true' && env.PUBLISH == 'true'
shell: bash
run: |
set -euo pipefail
git -C thirdparty/tcc push origin HEAD:${{ matrix.branch }}
update-tccbin-bsd:
if: github.repository == 'vlang/v' && (github.event_name != 'schedule' || github.ref == 'refs/heads/master')
strategy:
fail-fast: false
matrix:
include:
- id: freebsd-amd64
operating_system: freebsd
version: '15.0'
branch: thirdparty-freebsd-amd64
script: thirdparty/build_scripts/thirdparty-freebsd-amd64_tcc.sh
install: sudo pkg install -y bash git gmake rsync
cc: cc
- id: openbsd-amd64
operating_system: openbsd
version: '7.8'
branch: thirdparty-openbsd-amd64
script: thirdparty/build_scripts/thirdparty-openbsd-amd64_tcc.sh
install: sudo pkg_add bash git gmake rsync
cc: clang
runs-on: ubuntu-latest
env:
TCC_COMMIT: ${{ github.event.inputs.tcc_commit || 'mob' }}
TCCBIN_REPO: vlang/tccbin
PUBLISH: ${{ github.event_name == 'schedule' || github.event.inputs.publish == 'true' }}
FORCE_REBUILD: ${{ github.event.inputs.force_rebuild == 'true' }}
TCCBIN_TOKEN: ${{ secrets.VLANG_BOT_SECRET }}
steps:
- uses: actions/checkout@v7
- name: Start ${{ matrix.id }} VM
uses: cross-platform-actions/action@v1.2.0
with:
operating_system: ${{ matrix.operating_system }}
version: ${{ matrix.version }}
memory: 4G
shell: sh
sync_files: runner-to-vm
environment_variables: TCC_COMMIT TCCBIN_REPO PUBLISH FORCE_REBUILD TCCBIN_TOKEN
- name: Build and publish ${{ matrix.id }} TCC bundle
shell: cpa.sh {0}
run: |
set -eu
${{ matrix.install }}
git config --global user.name vlang-bot
git config --global user.email vlang-bot@users.noreply.github.com
git config --global --add safe.directory "$PWD"
git clone --quiet https://repo.or.cz/tinycc.git /tmp/tinycc-ref
git -C /tmp/tinycc-ref checkout --quiet "$TCC_COMMIT"
tinycc_hash="$(git -C /tmp/tinycc-ref rev-parse HEAD)"
echo "TinyCC $TCC_COMMIT resolves to $tinycc_hash"
git clone --branch "${{ matrix.branch }}" --depth=1 \
"https://github.com/${TCCBIN_REPO}.git" thirdparty/tcc
if [ "$PUBLISH" = 'true' ]; then
if [ -z "$TCCBIN_TOKEN" ]; then
echo "VLANG_BOT_SECRET is required to publish to ${TCCBIN_REPO}" >&2
exit 1
fi
git -C thirdparty/tcc remote set-url origin \
"https://vlang-bot:${TCCBIN_TOKEN}@github.com/${TCCBIN_REPO}.git"
fi
if [ "$FORCE_REBUILD" != 'true' ] \
&& [ -f thirdparty/tcc/build_source_hash.txt ] \
&& [ "$(cat thirdparty/tcc/build_source_hash.txt)" = "$tinycc_hash" ]; then
echo "tccbin/${{ matrix.branch }} already has TinyCC $tinycc_hash"
exit 0
fi
BUILD_CMD="TCC_COMMIT=$TCC_COMMIT TCC_FOLDER=thirdparty/tcc CC=${{ matrix.cc }} bash ${{ matrix.script }}" \
TCC_FOLDER=thirdparty/tcc CC="${{ matrix.cc }}" bash "${{ matrix.script }}"
test "$(cat thirdparty/tcc/build_source_hash.txt)" = "$tinycc_hash"
thirdparty/tcc/tcc.exe --version
thirdparty/tcc/tcc.exe -v -v
if [ "$PUBLISH" = 'true' ]; then
git -C thirdparty/tcc push origin HEAD:${{ matrix.branch }}
fi
@@ -0,0 +1,267 @@
name: V Apps and Modules
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/v_apps_and_modules_compile_ci.yml'
- 'examples/**'
- 'cmd/tools/vrepl.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/v_apps_and_modules_compile_ci.yml'
- 'examples/**'
- 'cmd/tools/vrepl.v'
concurrency:
group: v_apps-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
v-apps-compile:
strategy:
matrix:
os: [ubuntu-latest, macos-14]
fail-fast: false
runs-on: ${{ matrix.os }}
timeout-minutes: 60
steps:
- uses: actions/checkout@v7
- name: Cache apt packages
if: runner.os == 'Linux'
uses: ./.github/actions/cache-apt-packages-action
- name: Cache Homebrew downloads
if: runner.os == 'macOS'
uses: actions/cache@v5
with:
path: ~/Library/Caches/Homebrew
key: brew-${{ matrix.os }}-v_apps-${{ hashFiles('.github/workflows/v_apps_and_modules_compile_ci.yml') }}
restore-keys: |
brew-${{ matrix.os }}-v_apps-
brew-${{ matrix.os }}-
- name: Build V
id: build
run: make && sudo ./v symlink
- name: Install dependencies
run: |
if [ "$RUNNER_OS" == 'Linux' ]; then
.github/workflows/disable_azure_mirror.sh
v retry -- sudo apt -qq update
v retry -- sudo apt -qq install libgc-dev libsodium-dev libssl-dev sqlite3 libsqlite3-dev
v retry -- sudo apt -qq install libfreetype6-dev libxi-dev libxcursor-dev libgl-dev libxrandr-dev libasound2-dev xfonts-75dpi xfonts-base libegl-dev libharfbuzz-dev libfribidi-dev libfontconfig1-dev libpango1.0-dev libglib2.0-dev libdbus-1-dev
v retry -- sudo apt -qq install sassc libgit2-dev # needed by gitly
v retry -- sudo apt -qq install libunwind-18-dev # needed by v-analyzer for libbacktrace
else
v retry brew install sassc libgit2 libsodium pango fribidi pkg-config
fi
- name: Build docs generator
run: |
v retry -- v install markdown
v retry -- git clone https://github.com/vlang/docs --branch generator --depth 1
cd docs
v .
- name: Test vtcc
if: runner.os == 'macOS'
run: .github/workflows/compile_v_with_vtcc.sh
- name: Test vsql compilation and examples
if: ${{ false && !cancelled() && steps.build.outcome == 'success' }}
run: |
echo "Install vsql"
v retry -- v install elliotchance.vsql
cd ~/.vmodules/elliotchance/vsql
echo "Compile vsql"
make bin/vsql
echo "Run examples"
make examples
echo "Run vsql/connection_test.v"
v vsql/connection_test.v
- name: Test vlang/gui
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: .github/workflows/compile_vlang_gui_examples.sh
- name: Test discord.v
if: ${{ false && !cancelled() && steps.build.outcome == 'success' }} # disabled: upstream uses deprecated json2.raw_decode
run: .github/workflows/compile_discordv.sh
- name: Build herolib
if: ${{ false && !cancelled() && steps.build.outcome == 'success' }}
run: .github/workflows/compile_herolib.sh
- name: Build vlang/vab
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
echo "Install VAB"
v retry -- v install vab
echo "Build vab"
v ~/.vmodules/vab
echo "Build vab with -g"
v -g ~/.vmodules/vab
- name: Build vlang/ved
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
v retry -- git clone --depth 1 https://github.com/vlang/ved
cd ved && v -o ved .
echo "Build"
v .
echo "Build with -autofree ..."
v -autofree .
echo "Build with -prod ..."
v -prod .
cd ..
- name: Build vlang/pdf
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
v retry -- v install pdf
echo "PDF examples should compile"
v should-compile-all ~/.vmodules/pdf/examples
- name: Build vlang/libsodium
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
echo "Install the libsodium wrapper"
v retry -- v install libsodium
echo "Test libsodium"
VJOBS=1 v test ~/.vmodules/libsodium
- name: Build vlang/coreutils
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
echo "Clone Coreutils"
v retry -- git clone --depth 1 https://github.com/vlang/coreutils /tmp/coreutils
echo "Build Coreutils"
cd /tmp/coreutils; make
- name: Build vlang/gitly
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
echo "Install markdown"
v retry -- v install markdown
echo "Install pcre"
v retry -- v install pcre
echo "Clone Gitly"
v retry -- git clone https://github.com/vlang/gitly /tmp/gitly
echo "Build Gitly"
v -cc gcc /tmp/gitly
## echo "Build Gitly with -autofree"
## v -cc gcc -autofree /tmp/gitly
echo "Compile gitly.css from gitly.scss"
sassc /tmp/gitly/static/css/gitly.scss > /tmp/gitly/static/css/gitly.css
# echo "Run first_run.v"
# v -cc gcc run /tmp/gitly/tests/first_run.v
# # /tmp/gitly/gitly -ci_run
- name: Build V UI examples
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
v retry -- v install ui
v -no-parallel ~/.vmodules/ui/examples/rectangles.v
v -no-parallel ~/.vmodules/ui/examples/users.v
# v run ~/.vmodules/ui/examples/build_examples.vsh
- name: Build vlang/v-analyzer
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
echo "Clone v-analyzer"
v retry -- git clone --depth=1 --branch=master --filter=blob:none --recursive --shallow-submodules https://github.com/vlang/v-analyzer /tmp/v-analyzer
cd /tmp/v-analyzer
echo "Installing dependencies"
v install
echo "Build v-analyzer debug"
v build.vsh debug
echo "Build v-analyzer release"
v build.vsh release
- name: Format vlang/v-analyzer
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
cd /tmp/v-analyzer
fmt_files=($(git ls-files '*.v' '*.vsh' ':!:metadata/stubs/*.v' ':!:src/metadata/stubs/*.v'))
set +e
v fmt -c "${fmt_files[@]}"
exit_code=$?
if [[ $exit_code -ne 0 && $exit_code -ne 5 ]]; then
# Don't fail if there are only internal errors (exit code 5).
v fmt -diff "${fmt_files[@]}"
exit 1
fi
- name: Build vlang/go2v
if: ${{ !cancelled() && steps.build.outcome == 'success' && matrix.os != 'macos-14' }}
run: |
echo "Clone Go2V"
v retry -- git clone --depth=1 https://github.com/vlang/go2v /tmp/go2v/
echo "Build Go2V"
v /tmp/go2v/
echo "Run Go2V tests"
VJOBS=1 v test /tmp/go2v/
- name: Install UI through VPM and make sure its examples compile
if: ${{ false && !cancelled() && steps.build.outcome == 'success' }} # disabled: upstream vlang/ui has unused parameter notices that fail with -N -W
run: |
echo "Official VPM modules should be installable"
v retry -- v install ui
echo "Examples of UI should compile"
v ~/.vmodules/ui/examples/build_examples.vsh
- name: Build vlang/adventofcode
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
echo "Clone the AdventOfCode repo"
v retry -- git clone --depth 1 https://github.com/vlang/adventofcode /tmp/adventofcode
echo "Install dependencies"
v retry -- v install pcre
echo "Execute Tests"
cd /tmp/adventofcode && v run verify.v
- name: Build vlang/msgpack
if: ${{ !cancelled() && steps.build.outcome == 'success' }}
run: |
echo "Install msgpack"
v retry -- v install msgpack
echo "Build msgpack"
v -shared ~/.vmodules/msgpack/
echo "Run msgpack tests"
v test ~/.vmodules/msgpack/
echo "MessagePack examples should compile"
v should-compile-all ~/.vmodules/msgpack/examples
# - name: Build VEX
# if: ${{ !cancelled() }} && steps.build.outcome == 'success'
# run: |
# echo "Install Vex"
# v retry -- v install nedpals.vex
# echo "Compile all of the Vex examples"
# v should-compile-all ~/.vmodules/nedpals/vex/examples
# echo "Compile the simple Vex example"
# v ~/.vmodules/nedpals/vex/examples/simple_example.v
# echo "Run Vex Tests"
# v test ~/.vmodules/nedpals/vex
vpm-site-compile:
strategy:
matrix:
os: [ubuntu-24.04, macos-14]
fail-fast: false
runs-on: ${{ matrix.os }}
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Build V
run: make && ./v symlink
- name: Build vpm
run: |
v retry -- v install markdown
v retry -- git clone --depth 1 https://github.com/vlang/vpm
cd vpm && v .
+90
View File
@@ -0,0 +1,90 @@
name: vab CI
on:
workflow_call:
push:
branches:
- master
paths:
- 'vlib/**'
- 'thirdparty/**'
- 'cmd/tools/builders/**.v'
- '**/vab_ci.yml'
- '!**.md'
pull_request:
paths:
- 'vlib/**'
- 'thirdparty/**'
- 'cmd/tools/builders/**.v'
- '**/vab_ci.yml'
- '!**.md'
concurrency:
group: vab-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
vab-compiles-v-examples:
runs-on: ubuntu-24.04
timeout-minutes: 20
env:
VAB_FLAGS: --api 30 --build-tools 29.0.0 -v 3
steps:
- uses: actions/setup-java@v5
with:
distribution: 'temurin'
java-version: 11
- uses: actions/checkout@v7
- name: Build V
run: make -j4 && ./v symlink
- name: Install vab
run: |
v retry -- v install vab
v -g ~/.vmodules/vab
sudo ln -s ~/.vmodules/vab/vab /usr/local/bin/vab
- name: Run tests
run: v -g test ~/.vmodules/vab
- name: Run vab --help
run: vab --help
- name: Run vab doctor
run: |
vab doctor
which d8 || true
which dx || true
- name: Build graphical V examples as APK
run: |
declare -a v_examples=('flappylearning' '2048' 'fireworks' 'tetris' 'sokol/particles' 'sokol/drawing.v' 'sokol/freetype_raven.v' 'gg/polygons.v' 'gg/raven_text_rendering.v' 'gg/rectangles.v' 'gg/stars.v' 'gg/worker_thread.v')
mkdir apks
for example in "${v_examples[@]}"; do
safe_name=$(echo "$example" | sed 's%/%-%' | sed 's%\.%-%' )
vab "examples/$example" -o "apks/$safe_name.apk"
done
v-compiles-os-android:
runs-on: ubuntu-24.04
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Build V
run: make -j4 && ./v symlink
- name: Install vab
run: |
v retry -- v install vab
v -g ~/.vmodules/vab
sudo ln -s ~/.vmodules/vab/vab /usr/local/bin/vab
- name: Run vab --help
run: vab --help
- name: Run vab doctor
run: vab doctor
- name: Check `v -os android` *without* -apk flag
run: .github/workflows/android_cross_compile.vsh
+81
View File
@@ -0,0 +1,81 @@
name: Build Vinix
on:
workflow_call:
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/vinix_ci.yml'
- 'cmd/tools/vrepl.v'
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/vinix_ci.yml'
- 'cmd/tools/vrepl.v'
concurrency:
group: vinix-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
vinix-build:
runs-on: ubuntu-24.04
timeout-minutes: 20
steps:
- uses: actions/checkout@v7
- name: Build V
run: make -j4 && ./v symlink
- name: Install dependencies
run: |
.github/workflows/disable_azure_mirror.sh
v retry -- sudo apt update
v retry -- sudo apt install build-essential -y
- name: Clone current Vinix
run: v retry -- git clone --depth=1 --branch master https://github.com/vlang/vinix.git
- name: Download Vinix kernel dependencies
run: cd vinix/kernel && v retry -- ./get-deps
- name: Attempt to build the Vinix kernel (debug)
run: |
set -e
cd vinix/kernel
make PROD=false \
CFLAGS="-Ulinux -U__linux -U__linux__ -U__gnu_linux__ -D__vinix__ -O2 -g -pipe" \
V="$(realpath ../../v)"
make clean
- name: Attempt to build the Vinix kernel (prod)
run: |
set -e
cd vinix/kernel
make PROD=true \
CFLAGS="-Ulinux -U__linux -U__linux__ -U__gnu_linux__ -D__vinix__ -O2 -g -pipe" \
V="$(realpath ../../v)"
make clean
- name: Attempt to build the util-vinix (debug)
run: |
set -e
cd vinix/util-vinix
make PROD=false \
VFLAGS="-os vinix -gc none" \
CFLAGS="-Ulinux -U__linux -U__linux__ -U__gnu_linux__ -D__vinix__ -O2 -g -pipe" \
V="$(realpath ../../v)"
make clean
- name: Attempt to build the util-vinix (prod)
run: |
set -e
cd vinix/util-vinix
make PROD=true \
VFLAGS="-os vinix -gc none" \
CFLAGS="-Ulinux -U__linux -U__linux__ -U__gnu_linux__ -D__vinix__ -O2 -g -pipe" \
V="$(realpath ../../v)"
make clean
+77
View File
@@ -0,0 +1,77 @@
name: VPM CI
on:
push:
branches:
- master
paths:
- '**/vpm_ci.yml'
- '**/cmd/tools/vpm/**'
pull_request:
paths:
- '**/vpm_ci.yml'
- '**/cmd/tools/vpm/**'
concurrency:
group: vpm-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
setup-vpm:
strategy:
matrix:
os: [ubuntu-latest, windows-latest, macos-latest]
fail-fast: false
runs-on: ${{ matrix.os }}
steps:
- uses: actions/checkout@v7
with:
path: vlang
- name: Show git version
run: git version
- name: Build V
if: runner.os != 'Windows'
run: cd vlang && make -j4 && ./v doctor
- name: Build V (Windows)
if: runner.os == 'Windows'
run: cd vlang && ./makev.bat && ./v doctor
- name: Cache V
uses: actions/cache/save@v5
with:
path: vlang
key: ${{ runner.os }}-${{ github.sha }}
test-vpm:
needs: setup-vpm
strategy:
matrix:
include:
- os: ubuntu-latest
cc: tcc
- os: ubuntu-latest
cc: gcc
- os: ubuntu-latest
cc: clang
- os: macos-latest
cc: clang
- os: windows-latest
cc: tcc
- os: windows-latest
cc: gcc
- os: windows-latest
cc: msvc
fail-fast: false
runs-on: ${{ matrix.os }}
steps:
- name: Restore V cache
uses: actions/cache/restore@v5
with:
path: vlang
key: ${{ runner.os }}-${{ github.sha }}
- name: Show git version
run: git version
- name: Build and test VPM
run: |
cd vlang
./v -W -N cmd/tools/vpm
./v -cc ${{ matrix.cc }} -d network test cmd/tools/vpm
+131
View File
@@ -0,0 +1,131 @@
name: VSL and VTL
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/vsl_and_vtl_compile_ci.yml'
- 'examples/**'
- 'cmd/tools/vrepl.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/vsl_and_vtl_compile_ci.yml'
- 'examples/**'
- 'cmd/tools/vrepl.v'
concurrency:
group: vsl-vtl-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
vsl-compiles:
strategy:
matrix:
os: [ubuntu-24.04, macos-14]
fail-fast: false
runs-on: ${{ matrix.os }}
timeout-minutes: 30
env:
VFLAGS: -no-parallel
steps:
- uses: actions/checkout@v7
- name: Cache apt packages
if: runner.os == 'Linux'
uses: ./.github/actions/cache-apt-packages-action
- name: Cache Homebrew downloads
if: runner.os == 'macOS'
uses: actions/cache@v5
with:
path: ~/Library/Caches/Homebrew
key: brew-${{ matrix.os }}-vsl-${{ hashFiles('.github/workflows/vsl_and_vtl_compile_ci.yml') }}
restore-keys: |
brew-${{ matrix.os }}-vsl-
brew-${{ matrix.os }}-
- name: Build V
id: build
run: make && sudo ./v symlink
- name: Install dependencies
run: |
if [ "$RUNNER_OS" == 'Linux' ]; then
.github/workflows/disable_azure_mirror.sh
v retry -- sudo apt -qq update
v retry -- sudo apt -qq install \
libgc-dev libgl1-mesa-dev mesa-common-dev liblapacke-dev libopenblas-dev libopenmpi-dev \
opencl-headers libvulkan-dev libxcursor-dev libxi-dev libxrandr-dev \
libhdf5-cpp-103-1t64 libhdf5-dev libhdf5-mpi-dev hdf5-tools
else
v retry brew install coreutils hdf5 open-mpi openblas lapack opencl-headers
fi
- name: Install vsl
run: v retry -- v install vsl
- name: Skip optional Vulkan examples on macOS
if: runner.os == 'macOS'
run: |
for file in "$HOME"/.vmodules/vsl/examples/*vulkan*/*.v; do
[ -e "$file" ] || continue
mv "$file" "${file%.v}_not_ci.v"
done
- name: Test with Pure V Backend
run: ~/.vmodules/vsl/bin/test
- name: Test with Pure V Backend and Pure V Math
run: ~/.vmodules/vsl/bin/test --use-cblas --skip-examples
vtl-compiles:
strategy:
matrix:
os: [ubuntu-24.04, macos-14]
fail-fast: false
runs-on: ${{ matrix.os }}
timeout-minutes: 25
env:
VFLAGS: -no-parallel
VJOBS: 1
# Fixes complaints about $TERM not being set when running the vtl test script
# (a warning on Linux, but an error on macOS).
TERM: xterm
steps:
- uses: actions/checkout@v7
- name: Cache apt packages
if: runner.os == 'Linux'
uses: ./.github/actions/cache-apt-packages-action
- name: Cache Homebrew downloads
if: runner.os == 'macOS'
uses: actions/cache@v5
with:
path: ~/Library/Caches/Homebrew
key: brew-${{ matrix.os }}-vtl-${{ hashFiles('.github/workflows/vsl_and_vtl_compile_ci.yml') }}
restore-keys: |
brew-${{ matrix.os }}-vtl-
brew-${{ matrix.os }}-
- name: Build V
id: build
run: make && sudo ./v symlink
- name: Install dependencies
run: |
if [ "$RUNNER_OS" == 'Linux' ]; then
.github/workflows/disable_azure_mirror.sh
v retry -- sudo apt -qq update
v retry -- sudo apt -qq install \
libgc-dev libgl1-mesa-dev mesa-common-dev liblapacke-dev libopenblas-dev libopenmpi-dev
else
v retry brew install coreutils hdf5 open-mpi openblas lapack opencl-headers
fi
v retry v install vsl
- name: Install vtl
run: v retry v install vtl
- name: Skip optional Vulkan examples on macOS
if: runner.os == 'macOS'
run: |
for file in "$HOME"/.vmodules/vtl/examples/*vulkan*/*.v; do
[ -e "$file" ] || continue
mv "$file" "${file%.v}_not_ci.v"
done
- name: Test with Pure V Backend
run: ~/.vmodules/vtl/bin/test
- name: Test with Pure V Backend and Pure V Math
run: ~/.vmodules/vtl/bin/test --use-cblas
+87
View File
@@ -0,0 +1,87 @@
name: Upgrading from a previous release with v up works
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '**.vv'
- '**.out'
- '!**/vup_works.yml'
- '!cmd/tools/vup.v'
- 'cmd/tools/vrepl.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '**.vv'
- '**.out'
- '!**/vup_works.yml'
- '!cmd/tools/vup.v'
- 'cmd/tools/vrepl.v'
concurrency:
group: vup-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
v-up-works-nix:
strategy:
fail-fast: false
matrix:
include:
- os: ubuntu-latest
zip: v_linux.zip
- os: macos-15-intel
zip: v_macos_x86_64.zip
- os: macos-latest
zip: v_macos_arm64.zip
runs-on: ${{ matrix.os }}
timeout-minutes: 20
env:
VDIR: /tmp/v_from_release_zip
steps:
- uses: actions/checkout@v7
- name: Build v
run: make && ./v symlink && ./v version
- name: Download latest release ZIP
run: ./v retry -- ./v download --sha256 https://github.com/vlang/v/releases/latest/download/${{ matrix.zip }}
- name: Extract ZIP 1, no changes
run: |
rm -rf "$VDIR" && unzip -q -d v_from_release/ ${{ matrix.zip }} && mv v_from_release "$VDIR"
cd "$VDIR/v"
./v version
./v up
echo "Updated ./v version: $(./v version) | Current v version: $(v version)"
- name: Extract ZIP 2, with local changes
run: |
rm -rf "$VDIR" && unzip -q -d v_from_release/ ${{ matrix.zip }} && mv v_from_release "$VDIR"
touch "$VDIR/v/vlib/v/pref/local_file_not_present_in_master.c.v" && rm "$VDIR/v/examples/hello_world.v"
cd "$VDIR/v"
./v version
./v up
echo "Updated ./v version: $(./v version) | Current v version: $(v version)"
- name: Extract ZIP 3, with current vup.v in the extract
run: |
rm -rf "$VDIR" && unzip -q -d v_from_release/ ${{ matrix.zip }} && mv v_from_release "$VDIR"
rm -rf "$VDIR/v/cmd/tools/vup" && cp cmd/tools/vup.v "$VDIR/v/cmd/tools/vup.v"
cd "$VDIR/v"
./v version
./v up
echo "Updated ./v version: $(./v version) | Current v version: $(v version)"
- name: Extract ZIP 4, with local changes, and with current vup.v
run: |
rm -rf "$VDIR" && unzip -q -d v_from_release/ ${{ matrix.zip }} && mv v_from_release "$VDIR"
rm -rf "$VDIR/v/cmd/tools/vup" && cp cmd/tools/vup.v "$VDIR/v/cmd/tools/vup.v"
touch "$VDIR/v/vlib/v/pref/local_file_not_present_in_master.c.v" && rm "$VDIR/v/examples/hello_world.v"
cd "$VDIR/v"
./v version
./v up
echo "Updated ./v version: $(./v version) | Current v version: $(v version)"
+87
View File
@@ -0,0 +1,87 @@
name: wasm backend CI
on:
push:
branches:
- master
paths:
- 'cmd/tools/builders/**.v'
- 'vlib/builtin/**.v'
- 'vlib/v/ast/**.v'
- 'vlib/v/scanner/**.v'
- 'vlib/v/parser/**.v'
- 'vlib/v/checker/**.v'
- 'vlib/v/gen/c/**.v'
- 'vlib/v/builder/**.v'
- 'vlib/v/cflag/**.v'
- 'vlib/v/live/**.v'
- 'vlib/v/util/**.v'
- 'vlib/v/markused/**.v'
- 'vlib/v/preludes/**.v'
- 'vlib/v/gen/wasm/**.v'
- 'vlib/v/gen/wasm/tests/**.v'
- 'vlib/v/gen/wasm/tests/**.vv'
- 'vlib/v/gen/wasm/tests_decompile/**.v'
- 'vlib/v/gen/wasm/tests_decompile/**.vv'
- '**/wasm_backend_ci.yml'
pull_request:
paths:
- 'cmd/tools/builders/**.v'
- 'vlib/builtin/**.v'
- 'vlib/v/ast/**.v'
- 'vlib/v/scanner/**.v'
- 'vlib/v/parser/**.v'
- 'vlib/v/checker/**.v'
- 'vlib/v/gen/c/**.v'
- 'vlib/v/builder/**.v'
- 'vlib/v/cflag/**.v'
- 'vlib/v/live/**.v'
- 'vlib/v/util/**.v'
- 'vlib/v/markused/**.v'
- 'vlib/v/preludes/**.v'
- 'vlib/v/gen/wasm/**.v'
- 'vlib/v/gen/wasm/tests/**.v'
- 'vlib/v/gen/wasm/tests/**.vv'
- 'vlib/v/gen/wasm/tests_decompile/**.v'
- 'vlib/v/gen/wasm/tests_decompile/**.vv'
- '**/wasm_backend_ci.yml'
concurrency:
group: wasm-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
wasm-backend:
runs-on: ${{ matrix.os }}
strategy:
matrix:
os: [ubuntu-22.04, windows-2022]
fail-fast: false
timeout-minutes: 20
env:
VTEST_ONLY: wasm
steps:
- uses: actions/checkout@v7
- name: Build V
if: runner.os != 'Windows'
run: make -j4
- name: Build V (Windows)
if: runner.os == 'Windows'
run: ./makev.bat
- name: Install WABT to get wasm-decompile
if: runner.os != 'Windows'
run: ./v retry -- sudo apt install wabt
- name: Setup Wasmer
uses: wasmerio/setup-wasmer@v3.1
- name: Prebuild the WASM backend
run: ./v cmd/tools/builders/wasm_builder.v
- name: Test the WASM backend
run: ./v test vlib/v/gen/wasm/
- name: Build examples
run: ./v build-examples
+104
View File
@@ -0,0 +1,104 @@
name: Websockets CI
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**/websockets_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**/websockets_ci.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: websockets-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
websocket_tests:
runs-on: ubuntu-24.04
timeout-minutes: 121
env:
VFLAGS: -cc tcc -no-retry-compilation
steps:
- uses: actions/checkout@v7
- uses: ./.github/actions/cache-apt-packages-action
- name: Build v
run: |
echo "$VFLAGS"
sudo ln -s "$PWD/thirdparty/tcc/tcc.exe" /usr/local/bin/tcc ## TODO: remove
make -j4 && ./v symlink
./v -g -o v cmd/v
- name: Install dependencies
run: v retry -- sudo apt install --quiet -y libssl-dev
- name: v doctor
run: ./v doctor
- name: Run websockets tests
run: ./v -g test vlib/net/websocket/
## Autobahn integrations tests
- name: Run autobahn services
run: docker compose -f ${{github.workspace}}/vlib/net/websocket/tests/autobahn/docker-compose.yml up -d
- name: Wait for the service to start
run: sleep 10s
- name: Build client test
run: docker exec autobahn_client "/src/v" "/src/vlib/net/websocket/tests/autobahn/autobahn_client.v"
- name: Run client test
run: docker exec autobahn_client "/src/vlib/net/websocket/tests/autobahn/autobahn_client"
- name: Build client wss test
run: docker exec autobahn_client "/src/v" "/src/vlib/net/websocket/tests/autobahn/autobahn_client_wss.v"
- name: Run client wss test
run: docker exec autobahn_client "/src/vlib/net/websocket/tests/autobahn/autobahn_client_wss"
- name: Run server test
run: docker exec autobahn_server "wstest" "-m" "fuzzingclient" "-s" "/config/fuzzingclient.json"
- name: Copy reports
run: docker cp autobahn_server:/reports ${{github.workspace}}/reports
- name: Copy reports wss
run: docker cp autobahn_server_wss:/reports ${{github.workspace}}/reports_wss
- name: Test success
run: docker exec autobahn_server "python" "/check_results.py"
- name: Test success WSS
run: docker exec autobahn_server_wss "python" "/check_results.py"
- name: Publish all reports
uses: actions/upload-artifact@v7
with:
name: full report
path: ${{github.workspace}}/reports
- name: Publish report client
uses: actions/upload-artifact@v7
with:
name: client
path: ${{github.workspace}}/reports/clients/index.html
- name: Publish report server
uses: actions/upload-artifact@v7
with:
name: server
path: ${{github.workspace}}/reports/servers/index.html
- name: Publish all reports WSS
uses: actions/upload-artifact@v7
with:
name: full report wss
path: ${{github.workspace}}/reports_wss
- name: Publish report client wss
uses: actions/upload-artifact@v7
with:
name: client wss
path: ${{github.workspace}}/reports_wss/clients/index.html
+16
View File
@@ -0,0 +1,16 @@
@echo off
curl -L https://www.libsdl.org/release/SDL2-devel-2.0.10-VC.zip -o SDL2.zip
curl -L https://www.libsdl.org/projects/SDL_ttf/release/SDL2_ttf-devel-2.0.15-VC.zip -o SDL2_ttf.zip
curl -L https://www.libsdl.org/projects/SDL_image/release/SDL2_image-devel-2.0.5-VC.zip -o SDL2_image.zip
curl -L https://www.libsdl.org/projects/SDL_mixer/release/SDL2_mixer-devel-2.0.4-VC.zip -o SDL2_mixer.zip
unzip SDL2.zip -d thirdparty/
unzip SDL2_ttf.zip -d thirdparty/
unzip SDL2_image.zip -d thirdparty/
unzip SDL2_mixer.zip -d thirdparty/
move /y thirdparty/SDL2-2.0.10 thirdparty/SDL2
move /y thirdparty/SDL2_ttf-2.0.15 thirdparty/SDL2_ttf
move /y thirdparty/SDL2_image-2.0.5 thirdparty/SDL2_image
move /y thirdparty/SDL2_mixer-2.0.4 thirdparty/SDL2_mixer
+3
View File
@@ -0,0 +1,3 @@
REM This file should be run from the top folder of the V compiler itself.
v vlib/db/sqlite/install_thirdparty_sqlite.vsh
+105
View File
@@ -0,0 +1,105 @@
name: CI Windows GCC
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**.bat'
- '!**/windows_ci_gcc.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**.bat'
- '!**/windows_ci_gcc.yml'
- '!**/windows-install-sqlite.bat'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: windows-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
gcc-windows:
runs-on: windows-2025
timeout-minutes: 110
env:
VFLAGS: -cc gcc
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- name: Show tool versions
run: |
gcc --version
pkg-config --version
openssl version
echo "Flags for openssl:"
pkg-config openssl --cflags
echo "Flags for openssl libs:"
pkg-config openssl --libs
.github/workflows/find_openssl.bat
echo "OpenSSL files:"
where.exe /R "C:\Program Files\OpenSSL" *.*
echo "Include files for openssl:"
dir "c:/Program Files/OpenSSL/include"
echo "Lib Include files for openssl:"
dir "c:/Program Files/OpenSSL/lib/VC/x64/"
- name: Build
run: |
.\makev.bat -gcc
.\v.exe symlink
.\v.exe -stats vlib/crypto/ecdsa/ecdsa_test.v
- name: Test v binaries
run: v build-vbinaries
- name: All code is formatted
run: v -silent test-cleancode
- name: Test new v.c
run: |
v -o v.c cmd/v
$direct_c_flags = @(
'-Ithirdparty/zip'
'-Ithirdparty/cJSON'
'-Ithirdparty/mbedtls/library'
'-Ithirdparty/mbedtls/include'
'-Ithirdparty/mbedtls/3rdparty/everest/include'
'-Ithirdparty/mbedtls/3rdparty/everest/include/everest'
'-Ithirdparty/mbedtls/3rdparty/everest/include/everest/kremlib'
'-Ithirdparty/vschannel'
)
gcc -Werror -municode -w @direct_c_flags v.c -lws2_32 -std=c99
- name: Install dependencies
run: |
v retry -- v setup-freetype
.\.github\workflows\windows-install-sqlite.bat
- name: v doctor
run: |
v doctor
- name: Verify `v test` works
run: |
echo $VFLAGS
v cmd/tools/test_if_v_test_system_works.v
./cmd/tools/test_if_v_test_system_works
- name: Test pure V math module
run: v -silent -exclude @vlib/math/*.c.v test vlib/math/
- name: Self tests
run: v -silent test-self vlib
- name: Build option_test.c.v with -autofree
run: v -autofree vlib/v/tests/options/option_test.c.v
- name: Test v->js
run: v -o hi.js examples/js_hello_world.v && node hi.js
- name: Build examples
run: v build-examples
- name: v2 self compilation
run: v -o v2.exe cmd/v && .\v2.exe -o v3.exe cmd/v
- name: compile vdoctor.v with -prod
run: v -showcc -prod cmd/tools/vdoctor.v
- name: compile vup.v with -prod
run: v -showcc -prod cmd/tools/vup.v
+679
View File
@@ -0,0 +1,679 @@
name: CI Windows MSVC
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**.bat'
- '!**/windows_ci_msvc.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**.bat'
- '!**/windows_ci_msvc.yml'
- '!**/windows-install-sqlite.bat'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: windows-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
msvc-windows:
runs-on: windows-2022
timeout-minutes: 70
env:
VFLAGS: -cc msvc
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- uses: ilammy/msvc-dev-cmd@v1
with:
arch: x64
- name: Verify MSVC tools
run: |
where.exe cl.exe
where.exe link.exe
where.exe dumpbin.exe
- name: Build
run: |
echo %VFLAGS%
echo $VFLAGS
.\makev.bat -msvc
.\v.exe symlink
- name: backend x64 regressions
if: ${{ false }} # Temporarily disabled.
run: |
function Assert-LastExit([string] $label) {
if ($LASTEXITCODE -ne 0) {
throw "$label failed with exit code $LASTEXITCODE"
}
}
$env:VJOBS = '1'
.\v.exe test `
vlib/v2_toberemoved/abi `
vlib/v2_toberemoved/gen/x64/x64_abi_test.v `
vlib/v2_toberemoved/gen/x64/x64_backend_diagnostics_test.v `
vlib/v2_toberemoved/gen/x64/x64_object_format_test.v `
vlib/v2_toberemoved/gen/x64/x64_pe_linker_test.v `
vlib/v2_toberemoved/ssa/tree_sumtype_lowering_test.v
Assert-LastExit 'stable V2 x64 unit tests'
.\v.exe test -run-only test_module_qualified_alias_array_field_index_has_alias_element_type,test_module_storage_legacy_direct_import_nested_module_selector_uses_declared_leaf_module,test_module_storage_flat_direct_import_nested_module_selector_uses_declared_leaf_module vlib/v2_toberemoved/ssa/module_storage_test.v
Assert-LastExit 'targeted vlib/v2_toberemoved/ssa/module_storage_test.v regressions'
.\v.exe test -run-only test_x64_macos_windows_math_log_20_stdout_exact_bytes,test_x64_macos_windows_generic_sumtype_repeated_base_specialization_stdout_exact_bytes,test_x64_macos_windows_formatted_int_interpolation_stdout_exact_bytes,test_x64_macos_windows_formatted_int_width_100_interpolation_stdout_exact_bytes,test_x64_macos_windows_formatted_f64_interpolation_stdout_exact_bytes,test_x64_macos_windows_formatted_string_return_lifetime_stdout_exact_bytes,test_x64_macos_windows_spectral_reduced_formatted_stdout_exact_bytes,test_x64_macos_windows_bits_len32_stdout_exact_bytes,test_x64_macos_windows_rand_u32n_interface_result_stdout_exact_bytes,test_x64_macos_windows_rand_intn_range_interface_result_stdout_exact_bytes,test_x64_macos_windows_textscanner_embedded_parser_stdout_exact_bytes,test_x64_macos_windows_struct_positional_side_effect_stdout_exact_bytes,test_x64_macos_windows_struct_named_side_effect_stdout_exact_bytes,test_x64_macos_windows_unrelated_same_shape_struct_stdout_exact_bytes,test_x64_macos_windows_named_init_embedded_value_stdout_exact_bytes,test_x64_macos_windows_get_raw_line_example_stdin_stdout_exact_bytes,test_x64_macos_windows_mini_calculator_example_stdin_stdout_exact_bytes,test_x64_macos_windows_mini_calculator_recursive_descent_example_stdin_stdout_exact_bytes vlib/v2_toberemoved/gen/x64/x64_runtime_smoke_test.v
Assert-LastExit 'reduced V2 x64 runtime smoke tests'
Remove-Item Env:\VJOBS -ErrorAction SilentlyContinue
.\v.exe test vlib/v2_toberemoved/builder/native_test.v vlib/v2_toberemoved/builder/target_os_test.v
Assert-LastExit 'vlib/v2_toberemoved/builder/native_test.v vlib/v2_toberemoved/builder/target_os_test.v'
.\v.exe test vlib/v2_toberemoved/ssa/optimize
Assert-LastExit 'vlib/v2_toberemoved/ssa/optimize'
$env:V2_VERIFY_STRICT = '1'
.\v.exe test vlib/v2_toberemoved/ssa/optimize
Assert-LastExit 'strict vlib/v2_toberemoved/ssa/optimize'
Remove-Item Env:\V2_VERIFY_STRICT -ErrorAction SilentlyContinue
- name: backend x64 examples
if: ${{ false }} # Temporarily disabled.
run: |
function Assert-LastExit([string] $label) {
if ($LASTEXITCODE -ne 0) {
throw "$label failed with exit code $LASTEXITCODE"
}
}
function Assert-ByteArrayEqual([byte[]] $actual, [byte[]] $expected, [string] $label) {
if ($actual.Length -ne $expected.Length) {
$actual_text = [System.Text.Encoding]::UTF8.GetString($actual)
$expected_text = [System.Text.Encoding]::UTF8.GetString($expected)
throw "$label mismatch. Expected length $($expected.Length), got $($actual.Length).`nExpected:`n$expected_text`nActual:`n$actual_text"
}
for ($i = 0; $i -lt $actual.Length; $i++) {
if ($actual[$i] -ne $expected[$i]) {
$actual_text = [System.Text.Encoding]::UTF8.GetString($actual)
$expected_text = [System.Text.Encoding]::UTF8.GetString($expected)
throw "$label mismatch at byte $i.`nExpected:`n$expected_text`nActual:`n$actual_text"
}
}
}
function Get-PeImportedDlls([string] $exe) {
$output = & dumpbin.exe /imports $exe 2>&1
if ($LASTEXITCODE -ne 0) {
$text = ($output | Out-String).Trim()
throw "dumpbin import inspection failed for $exe with exit code $LASTEXITCODE`n$text"
}
$dlls = [System.Collections.Generic.List[string]]::new()
foreach ($lineObject in $output) {
$line = [string] $lineObject
if ($line -match '^\s*([A-Za-z0-9_.-]+\.dll)\s*$') {
$dlls.Add($matches[1].ToLowerInvariant())
}
}
return $dlls | Sort-Object -Unique
}
function Assert-TinyPeImports([string] $name, [string] $exe, [string] $pe_import_mode) {
if ($pe_import_mode -eq '') {
return
}
if ($pe_import_mode -eq 'tiny-used') {
[string[]] $allowed_dlls = @('kernel32.dll')
} elseif ($pe_import_mode -eq 'tiny-shell32-argv') {
[string[]] $allowed_dlls = @('kernel32.dll', 'shell32.dll')
} else {
throw "$name has unknown PE import validation mode: $pe_import_mode"
}
[string[]] $dlls = @(Get-PeImportedDlls $exe)
if ($dlls.Count -eq 0) {
throw "$name PE import validation found no imported DLLs with dumpbin.exe"
}
$crt_dlls = $dlls | Where-Object {
$_ -match '^(msvcrt|ucrtbase|vcruntime)[0-9]*\.dll$' -or $_ -match '^api-ms-win-crt-.*\.dll$'
}
if ($crt_dlls.Count -gt 0) {
throw "$name tiny PE unexpectedly imports CRT DLL(s): $($crt_dlls -join ', ')"
}
$unexpected_dlls = $dlls | Where-Object { $_ -notin $allowed_dlls }
if ($unexpected_dlls.Count -gt 0) {
throw "$name PE imports unexpected DLL(s): $($unexpected_dlls -join ', ')"
}
$missing_dlls = $allowed_dlls | Where-Object { $_ -notin $dlls }
if ($missing_dlls.Count -gt 0) {
throw "$name PE import validation missed expected DLL(s): $($missing_dlls -join ', ')"
}
}
function Invoke-NativeX64Example([string] $source, [string] $name, [byte[]] $expected_stdout, [string] $pe_import_mode = '', [string[]] $program_args = @()) {
$exe = Join-Path $tmp "$name.exe"
$stdout_path = Join-Path $tmp "$name.out"
$stderr_path = Join-Path $tmp "$name.err"
$compile_output = & .\v.exe -v2 -no-parallel -b x64 $source -o $exe 2>&1
$compile_exit = $LASTEXITCODE
foreach ($line in $compile_output) {
Write-Host $line
}
if ($compile_exit -ne 0) {
throw "compile $source failed with exit code $compile_exit"
}
Assert-TinyPeImports $name $exe $pe_import_mode
Remove-Item -LiteralPath $stdout_path, $stderr_path -Force -ErrorAction SilentlyContinue
if ($program_args.Count -gt 0) {
$process = Start-Process -FilePath $exe -ArgumentList $program_args -NoNewWindow -Wait -PassThru -RedirectStandardOutput $stdout_path -RedirectStandardError $stderr_path
} else {
$process = Start-Process -FilePath $exe -NoNewWindow -Wait -PassThru -RedirectStandardOutput $stdout_path -RedirectStandardError $stderr_path
}
if ($process.ExitCode -ne 0) {
if (Test-Path -LiteralPath $stderr_path) {
Get-Content -LiteralPath $stderr_path
}
throw "$source exited with code $($process.ExitCode)"
}
[byte[]] $stdout = if (Test-Path -LiteralPath $stdout_path) { [System.IO.File]::ReadAllBytes($stdout_path) } else { New-Object byte[] 0 }
[byte[]] $stderr = if (Test-Path -LiteralPath $stderr_path) { [System.IO.File]::ReadAllBytes($stderr_path) } else { New-Object byte[] 0 }
$empty = New-Object byte[] 0
Assert-ByteArrayEqual $stdout $expected_stdout "$source stdout"
Assert-ByteArrayEqual $stderr $empty "$source stderr"
}
function Invoke-NativeX64ExampleWithStdin([string] $source, [string] $name, [byte[]] $expected_stdout, [string] $stdin_path, [string] $pe_import_mode = '', [string[]] $program_args = @()) {
$exe = Join-Path $tmp "$name.exe"
$stdout_path = Join-Path $tmp "$name.out"
$stderr_path = Join-Path $tmp "$name.err"
$compile_output = & .\v.exe -v2 -no-parallel -b x64 $source -o $exe 2>&1
$compile_exit = $LASTEXITCODE
foreach ($line in $compile_output) {
Write-Host $line
}
if ($compile_exit -ne 0) {
throw "compile $source failed with exit code $compile_exit"
}
Assert-TinyPeImports $name $exe $pe_import_mode
Remove-Item -LiteralPath $stdout_path, $stderr_path -Force -ErrorAction SilentlyContinue
if ($program_args.Count -gt 0) {
$process = Start-Process -FilePath $exe -ArgumentList $program_args -NoNewWindow -Wait -PassThru -RedirectStandardInput $stdin_path -RedirectStandardOutput $stdout_path -RedirectStandardError $stderr_path
} else {
$process = Start-Process -FilePath $exe -NoNewWindow -Wait -PassThru -RedirectStandardInput $stdin_path -RedirectStandardOutput $stdout_path -RedirectStandardError $stderr_path
}
if ($process.ExitCode -ne 0) {
if (Test-Path -LiteralPath $stderr_path) {
Get-Content -LiteralPath $stderr_path
}
throw "$source exited with code $($process.ExitCode)"
}
[byte[]] $stdout = if (Test-Path -LiteralPath $stdout_path) { [System.IO.File]::ReadAllBytes($stdout_path) } else { New-Object byte[] 0 }
[byte[]] $stderr = if (Test-Path -LiteralPath $stderr_path) { [System.IO.File]::ReadAllBytes($stderr_path) } else { New-Object byte[] 0 }
$empty = New-Object byte[] 0
Assert-ByteArrayEqual $stdout $expected_stdout "$source stdout"
Assert-ByteArrayEqual $stderr $empty "$source stderr"
}
function Invoke-NativeX64ExampleCapture([string] $source, [string] $name, [string[]] $program_args = @()) {
$exe = Join-Path $tmp "$name.exe"
$stdout_path = Join-Path $tmp "$name.out"
$stderr_path = Join-Path $tmp "$name.err"
$compile_output = & .\v.exe -v2 -no-parallel -b x64 $source -o $exe 2>&1
$compile_exit = $LASTEXITCODE
foreach ($line in $compile_output) {
Write-Host $line
}
if ($compile_exit -ne 0) {
throw "compile $source failed with exit code $compile_exit"
}
Remove-Item -LiteralPath $stdout_path, $stderr_path -Force -ErrorAction SilentlyContinue
if ($program_args.Count -gt 0) {
$process = Start-Process -FilePath $exe -ArgumentList $program_args -NoNewWindow -Wait -PassThru -RedirectStandardOutput $stdout_path -RedirectStandardError $stderr_path
} else {
$process = Start-Process -FilePath $exe -NoNewWindow -Wait -PassThru -RedirectStandardOutput $stdout_path -RedirectStandardError $stderr_path
}
if ($process.ExitCode -ne 0) {
if (Test-Path -LiteralPath $stderr_path) {
Get-Content -LiteralPath $stderr_path
}
throw "$source exited with code $($process.ExitCode)"
}
[byte[]] $stderr = if (Test-Path -LiteralPath $stderr_path) { [System.IO.File]::ReadAllBytes($stderr_path) } else { New-Object byte[] 0 }
$empty = New-Object byte[] 0
Assert-ByteArrayEqual $stderr $empty "$source stderr"
return $stdout_path
}
function Assert-RandomIpsStdout([string] $path) {
[string[]] $lines = [System.IO.File]::ReadAllLines($path)
if ($lines.Count -ne 10) {
throw "random_ips expected 10 lines, got $($lines.Count)"
}
$rows = [System.Collections.Generic.List[string]]::new()
$all_second_zero = $true
$all_fourth_zero = $true
foreach ($line in $lines) {
[string[]] $parts = $line.Split('.')
if ($parts.Count -ne 4) {
throw "random_ips invalid IPv4 shape: $line"
}
[int[]] $octets = @()
foreach ($part in $parts) {
if ($part -notmatch '^[0-9]+$') {
throw "random_ips non-numeric octet: $line"
}
$value = [int] $part
if ($value -lt 0 -or $value -gt 254) {
throw "random_ips octet out of range: $line"
}
$octets += $value
}
if ($octets[1] -ne 0) {
$all_second_zero = $false
}
if ($octets[3] -ne 0) {
$all_fourth_zero = $false
}
$rows.Add(($octets -join '.'))
}
if (($rows | Sort-Object -Unique).Count -lt 3) {
throw 'random_ips output has too little row diversity'
}
if ($all_second_zero -and $all_fourth_zero) {
throw 'random_ips suspicious old x.0.x.0 pattern'
}
}
function Assert-Rule110Stdout([string] $path, [int] $width) {
[string[]] $lines = [System.IO.File]::ReadAllLines($path)
$title = 'Rule 110 V Implementation'
$idx = -1
for ($i = 0; $i -lt $lines.Count; $i++) {
if ($lines[$i].Contains($title)) {
$idx = $i
break
}
}
if ($idx -lt 0) {
throw 'rule110 missing title'
}
[string[]] $generations = @()
if ($idx + 1 -lt $lines.Count) {
$generations = @($lines[($idx + 1)..($lines.Count - 1)])
}
if ($generations.Count -gt 0 -and $generations[0] -eq '') {
if ($generations.Count -eq 1) {
$generations = @()
} else {
$generations = @($generations[1..($generations.Count - 1)])
}
}
if ($generations.Count -ne $width) {
throw "rule110 expected $width generation lines, got $($generations.Count)"
}
$has_live_cell = $false
foreach ($line in $generations) {
if ($line.Length -ne $width) {
throw "rule110 generation line has width $($line.Length), expected $width`: '$line'"
}
if ($line -match '[^ *]') {
throw "rule110 invalid generation chars: '$line'"
}
if ($line.Contains('*')) {
$has_live_cell = $true
}
}
if (-not $has_live_cell) {
throw 'rule110 expected at least one live cell'
}
if (($generations | Sort-Object -Unique).Count -lt 3) {
throw 'rule110 expected at least 3 distinct generation lines'
}
}
$tmp = Join-Path $env:RUNNER_TEMP 'v2_x64_native'
New-Item -ItemType Directory -Force -Path $tmp | Out-Null
function Get-VRunExpectedBytes([string] $source, [string] $name, [string[]] $program_args = @()) {
$stdout_path = Join-Path $tmp "$name.vrun.out"
$stderr_path = Join-Path $tmp "$name.vrun.err"
Remove-Item -LiteralPath $stdout_path, $stderr_path -Force -ErrorAction SilentlyContinue
$v_args = @('run', $source) + $program_args
$process = Start-Process -FilePath '.\v.exe' -ArgumentList $v_args -NoNewWindow -Wait -PassThru -RedirectStandardOutput $stdout_path -RedirectStandardError $stderr_path
if ($process.ExitCode -ne 0) {
if (Test-Path -LiteralPath $stderr_path) {
Get-Content -LiteralPath $stderr_path
}
throw "v run $source $($program_args -join ' ') failed with code $($process.ExitCode)"
}
[byte[]] $stderr = if (Test-Path -LiteralPath $stderr_path) { [System.IO.File]::ReadAllBytes($stderr_path) } else { New-Object byte[] 0 }
$empty = New-Object byte[] 0
Assert-ByteArrayEqual $stderr $empty "v run $source stderr"
return [System.IO.File]::ReadAllBytes($stdout_path)
}
function Get-VRunExpectedBytesWithStdin([string] $source, [string] $name, [string] $stdin_path, [string[]] $program_args = @()) {
$stdout_path = Join-Path $tmp "$name.vrun.out"
$stderr_path = Join-Path $tmp "$name.vrun.err"
Remove-Item -LiteralPath $stdout_path, $stderr_path -Force -ErrorAction SilentlyContinue
$v_args = @('run', $source) + $program_args
$process = Start-Process -FilePath '.\v.exe' -ArgumentList $v_args -NoNewWindow -Wait -PassThru -RedirectStandardInput $stdin_path -RedirectStandardOutput $stdout_path -RedirectStandardError $stderr_path
if ($process.ExitCode -ne 0) {
if (Test-Path -LiteralPath $stderr_path) {
Get-Content -LiteralPath $stderr_path
}
throw "v run $source $($program_args -join ' ') failed with code $($process.ExitCode)"
}
[byte[]] $stderr = if (Test-Path -LiteralPath $stderr_path) { [System.IO.File]::ReadAllBytes($stderr_path) } else { New-Object byte[] 0 }
$empty = New-Object byte[] 0
Assert-ByteArrayEqual $stderr $empty "v run $source stderr"
return [System.IO.File]::ReadAllBytes($stdout_path)
}
$hello_expected = [System.Text.Encoding]::UTF8.GetBytes("Hello, World!`n")
Invoke-NativeX64Example 'examples/hello_world.v' 'hello_world' $hello_expected 'tiny-used'
$fizz_lines = 1..100 | ForEach-Object {
if ($_ % 15 -eq 0) {
'FizzBuzz'
} elseif ($_ % 3 -eq 0) {
'Fizz'
} elseif ($_ % 5 -eq 0) {
'Buzz'
} else {
[string] $_
}
}
$fizz_expected = [System.Text.Encoding]::UTF8.GetBytes(($fizz_lines -join "`n") + "`n")
Invoke-NativeX64Example 'examples/fizz_buzz.v' 'fizz_buzz' $fizz_expected 'tiny-used'
$fibonacci_expected = [System.Text.Encoding]::UTF8.GetBytes("1`n1`n2`n3`n5`n8`n13`n21`n34`n55`n89`n")
Invoke-NativeX64Example 'examples/fibonacci.v' 'fibonacci' $fibonacci_expected 'tiny-shell32-argv' @('10')
$dump_factorial_expected = [System.Text.Encoding]::UTF8.GetBytes("120`n")
Invoke-NativeX64Example 'examples/dump_factorial.v' 'dump_factorial' $dump_factorial_expected 'tiny-used'
function Get-HanoiExpectedLines([int] $n, [string] $a, [string] $b, [string] $c) {
if ($n -eq 1) {
"Disc 1 from $a to $c..."
return
}
Get-HanoiExpectedLines ($n - 1) $a $c $b
"Disc $n from $a to $c..."
Get-HanoiExpectedLines ($n - 1) $b $a $c
}
$hanoi_lines = @(Get-HanoiExpectedLines 7 'A' 'B' 'C')
$hanoi_expected = [System.Text.Encoding]::UTF8.GetBytes(($hanoi_lines -join "`n") + "`n")
Invoke-NativeX64Example 'examples/hanoi.v' 'hanoi' $hanoi_expected 'tiny-used'
function Get-SudokuExpectedLines {
$puzzle = @(
,@(0, 3, 0, 0, 7, 0, 0, 0, 0)
,@(0, 0, 0, 1, 3, 5, 0, 0, 0)
,@(0, 0, 1, 0, 0, 0, 0, 5, 0)
,@(1, 0, 0, 0, 6, 0, 0, 0, 3)
,@(4, 0, 0, 8, 0, 3, 0, 0, 1)
,@(7, 0, 0, 0, 2, 0, 0, 0, 6)
,@(0, 0, 0, 0, 0, 0, 2, 1, 0)
,@(0, 0, 0, 4, 1, 2, 0, 0, 5)
,@(0, 0, 0, 0, 0, 0, 0, 7, 4)
)
$solution = @(
,@(2, 3, 5, 6, 7, 8, 1, 4, 9)
,@(9, 4, 7, 1, 3, 5, 8, 6, 2)
,@(6, 8, 1, 2, 4, 9, 3, 5, 7)
,@(1, 2, 8, 7, 6, 4, 5, 9, 3)
,@(4, 5, 6, 8, 9, 3, 7, 2, 1)
,@(7, 9, 3, 5, 2, 1, 4, 8, 6)
,@(3, 6, 4, 9, 5, 7, 2, 1, 8)
,@(8, 7, 9, 4, 1, 2, 6, 3, 5)
,@(5, 1, 2, 3, 8, 6, 9, 7, 4)
)
$lines = [System.Collections.Generic.List[string]]::new()
function Add-SudokuGrid([string] $label, [object[]] $grid) {
$lines.Add($label)
for ($i = 0; $i -lt $grid.Count; $i++) {
if ($i % 3 -eq 0 -and $i -ne 0) {
$lines.Add('- - - - - - - - - - - -')
}
$line = ''
for ($j = 0; $j -lt $grid[$i].Count; $j++) {
if ($j % 3 -eq 0 -and $j -ne 0) {
$line += ' | '
}
$line += "$($grid[$i][$j]) "
}
$lines.Add($line)
}
}
Add-SudokuGrid 'Sudoku Puzzle:' $puzzle
$lines.Add('Solving...')
Add-SudokuGrid 'Solution:' $solution
return $lines.ToArray()
}
$sudoku_lines = @(Get-SudokuExpectedLines)
$sudoku_expected = [System.Text.Encoding]::UTF8.GetBytes(($sudoku_lines -join "`n") + "`n")
if ($sudoku_expected.Length -ne 582) {
throw "sudoku stdout oracle shape changed: $($sudoku_expected.Length) bytes"
}
Invoke-NativeX64Example 'examples/sudoku.v' 'sudoku' $sudoku_expected
$function_types_expected = [System.Text.Encoding]::UTF8.GetBytes("HELLO WORLD`nHELLO WORLD`nHELLO WORLD`n")
Invoke-NativeX64Example 'examples/function_types.v' 'function_types' $function_types_expected
$submodule_expected = [System.Text.Encoding]::UTF8.GetBytes("5`n3`n")
Invoke-NativeX64Example 'examples/submodule/main.v' 'submodule' $submodule_expected 'tiny-used'
function Get-TreeOfNodesExpectedLines {
@(
'tree structure:'
' Node{'
' value: 10'
' left: Tree(Node{'
' value: 30'
' left: Tree(Empty{})'
' right: Tree(Empty{})'
' })'
' right: Tree(Node{'
' value: 20'
' left: Tree(Empty{})'
' right: Tree(Empty{})'
' })'
'}'
'tree size: 3'
)
}
$tree_of_nodes_lines = @(Get-TreeOfNodesExpectedLines)
$tree_of_nodes_expected = [System.Text.Encoding]::UTF8.GetBytes(($tree_of_nodes_lines -join "`n") + "`n")
if ($tree_of_nodes_expected.Length -ne 259) {
throw "tree_of_nodes stdout oracle shape changed: $($tree_of_nodes_expected.Length) bytes"
}
Invoke-NativeX64Example 'examples/tree_of_nodes.v' 'tree_of_nodes' $tree_of_nodes_expected
$js_hello_world_expected = [System.Text.Encoding]::UTF8.GetBytes("Hello from V.js (0)`nHello from V.js (1)`nHello from V.js (2)`n")
Invoke-NativeX64Example 'examples/js_hello_world.v' 'js_hello_world' $js_hello_world_expected 'tiny-used'
function Get-VSingleQuotedLiteralBytes([string] $literal) {
$bytes = [System.Collections.Generic.List[byte]]::new()
for ($i = 0; $i -lt $literal.Length; $i++) {
$ch = $literal[$i]
if ($ch -eq '\') {
$i++
if ($i -ge $literal.Length) {
throw 'unterminated escape in V single-quoted literal'
}
$escaped = $literal[$i]
switch ([int][char] $escaped) {
110 { [void] $bytes.Add(10) }
116 { [void] $bytes.Add(9) }
114 { [void] $bytes.Add(13) }
92 { [void] $bytes.Add(92) }
39 { [void] $bytes.Add(39) }
34 { [void] $bytes.Add(34) }
default {
foreach ($byte in [System.Text.Encoding]::UTF8.GetBytes([string] $escaped)) {
[void] $bytes.Add($byte)
}
}
}
} else {
foreach ($byte in [System.Text.Encoding]::UTF8.GetBytes([string] $ch)) {
[void] $bytes.Add($byte)
}
}
}
return $bytes.ToArray()
}
function Get-VasciiExpectedBytes() {
$source = [System.IO.File]::ReadAllText((Join-Path (Get-Location) 'examples/vascii.v'), [System.Text.Encoding]::UTF8)
$start_marker = "println('"
$end_marker = "')"
$first = $source.IndexOf($start_marker, [System.StringComparison]::Ordinal)
if ($first -lt 0) {
throw 'missing vascii println literal start'
}
$second = $source.IndexOf($start_marker, $first + $start_marker.Length, [System.StringComparison]::Ordinal)
if ($second -ne -1) {
throw 'vascii stdout oracle expects one single-quoted println literal'
}
$start = $first + $start_marker.Length
$end = $source.LastIndexOf($end_marker, [System.StringComparison]::Ordinal)
if ($end -lt $start) {
throw 'missing vascii println literal end'
}
if ($source.Substring($end + $end_marker.Length).Trim() -ne '}') {
throw 'vascii stdout oracle expects the println literal to be the final main statement'
}
[byte[]] $bytes = Get-VSingleQuotedLiteralBytes ($source.Substring($start, $end - $start))
return $bytes + [byte] 10
}
[byte[]] $vascii_expected = Get-VasciiExpectedBytes
Invoke-NativeX64Example 'examples/vascii.v' 'vascii' $vascii_expected 'tiny-used'
[byte[]] $rune_expected = 0xF0, 0x9F, 0x98, 0x80, 0x0A, 0x40, 0x0A
Invoke-NativeX64Example 'examples/rune.v' 'rune' $rune_expected 'tiny-used'
[byte[]] $bfs_expected = Get-VRunExpectedBytes 'examples/graphs/bfs.v' 'bfs'
Invoke-NativeX64Example 'examples/graphs/bfs.v' 'bfs' $bfs_expected
[byte[]] $bfs3_expected = Get-VRunExpectedBytes 'examples/graphs/bfs3.v' 'bfs3'
Invoke-NativeX64Example 'examples/graphs/bfs3.v' 'bfs3' $bfs3_expected
[byte[]] $primes_expected = Get-VRunExpectedBytes 'examples/primes.v' 'primes' @('20')
Invoke-NativeX64Example 'examples/primes.v' 'primes' $primes_expected '' @('20')
[byte[]] $dfs_expected = Get-VRunExpectedBytes 'examples/graphs/dfs.v' 'dfs'
Invoke-NativeX64Example 'examples/graphs/dfs.v' 'dfs' $dfs_expected
[byte[]] $dijkstra_expected = Get-VRunExpectedBytes 'examples/graphs/dijkstra.v' 'dijkstra'
Invoke-NativeX64Example 'examples/graphs/dijkstra.v' 'dijkstra' $dijkstra_expected
[byte[]] $topological_sorting_greedy_expected = Get-VRunExpectedBytes 'examples/graphs/topological_sorting_greedy.v' 'topological_sorting_greedy'
Invoke-NativeX64Example 'examples/graphs/topological_sorting_greedy.v' 'topological_sorting_greedy' $topological_sorting_greedy_expected
[byte[]] $topological_sorting_dfs_expected = Get-VRunExpectedBytes 'examples/graphs/topological_sorting_dfs.v' 'topological_sorting_dfs'
Invoke-NativeX64Example 'examples/graphs/topological_sorting_dfs.v' 'topological_sorting_dfs' $topological_sorting_dfs_expected
[byte[]] $dfs2_expected = Get-VRunExpectedBytes 'examples/graphs/dfs2.v' 'dfs2'
Invoke-NativeX64Example 'examples/graphs/dfs2.v' 'dfs2' $dfs2_expected
[byte[]] $minimal_spann_tree_prim_expected = Get-VRunExpectedBytes 'examples/graphs/minimal_spann_tree_prim.v' 'minimal_spann_tree_prim'
Invoke-NativeX64Example 'examples/graphs/minimal_spann_tree_prim.v' 'minimal_spann_tree_prim' $minimal_spann_tree_prim_expected
[byte[]] $bellman_ford_expected = Get-VRunExpectedBytes 'examples/graphs/bellman-ford.v' 'bellman_ford'
Invoke-NativeX64Example 'examples/graphs/bellman-ford.v' 'bellman_ford' $bellman_ford_expected
[byte[]] $binary_search_tree_expected = Get-VRunExpectedBytes 'examples/binary_search_tree.v' 'binary_search_tree'
Invoke-NativeX64Example 'examples/binary_search_tree.v' 'binary_search_tree' $binary_search_tree_expected
# normal-required: IError/custom errors
[byte[]] $errors_expected = [System.Text.Encoding]::UTF8.GetBytes("wrong format`nempty input`n")
Invoke-NativeX64Example 'examples/errors.v' 'errors' $errors_expected
[byte[]] $custom_error_expected = Get-VRunExpectedBytes 'examples/custom_error.v' 'custom_error'
Invoke-NativeX64Example 'examples/custom_error.v' 'custom_error' $custom_error_expected
# normal-required: spectral norm/math.sqrt/formatted f64 interpolation
[byte[]] $spectral_expected = Get-VRunExpectedBytes 'examples/spectral.v' 'spectral' @('10')
Invoke-NativeX64Example 'examples/spectral.v' 'spectral' $spectral_expected '' @('10')
[byte[]] $quick_sort_expected = [System.Text.Encoding]::UTF8.GetBytes("length of random array is 1000`nbefore quick sort whether array is sorted: false`nafter quick sort whether array is sorted: true`n")
Invoke-NativeX64Example 'examples/quick_sort.v' 'quick_sort' $quick_sort_expected
$get_raw_line_input = Join-Path $tmp 'get_raw_line.in'
[System.IO.File]::WriteAllText($get_raw_line_input, "hello`nworld`n", [System.Text.UTF8Encoding]::new($false))
[byte[]] $get_raw_line_expected = Get-VRunExpectedBytesWithStdin 'examples/get_raw_line.v' 'get_raw_line' $get_raw_line_input
Invoke-NativeX64ExampleWithStdin 'examples/get_raw_line.v' 'get_raw_line' $get_raw_line_expected $get_raw_line_input
$mini_calculator_input = Join-Path $tmp 'mini_calculator.in'
[System.IO.File]::WriteAllText($mini_calculator_input, "3+4*2`nexit`n", [System.Text.UTF8Encoding]::new($false))
[byte[]] $mini_calculator_expected = Get-VRunExpectedBytesWithStdin 'examples/mini_calculator.v' 'mini_calculator' $mini_calculator_input
Invoke-NativeX64ExampleWithStdin 'examples/mini_calculator.v' 'mini_calculator' $mini_calculator_expected $mini_calculator_input
$mini_calculator_recursive_descent_input = Join-Path $tmp 'mini_calculator_recursive_descent.in'
[System.IO.File]::WriteAllText($mini_calculator_recursive_descent_input, "3+4*2`nexit`n", [System.Text.UTF8Encoding]::new($false))
[byte[]] $mini_calculator_recursive_descent_expected = Get-VRunExpectedBytesWithStdin 'examples/mini_calculator_recursive_descent.v' 'mini_calculator_recursive_descent' $mini_calculator_recursive_descent_input
Invoke-NativeX64ExampleWithStdin 'examples/mini_calculator_recursive_descent.v' 'mini_calculator_recursive_descent' $mini_calculator_recursive_descent_expected $mini_calculator_recursive_descent_input
$random_ips_stdout = Invoke-NativeX64ExampleCapture 'examples/random_ips.v' 'random_ips'
Assert-RandomIpsStdout $random_ips_stdout
$rule110_stdout = Invoke-NativeX64ExampleCapture 'examples/rule110.v' 'rule110' @('31')
Assert-Rule110Stdout $rule110_stdout 31
- name: Build V with WX
run: v -cflags /WX self
- name: All code is formatted
run: v -silent test-cleancode
- name: Test -cc msvc works
run: v -no-retry-compilation run examples/hello_world.v
- name: Install dependencies
run: |
v retry -- v setup-freetype
.\.github\workflows\windows-install-sqlite.bat
- name: v doctor
run: |
v doctor
- name: Verify `v test` works
run: |
echo $VFLAGS
v cmd/tools/test_if_v_test_system_works.v
./cmd/tools/test_if_v_test_system_works
- name: Test pure V math module
run: v -silent -exclude @vlib/math/*.c.v test vlib/math/
- name: Self tests
run: v -silent test-self vlib
- name: Test v->js
run: v -o hi.js examples/js_hello_world.v && node hi.js
- name: Test v binaries
run: v build-vbinaries
- name: Build examples
run: v build-examples
- name: v2 self compilation
run: v -o v2.exe cmd/v && .\v2.exe -o v3.exe cmd/v
+93
View File
@@ -0,0 +1,93 @@
name: CI Windows TCC
on:
push:
branches:
- master
paths-ignore:
- '**.md'
- '**.yml'
- '!**.bat'
- '!**/windows_ci_tcc.yml'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
pull_request:
paths-ignore:
- '**.md'
- '**.yml'
- '!**.bat'
- '!**/windows_ci_tcc.yml'
- '!**/windows-install-sqlite.bat'
- 'cmd/tools/**'
- '!cmd/tools/builders/**.v'
concurrency:
group: windows-${{ github.workflow }}-${{ github.ref == 'refs/heads/master' && github.sha || github.ref }}
cancel-in-progress: true
jobs:
tcc-windows:
runs-on: windows-2022
timeout-minutes: 60
env:
VFLAGS: -cc tcc -no-retry-compilation
VTEST_SHOW_LONGEST_BY_RUNTIME: 3
VTEST_SHOW_LONGEST_BY_COMPTIME: 3
VTEST_SHOW_LONGEST_BY_TOTALTIME: 3
steps:
- uses: actions/checkout@v7
- name: Build with makev.bat -tcc
run: |
.\makev.bat -tcc
.\v.exe symlink
- name: All code is formatted
run: v -silent test-cleancode
- name: Test new v.c
run: |
v -o v.c cmd/v
$direct_c_flags = @(
'-Ithirdparty/zip'
'-Ithirdparty/cJSON'
'-Ithirdparty/mbedtls/library'
'-Ithirdparty/mbedtls/include'
'-Ithirdparty/mbedtls/3rdparty/everest/include'
'-Ithirdparty/mbedtls/3rdparty/everest/include/everest'
'-Ithirdparty/mbedtls/3rdparty/everest/include/everest/kremlib'
'-Ithirdparty/vschannel'
)
# Match makev.bat's Windows stack reserve; the direct TCC-built
# compiler can otherwise crash while compiling net.http-heavy scripts.
.\thirdparty\tcc\tcc.exe -Werror -w @direct_c_flags -ladvapi32 -lws2_32 -bt10 '-Wl,-stack=33554432' v.c
- name: Install dependencies
run: |
v retry -- v setup-freetype
.\.github\workflows\windows-install-sqlite.bat
- name: v -g self
run: v -g self
- name: v doctor
run: |
v doctor
- name: Verify `v test` works
run: |
v cmd/tools/test_if_v_test_system_works.v
.\cmd\tools\test_if_v_test_system_works.exe
- name: Verify `v vlib/v/gen/c/coutput_test.v` works
run: v vlib/v/gen/c/coutput_test.v
- name: Make sure running TCC64 instead of TCC32
run: v test .github\workflows\make_sure_ci_run_with_64bit_compiler_test.v
- name: Test ./v doc -v clipboard *BEFORE building tools*
run: v doc -v clipboard
- name: Test v build-tools
run: v -silent -W build-tools
- name: Test pure V math module
run: v -silent -exclude @vlib/math/*.c.v test vlib/math/
- name: Self tests
run: v -silent test-self vlib
- name: Test v->js
run: v -o hi.js examples/js_hello_world.v && node hi.js
- name: Test v binaries
run: v build-vbinaries
- name: Build examples
run: v build-examples
- name: v2 self compilation
run: v -o v2.exe cmd/v && .\v2.exe -o v3.exe cmd/v && .\v3.exe -o v4.exe cmd/v
+27
View File
@@ -0,0 +1,27 @@
name: Workflow Lint
## Note: to install `prettier` locally, see https://prettier.io/docs/en/install,
## or just: `npm install --save-dev --save-exact prettier`
## If you already have `prettier` installed, to run it locally,
## just run: `npx prettier --check **.yml` .
on:
push:
branches:
- master
paths:
- '**.yml'
pull_request:
paths:
- '**.yml'
jobs:
lint-yml-workflows:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v7
- name: Verify formatting
uses: creyD/prettier_action@v4.6
with:
prettier_options: --check **.yml
Loaded 100 of 11957 files, more files were not shown because too many files have changed in this diff. Show more